Exemplo n.º 1
0
int main(void)
{
    int count = 15;

    mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
    mount("sysfs", "/sys", "sysfs", 0, NULL);

    klog_init();
    klog_set_level(8);

    while (1) {
        if (!mount_device())
            break;

        if (count--) {
            sleep(2);
            dbg("Iago media not found, trying again...\n");
            continue;
        }
        KLOG_ERROR("Iago", "Couldn't find installation media!\n");
        exit(1); /* will result in kernel panic */
    }

    umount("/dev");
    umount("/sys");

    /* ok, start the real init */
    dbg("Installation media mounted, now starting Android init\n");
    execl("/init2", "init", NULL);
    KLOG_ERROR("Iago", "Failed to execl() Android init: %s\n", strerror(errno));
    return EXIT_FAILURE;
}
Exemplo n.º 2
0
int main(int argc, char *argv[])
{
    int a_flag=0;
    int u_flag=0;
    int n_flag=0;
    char *n_name=NULL;
    char *n_blk_dev=NULL;
    char *fstab_file=NULL;
    struct fstab *fstab=NULL;

    klog_set_level(6);

    parse_options(argc, argv, &a_flag, &u_flag, &n_flag, &n_name, &n_blk_dev);

    /* The name of the fstab file is last, after the option */
    fstab_file = argv[argc - 1];

    fstab = fs_mgr_read_fstab(fstab_file);

    if (a_flag) {
        return fs_mgr_mount_all(fstab);
    } else if (n_flag) {
        return fs_mgr_do_mount(fstab, n_name, n_blk_dev, 0);
    } else if (u_flag) {
        return fs_mgr_unmount_all(fstab);
    } else {
        ERROR("%s: Internal error, unknown option\n", me);
        exit(1);
    }

    fs_mgr_free_fstab(fstab);

    /* Should not get here */
    exit(1);
}
Exemplo n.º 3
0
int do_loglevel(int nargs, char **args) {
    if (nargs == 2) {
        klog_set_level(atoi(args[1]));
        return 0;
    }
    return -1;
}
Exemplo n.º 4
0
static int do_loglevel(const std::vector<std::string>& args) {
    int log_level = std::stoi(args[1]);
    if (log_level < KLOG_ERROR_LEVEL || log_level > KLOG_DEBUG_LEVEL) {
        ERROR("loglevel: invalid log level'%d'\n", log_level);
        return -EINVAL;
    }
    klog_set_level(log_level);
    return 0;
}
Exemplo n.º 5
0
int do_mount_all(int nargs, char **args)
{
    pid_t pid;
    int ret = -1;
    int child_ret = -1;
    int status;
    const char *prop;
    struct fstab *fstab;

    if (nargs != 2) {
        return -1;
    }

    /*
     * Call fs_mgr_mount_all() to mount all filesystems.  We fork(2) and
     * do the call in the child to provide protection to the main init
     * process if anything goes wrong (crash or memory leak), and wait for
     * the child to finish in the parent.
     */
    pid = fork();
    if (pid > 0) {
        /* Parent.  Wait for the child to return */
        waitpid(pid, &status, 0);
        if (WIFEXITED(status)) {
            ret = WEXITSTATUS(status);
        } else {
            ret = -1;
        }
    } else if (pid == 0) {
        /* child, call fs_mgr_mount_all() */
        klog_set_level(6);  /* So we can see what fs_mgr_mount_all() does */
        fstab = fs_mgr_read_fstab(args[1]);
        child_ret = fs_mgr_mount_all(fstab);
        fs_mgr_free_fstab(fstab);
        if (child_ret == -1) {
            ERROR("fs_mgr_mount_all returned an error\n");
        }
        exit(child_ret);
    } else {
        /* fork failed, return an error */
        return -1;
    }

    /* ret is 1 if the device is encrypted, 0 if not, and -1 on error */
    if (ret == 1) {
        property_set("ro.crypto.state", "encrypted");
        property_set("vold.decrypt", "1");
    } else if (ret == 0) {
        property_set("ro.crypto.state", "unencrypted");
        /* If fs_mgr determined this is an unencrypted device, then trigger
         * that action.
         */
        action_for_each_trigger("nonencrypted", action_add_queue_tail);
    }

    return ret;
}
Exemplo n.º 6
0
int main() {
    int ret;

    klog_set_level(KLOG_LEVEL);

    ret = uevent_init();
    if (ret == 0)
        ret = chargeled_mainloop();

    return ret;
}
Exemplo n.º 7
0
int ueventd_main(int argc, char **argv)
{
    /*
     * init sets the umask to 077 for forked processes. We need to
     * create files with exact permissions, without modification by
     * the umask.
     */
    umask(000);

    /* Prevent fire-and-forget children from becoming zombies.
     * If we should need to wait() for some children in the future
     * (as opposed to none right now), double-forking here instead
     * of ignoring SIGCHLD may be the better solution.
     */
    signal(SIGCHLD, SIG_IGN);

    open_devnull_stdio();
    klog_init();
    klog_set_level(KLOG_NOTICE_LEVEL);

    NOTICE("ueventd started!\n");

    selinux_callback cb;
    cb.func_log = selinux_klog_callback;
    selinux_set_callback(SELINUX_CB_LOG, cb);

    std::string hardware = property_get("ro.hardware");

    ueventd_parse_config_file("/ueventd.rc");
    ueventd_parse_config_file(android::base::StringPrintf("/ueventd.%s.rc", hardware.c_str()).c_str());

    device_init();

    pollfd ufd;
    ufd.events = POLLIN;
    ufd.fd = get_device_fd();

    while (true) {
        ufd.revents = 0;
        int nr = poll(&ufd, 1, -1);
        if (nr <= 0) {
            continue;
        }
        if (ufd.revents & POLLIN) {
            handle_device_fd();
        }
    }

    return 0;
}
Exemplo n.º 8
0
int main(int argc, char* argv[]) {
    int seg_fault_on_exit = 0;
    int log_target = LOG_ALOG;
    bool abbreviated = false;
    int ch;
    int status = 0xAAAA;
    int rc;

    while ((ch = getopt(argc, argv, "adk")) != -1) {
        switch (ch) {
            case 'a':
                abbreviated = true;
                break;
            case 'd':
                seg_fault_on_exit = 1;
                break;
            case 'k':
                log_target = LOG_KLOG;
                klog_set_level(6);
                break;
            case '?':
            default:
              usage();
        }
    }
    argc -= optind;
    argv += optind;

    if (argc < 1) {
        usage();
    }

    rc = android_fork_execvp_ext(argc, &argv[0], &status, true,
                                 log_target, abbreviated, NULL, NULL, 0);
    if (!rc) {
        if (WIFEXITED(status))
            rc = WEXITSTATUS(status);
        else
            rc = -ECHILD;
    }

    if (seg_fault_on_exit) {
        uintptr_t fault_address = (uintptr_t) status;
        *(int *) fault_address = 0;  // causes SIGSEGV with fault_address = status
    }

    return rc;
}
Exemplo n.º 9
0
int main(int argc, char *argv[])
{
    int i;
    for(i = 1; i < argc; ++i)
    {
        if(strcmp(argv[i], "-v") == 0)
        {
            printf("%d%s\n", VERSION_MULTIROM, VERSION_DEV_FIX);
            return 0;
        }
    }

    srand(time(0));
    klog_init();

    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    ERROR("Running MultiROM v%d%s\n", VERSION_MULTIROM, VERSION_DEV_FIX);

    int exit = multirom();

    if(exit >= 0)
    {
        if(exit & EXIT_REBOOT_MASK)
        {
            do_reboot(exit);
            return 0;
        }

        if(exit & EXIT_KEXEC)
        {
            do_kexec();
            return 0;
        }

        // indicates trampoline to keep /realdata mounted
        if(!(exit & EXIT_UMOUNT))
            close(open(KEEP_REALDATA, O_WRONLY | O_CREAT, 0000));
    }

    vt_set_mode(0);

    return 0;
}
Exemplo n.º 10
0
int do_loglevel(int nargs, char **args) {
    int log_level;
    char log_level_str[PROP_VALUE_MAX] = "";
    if (nargs != 2) {
        ERROR("loglevel: missing argument\n");
        return -EINVAL;
    }

    if (expand_props(log_level_str, args[1], sizeof(log_level_str))) {
        ERROR("loglevel: cannot expand '%s'\n", args[1]);
        return -EINVAL;
    }
    log_level = atoi(log_level_str);
    if (log_level < KLOG_ERROR_LEVEL || log_level > KLOG_DEBUG_LEVEL) {
        ERROR("loglevel: invalid log level'%d'\n", log_level);
        return -EINVAL;
    }
    klog_set_level(log_level);
    return 0;
}
Exemplo n.º 11
0
int main(int argc, char *argv[])
{
    if (argc > 1)
        return do_cmdline(argc, argv);

    int res;
    static char *const cmd[] = { "/init", NULL };

    umask(000);

    // Init only the little we need, leave the rest for real init
    mkdir("/dev", 0755);
    mkdir("/dev/pts", 0755);
    mkdir("/dev/socket", 0755);
    mkdir("/proc", 0755);
    mkdir("/sys", 0755);

    mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
    mount("devpts", "/dev/pts", "devpts", 0, NULL);
    mount("proc", "/proc", "proc", 0, NULL);
    mount("sysfs", "/sys", "sysfs", 0, NULL);
    mount("pstore", "/sys/fs/pstore", "pstore", 0, NULL);

#if MR_USE_DEBUGFS_MOUNT
    // Mount the debugfs kernel sysfs
    mkdir("/sys/kernel/debug", 0755);
    mount("debugfs", "/sys/kernel/debug", "debugfs", 0, NULL);
#endif

    klog_init();
    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    mrom_set_log_tag("trampoline");
    INFO("Running trampoline v%d\n", VERSION_TRAMPOLINE);

    if(is_charger_mode())
    {
        INFO("Charger mode detected, skipping multirom\n");
        goto run_main_init;
    }

#if MR_DEVICE_HOOKS >= 3
    tramp_hook_before_device_init();
#endif

    INFO("Initializing devices...\n");
    devices_init();
    INFO("Done initializing\n");

    run_core();

    // close and destroy everything
    devices_close();

run_main_init:
    umount("/dev/pts");
    rmdir("/dev/pts");
    rmdir("/dev/socket");

    if(access(KEEP_REALDATA, F_OK) < 0) {
        umount("/dev");
    }

#if MR_USE_DEBUGFS_MOUNT
    umount("/sys/kernel/debug");
#endif

    umount("/proc");
    umount("/sys/fs/pstore");
    umount("/sys");

    INFO("Running main_init\n");

    fixup_symlinks();

    chmod("/main_init", EXEC_MASK);
    rename("/main_init", "/init");

    res = execve(cmd[0], cmd, NULL);
    ERROR("execve returned %d %d %s\n", res, errno, strerror(errno));
    return 0;
}
int main(int argc, char **argv)
{
    int alarm_time = 5;
    int count = -1;
    bool abort_on_failure = false;

    while (1) {
        const static struct option long_options[] = {
            {"abort", no_argument, 0, 'a'},
            {"count", required_argument, 0, 'c'},
            {"time", required_argument, 0, 't'},
        };
        int c = getopt_long(argc, argv, "ac:t:", long_options, NULL);
        if (c < 0) {
            break;
        }

        switch (c) {
        case 'a':
            abort_on_failure = true;
            break;
        case 'c':
            count = strtoul(optarg, NULL, 0);
            break;
        case 't':
            alarm_time = strtoul(optarg, NULL, 0);
            break;
        case '?':
            usage();
            exit(EXIT_FAILURE);
        default:
            abort();
        }
    }

    klog_init();
    klog_set_level(KLOG_INFO_LEVEL);

    if (optind < argc) {
        fprintf(stderr, "Unexpected argument: %s\n", argv[optind]);
        usage();
        exit(EXIT_FAILURE);
    }

    int fd = timerfd_create(CLOCK_BOOTTIME_ALARM, 0);
    if (fd < 0) {
        perror("timerfd_create failed");
        exit(EXIT_FAILURE);
    }

    struct itimerspec delay = itimerspec();
    delay.it_value.tv_sec = alarm_time;
    int i = 0;

    int epoll_fd = epoll_create(1);
    if (epoll_fd < 0) {
        perror("epoll_create failed");
        exit(EXIT_FAILURE);
    }

    struct epoll_event ev = epoll_event();
    ev.events = EPOLLIN | EPOLLWAKEUP;
    int ret = epoll_ctl(epoll_fd, EPOLL_CTL_ADD, fd, &ev);
    if (ret < 0) {
        perror("epoll_ctl failed");
        exit(EXIT_FAILURE);
    }

    while (count != 0) {
        struct timespec expected_time;
        struct timespec actual_time;
        uint64_t fired = 0;

        ret = timerfd_settime(fd, 0, &delay, NULL);
        if (ret < 0) {
            perror("timerfd_settime failed");
            exit(EXIT_FAILURE);
        }

        ret = clock_gettime(CLOCK_BOOTTIME, &expected_time);
        if (ret < 0) {
            perror("failed to get time");
            exit(EXIT_FAILURE);
        }
        expected_time.tv_sec += alarm_time;

        ret = 0;
        while (ret != 1) {
            struct epoll_event out_ev;
            ret = epoll_wait(epoll_fd, &out_ev, 1, -1);
            if (ret < 0 && errno != EINTR) {
                perror("epoll_wait failed");
                exit(EXIT_FAILURE);
            }
        }

        ssize_t bytes = read(fd, &fired, sizeof(fired));
        if (bytes < 0) {
            perror("read from timer fd failed");
            exit(EXIT_FAILURE);
        } else if (bytes < (ssize_t)sizeof(fired)) {
            fprintf(stderr, "unexpected read from timer fd: %zd\n", bytes);
        }

        if (fired != 1) {
            fprintf(stderr, "unexpected timer fd fired count: %" PRIu64 "\n", fired);
        }

        ret = clock_gettime(CLOCK_BOOTTIME, &actual_time);
        if (ret < 0) {
            perror("failed to get time");
            exit(EXIT_FAILURE);
        }

        long long diff = timediff_ns(&actual_time, &expected_time);
        if (llabs(diff) > NSEC_PER_SEC) {
            fprintf(stderr, "alarm arrived %lld.%03lld seconds %s\n",
                    llabs(diff) / NSEC_PER_SEC,
                    (llabs(diff) / NSEC_PER_MSEC) % MSEC_PER_SEC,
                    diff > 0 ? "late" : "early");
            KLOG_ERROR("suspend_stress", "alarm arrived %lld.%03lld seconds %s\n",
                    llabs(diff) / NSEC_PER_SEC,
                    (llabs(diff) / NSEC_PER_MSEC) % MSEC_PER_SEC,
                    diff > 0 ? "late" : "early");
            if (abort_on_failure) {
                exit(EXIT_FAILURE);
            }
        }

        time_t t = time(NULL);
        i += fired;
        printf("timer fired: %d at boottime %lld.%.3ld, %s", i,
                   (long long)actual_time.tv_sec,
                   actual_time.tv_nsec / NSEC_PER_MSEC,
                   ctime(&t));

        KLOG_INFO("suspend_stress", "timer fired: %d at boottime %lld.%.3ld, %s", i,
                   (long long)actual_time.tv_sec,
                   actual_time.tv_nsec / NSEC_PER_MSEC,
                   ctime(&t));

        if (count > 0)
            count--;
    }
    return 0;
}
Exemplo n.º 13
0
/*
 * This function might request a reboot, in which case it will
 * not return.
 */
int do_mount_all(int nargs, char **args)
{
    pid_t pid;
    int ret = -1;
    int child_ret = -1;
    int status;
    struct fstab *fstab;

    if (nargs != 2) {
        return -1;
    }

    /*
     * Call fs_mgr_mount_all() to mount all filesystems.  We fork(2) and
     * do the call in the child to provide protection to the main init
     * process if anything goes wrong (crash or memory leak), and wait for
     * the child to finish in the parent.
     */
    pid = fork();
    if (pid > 0) {
        /* Parent.  Wait for the child to return */
        int wp_ret = TEMP_FAILURE_RETRY(waitpid(pid, &status, 0));
        if (wp_ret < 0) {
            /* Unexpected error code. We will continue anyway. */
            NOTICE("waitpid failed rc=%d, errno=%d\n", wp_ret, errno);
        }

        if (WIFEXITED(status)) {
            ret = WEXITSTATUS(status);
        } else {
            ret = -1;
        }
    } else if (pid == 0) {
        /* child, call fs_mgr_mount_all() */
        klog_set_level(6);  /* So we can see what fs_mgr_mount_all() does */
        fstab = fs_mgr_read_fstab(args[1]);
        child_ret = fs_mgr_mount_all(fstab);
        fs_mgr_free_fstab(fstab);
        if (child_ret == -1) {
            ERROR("fs_mgr_mount_all returned an error\n");
        }
        _exit(child_ret);
    } else {
        /* fork failed, return an error */
        return -1;
    }

    if (ret == FS_MGR_MNTALL_DEV_NEEDS_ENCRYPTION) {
        property_set("vold.decrypt", "trigger_encryption");
    } else if (ret == FS_MGR_MNTALL_DEV_MIGHT_BE_ENCRYPTED) {
        property_set("ro.crypto.state", "encrypted");
        property_set("vold.decrypt", "trigger_default_encryption");
    } else if (ret == FS_MGR_MNTALL_DEV_NOT_ENCRYPTED) {
        property_set("ro.crypto.state", "unencrypted");
        /* If fs_mgr determined this is an unencrypted device, then trigger
         * that action.
         */
        action_for_each_trigger("nonencrypted", action_add_queue_tail);
    } else if (ret == FS_MGR_MNTALL_DEV_NEEDS_RECOVERY) {
        /* Setup a wipe via recovery, and reboot into recovery */
        ERROR("fs_mgr_mount_all suggested recovery, so wiping data via recovery.\n");
        ret = wipe_data_via_recovery();
        /* If reboot worked, there is no return. */
    } else if (ret > 0) {
        ERROR("fs_mgr_mount_all returned unexpected error %d\n", ret);
    }
    /* else ... < 0: error */

    return ret;
}
Exemplo n.º 14
0
int main(int argc, const char *argv[])
{
    int i;
    const char *rom_to_boot = NULL;

    for(i = 1; i < argc; ++i)
    {
        if(strcmp(argv[i], "-v") == 0)
        {
            printf("%d%s apkL%d\n", VERSION_MULTIROM, VERSION_DEV_FIX, VERSION_APKL);
            fflush(stdout);
            return 0;
        }
        else if(strcmp(argv[i], "-apkL") == 0)
        {
            // Return all (internal and external) installed ROMs needed for the MultiROM Manager app

            // external partitions will be mounted to /mnt/mrom/APK and kept mounted so the app
            // can manipulate them, use "multirom -apkU" to unmount them when no longer needed

            // unmount everything in /mnt/mrom/APK first
            //multirom_apk_umount_usb();

            int i;
            struct multirom_status s;
            memset(&s, 0, sizeof(struct multirom_status));

            multirom_apk_get_roms(&s);

            for(i = 0; s.roms && s.roms[i]; ++i)
            {
                if (!s.roms[i]->partition)
                {
                    // Internal ROMs
                    printf("ROM: name=%s base=%s icon=%s\n",
                        s.roms[i]->name, s.roms[i]->base_path, s.roms[i]->icon_path);
                }
                else
                {
                    // External ROMs
                    printf("ROM: name=%s base=%s icon=%s part_name=%s part_mount=%s part_uuid=%s part_fs=%s\n",
                        s.roms[i]->name, s.roms[i]->base_path, s.roms[i]->icon_path,
                        s.roms[i]->partition->name, s.roms[i]->partition->mount_path, s.roms[i]->partition->uuid, s.roms[i]->partition->fs);
                }
            }
            fflush(stdout);

            multirom_free_status(&s);

            return 0;
        }
        else if(strcmp(argv[i], "-apkU") == 0)
        {
            // Unmount all partitions mounted in /mnt/mrom/APK
            multirom_apk_umount_usb();

            return 0;
        }
        else if(strncmp(argv[i], "--boot-rom=", sizeof("--boot-rom")) == 0)
        {
            rom_to_boot = argv[i] + sizeof("--boot-rom");
        }
    }

    srand(time(0));
    klog_init();

    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    mrom_set_log_tag("multirom");

    ERROR("Running MultiROM v%d%s\n", VERSION_MULTIROM, VERSION_DEV_FIX);

    // root is mounted read only in android and MultiROM uses
    // it to store some temp files, so remount it.
    // Yes, there is better solution to this.
    if(rom_to_boot)
        mount(NULL, "/", NULL, MS_REMOUNT, NULL);

    int exit = multirom(rom_to_boot);

    if(rom_to_boot)
        mount(NULL, "/", NULL, MS_RDONLY | MS_REMOUNT, NULL);

    if(exit >= 0)
    {
        if(exit & EXIT_REBOOT_RECOVERY)
            do_reboot(REBOOT_RECOVERY);
        else if(exit & EXIT_REBOOT_BOOTLOADER)
            do_reboot(REBOOT_BOOTLOADER);
        else if(exit & EXIT_SHUTDOWN)
            do_reboot(REBOOT_SHUTDOWN);
        else if(exit & EXIT_REBOOT)
            do_reboot(REBOOT_SYSTEM);

        if(exit & EXIT_KEXEC)
        {
            do_kexec();
            return 0;
        }

        // indicates trampoline to keep /realdata mounted
        if(!(exit & EXIT_UMOUNT))
            close(open(KEEP_REALDATA, O_WRONLY | O_CREAT, 0000));
    }

    return 0;
}
Exemplo n.º 15
0
int main(int argc, char** argv) {
    if (!strcmp(basename(argv[0]), "ueventd")) {
        return ueventd_main(argc, argv);
    }

    if (!strcmp(basename(argv[0]), "watchdogd")) {
        return watchdogd_main(argc, argv);
    }

    // Clear the umask.
    umask(0);

    add_environment("PATH", _PATH_DEFPATH);

    bool is_first_stage = (argc == 1) || (strcmp(argv[1], "--second-stage") != 0);

    // Get the basic filesystem setup we need put together in the initramdisk
    // on / and then we'll let the rc file figure out the rest.
    if (is_first_stage) {
        mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
        mkdir("/dev/pts", 0755);
        mkdir("/dev/socket", 0755);
        mount("devpts", "/dev/pts", "devpts", 0, NULL);
        #define MAKE_STR(x) __STRING(x)
        mount("proc", "/proc", "proc", 0, "hidepid=2,gid=" MAKE_STR(AID_READPROC));
        mount("sysfs", "/sys", "sysfs", 0, NULL);
        mount("selinuxfs", "/sys/fs/selinux", "selinuxfs", 0, NULL);
    }

    // We must have some place other than / to create the device nodes for
    // kmsg and null, otherwise we won't be able to remount / read-only
    // later on. Now that tmpfs is mounted on /dev, we can actually talk
    // to the outside world.
    open_devnull_stdio();
    klog_init();
    klog_set_level(KLOG_NOTICE_LEVEL);

    NOTICE("init %s started!\n", is_first_stage ? "first stage" : "second stage");

    if (!is_first_stage) {
        // Indicate that booting is in progress to background fw loaders, etc.
        close(open("/dev/.booting", O_WRONLY | O_CREAT | O_CLOEXEC, 0000));

        property_init();

        // If arguments are passed both on the command line and in DT,
        // properties set in DT always have priority over the command-line ones.
        process_kernel_dt();
        process_kernel_cmdline();

        // Propagate the kernel variables to internal variables
        // used by init as well as the current required properties.
        export_kernel_boot_props();
    }

    // Set up SELinux, including loading the SELinux policy if we're in the kernel domain.
    selinux_initialize(is_first_stage);

    // If we're in the kernel domain, re-exec init to transition to the init domain now
    // that the SELinux policy has been loaded.
    if (is_first_stage) {
        if (restorecon("/init") == -1) {
            ERROR("restorecon failed: %s\n", strerror(errno));
            security_failure();
        }
        char* path = argv[0];
        char* args[] = { path, const_cast<char*>("--second-stage"), nullptr };
        if (execv(path, args) == -1) {
            ERROR("execv(\"%s\") failed: %s\n", path, strerror(errno));
            security_failure();
        }
    }

    // These directories were necessarily created before initial policy load
    // and therefore need their security context restored to the proper value.
    // This must happen before /dev is populated by ueventd.
    NOTICE("Running restorecon...\n");
    restorecon("/dev");
    restorecon("/dev/socket");
    restorecon("/dev/__properties__");
    restorecon("/property_contexts");
    restorecon_recursive("/sys");

    epoll_fd = epoll_create1(EPOLL_CLOEXEC);
    if (epoll_fd == -1) {
        ERROR("epoll_create1 failed: %s\n", strerror(errno));
        exit(1);
    }

    signal_handler_init();

    property_load_boot_defaults();
    export_oem_lock_status();
    start_property_service();

    const BuiltinFunctionMap function_map;
    Action::set_function_map(&function_map);

    Parser& parser = Parser::GetInstance();
    parser.AddSectionParser("service",std::make_unique<ServiceParser>());
    parser.AddSectionParser("on", std::make_unique<ActionParser>());
    parser.AddSectionParser("import", std::make_unique<ImportParser>());
    parser.ParseConfig("/init.rc");

    ActionManager& am = ActionManager::GetInstance();

    am.QueueEventTrigger("early-init");

    // Queue an action that waits for coldboot done so we know ueventd has set up all of /dev...
    am.QueueBuiltinAction(wait_for_coldboot_done_action, "wait_for_coldboot_done");
    // ... so that we can start queuing up actions that require stuff from /dev.
    am.QueueBuiltinAction(mix_hwrng_into_linux_rng_action, "mix_hwrng_into_linux_rng");
    am.QueueBuiltinAction(keychord_init_action, "keychord_init");
    am.QueueBuiltinAction(console_init_action, "console_init");

    // Trigger all the boot actions to get us started.
    am.QueueEventTrigger("init");

    // Repeat mix_hwrng_into_linux_rng in case /dev/hw_random or /dev/random
    // wasn't ready immediately after wait_for_coldboot_done
    am.QueueBuiltinAction(mix_hwrng_into_linux_rng_action, "mix_hwrng_into_linux_rng");

    // Don't mount filesystems or start core system services in charger mode.
    std::string bootmode = property_get("ro.bootmode");
    if (bootmode == "charger") {
        am.QueueEventTrigger("charger");
    } else {
        am.QueueEventTrigger("late-init");
    }

    // Run all property triggers based on current state of the properties.
    am.QueueBuiltinAction(queue_property_triggers_action, "queue_property_triggers");

    while (true) {
        if (!waiting_for_exec) {
            am.ExecuteOneCommand();
            restart_processes();
        }

        int timeout = -1;
        if (process_needs_restart) {
            timeout = (process_needs_restart - gettime()) * 1000;
            if (timeout < 0)
                timeout = 0;
        }

        if (am.HasMoreCommands()) {
            timeout = 0;
        }

        bootchart_sample(&timeout);

        epoll_event ev;
        int nr = TEMP_FAILURE_RETRY(epoll_wait(epoll_fd, &ev, 1, timeout));
        if (nr == -1) {
            ERROR("epoll_wait failed: %s\n", strerror(errno));
        } else if (nr == 1) {
            ((void (*)()) ev.data.ptr)();
        }
    }

    return 0;
}
int main(int argc, char *argv[]) {
    int print_cmd = 0;
    int config_cmd = 0;
    int add_cmd = 0;
    int del_cmd = 0;
    int sync_cmd = 0;
    int c;
    const char *new_partition = NULL;
    const char *old_partition = NULL;
    const char *type_guid = NULL;
    const char *partition_guid = NULL;
    unsigned gpt_location = 1;

    klog_init();
    klog_set_level(6);

    const struct option longopts[] = {
        {"print", no_argument, 0, 'p'},
        {"config-print", no_argument, 0, 'c'},
        {"add", no_argument, 0, 'a'},
        {"del", no_argument, 0, 'd'},
        {"new", required_argument, 0, 'n'},
        {"old", required_argument, 0, 'o'},
        {"type", required_argument, 0, 't'},
        {"sync", required_argument, 0, 's'},
        {"guid", required_argument, 0, 'g'},
        {"location", required_argument, 0, 'l'},
        {0, 0, 0, 0}
    };

    while (1) {
        c = getopt_long(argc, argv, "pcadt:g:n:o:sl:", longopts, NULL);
        /* Alphabetical cases */
        if (c < 0)
            break;
        switch (c) {
        case 'p':
            print_cmd = 1;
            break;
        case 'c':
            config_cmd = 1;
            break;
        case 'a':
            add_cmd = 1;
            break;
        case 'd':
            del_cmd = 1;
            break;
        case 'n':
            new_partition = optarg;
            break;
        case 'o':
            old_partition = optarg;
            break;
        case 't':
            type_guid = optarg;
        case 'g':
            partition_guid = optarg;
            break;
        case 's':
            sync_cmd = 1;
            break;
        case 'l':
            gpt_location = strtoul(optarg, NULL, 10);
            fprintf(stderr, "Got offset as %d", gpt_location);
            break;
        case '?':
            return 1;
        default:
            abort();
        }
    }

    argc -= optind;
    argv += optind;

    if (argc < 1) {
        usage();
        return 1;
    }

    const char *path = argv[0];
    struct GPT_entry_table *table = GPT_get_device(path, gpt_location);
    if (table == NULL) {
        fprintf(stderr, "unable to get GPT table from %s\n", path);
        return 1;
    }

    if (add_cmd)
        addGPT(table, new_partition, partition_guid, type_guid);
    if (del_cmd)
        deleteGPT(table, old_partition);
    if (print_cmd)
        printGPT(table);
    if (config_cmd)
        configPrintGPT(table);
    if (sync_cmd)
        GPT_sync(table);

    GPT_release_device(table);

    return 0;
}
Exemplo n.º 17
0
int main(int argc, char **argv)
{
    int fd_count = 0;
    struct pollfd ufds[4];
    char *tmpdev;
    char* debuggable;
    char tmp[32];
    int property_set_fd_init = 0;
    int signal_fd_init = 0;
    int keychord_fd_init = 0;
    bool is_charger = false;
#ifdef MTK_INIT
    int mt_boot_mode = 0;

    klog_set_level(6);
#endif
    if (!strcmp(basename(argv[0]), "ueventd"))
        return ueventd_main(argc, argv);

    if (!strcmp(basename(argv[0]), "watchdogd"))
        return watchdogd_main(argc, argv);

    /* clear the umask */
    umask(0);

        /* Get the basic filesystem setup we need put
         * together in the initramdisk on / and then we'll
         * let the rc file figure out the rest.
         */
    mkdir("/dev", 0755);
    mkdir("/proc", 0755);
    mkdir("/sys", 0755);

    mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
    mkdir("/dev/pts", 0755);
    mkdir("/dev/socket", 0755);
    mount("devpts", "/dev/pts", "devpts", 0, NULL);
    mount("proc", "/proc", "proc", 0, NULL);
    mount("sysfs", "/sys", "sysfs", 0, NULL);

#ifdef INIT_ENG_BUILD
    mount("debugfs", "/sys/kernel/debug", "debugfs", 0, NULL);
#endif
        /* indicate that booting is in progress to background fw loaders, etc */
    close(open("/dev/.booting", O_WRONLY | O_CREAT, 0000));

        /* We must have some place other than / to create the
         * device nodes for kmsg and null, otherwise we won't
         * be able to remount / read-only later on.
         * Now that tmpfs is mounted on /dev, we can actually
         * talk to the outside world.
         */
    open_devnull_stdio();
    klog_init();
    property_init();

    get_hardware_name(hardware, &revision);

    process_kernel_cmdline();

    union selinux_callback cb;
    cb.func_log = log_callback;
    selinux_set_callback(SELINUX_CB_LOG, cb);

    cb.func_audit = audit_callback;
    selinux_set_callback(SELINUX_CB_AUDIT, cb);

    selinux_initialize();
    /* These directories were necessarily created before initial policy load
     * and therefore need their security context restored to the proper value.
     * This must happen before /dev is populated by ueventd.
     */
    restorecon("/dev");
    restorecon("/dev/socket");
    restorecon("/dev/__properties__");
    restorecon_recursive("/sys");

    is_charger = !strcmp(bootmode, "charger");

    INFO("property init\n");
    property_load_boot_defaults();
#ifndef INIT_ENG_BUILD
    property_set("ro.mtprof.disable", "1");
#endif


    INFO("reading config file\n");

#ifdef MTK_INIT
/* NEW FEATURE: multi-boot mode */
    mt_boot_mode = get_boot_mode();
    if ( (mt_boot_mode == MT_FACTORY_BOOT) || (mt_boot_mode == MT_ATE_FACTORY_BOOT) ) {
        printf("Factory Mode Booting.....\n");
        property_set("sys.mtk.no.factoryimage","1");
        init_parse_config_file("/factory_init.rc");
        init_parse_config_file("/factory_init.project.rc");
    }
    else if ( mt_boot_mode == MT_META_BOOT ) {
        printf("META Mode Booting.....\n");
        init_parse_config_file("/meta_init.rc");
        init_parse_config_file("/meta_init.project.rc");
    }
	else
     {
#endif // MTK_INIT
        init_parse_config_file("/init.rc");
#ifdef MTK_INIT
    }
#endif

#ifdef MTK_INIT
    if ( (mt_boot_mode == MT_FACTORY_BOOT) || (mt_boot_mode == MT_ATE_FACTORY_BOOT) ) {
    	  NOTICE("No need modem.rc for factory mode\n");
    }
    else if ( mt_boot_mode == MT_META_BOOT ) {
        init_parse_config_file("/meta_init.modem.rc");
    }else {
        init_parse_config_file("/init.modem.rc");
    }
#endif // MTK_INIT
/**** End of Parsing .rc files ****/

    action_for_each_trigger("early-init", action_add_queue_tail);

    queue_builtin_action(wait_for_coldboot_done_action, "wait_for_coldboot_done");
    queue_builtin_action(mix_hwrng_into_linux_rng_action, "mix_hwrng_into_linux_rng");
    queue_builtin_action(keychord_init_action, "keychord_init");
    queue_builtin_action(console_init_action, "console_init");

    /* execute all the boot actions to get us started */
    action_for_each_trigger("init", action_add_queue_tail);

    /* Repeat mix_hwrng_into_linux_rng in case /dev/hw_random or /dev/random
     * wasn't ready immediately after wait_for_coldboot_done
     */
    queue_builtin_action(mix_hwrng_into_linux_rng_action, "mix_hwrng_into_linux_rng");
    queue_builtin_action(property_service_init_action, "property_service_init");
    queue_builtin_action(signal_init_action, "signal_init");

    /* Don't mount filesystems or start core system services if in charger mode. */
    if (is_charger) {
        action_for_each_trigger("charger", action_add_queue_tail);
    }
    else
     {
        action_for_each_trigger("late-init", action_add_queue_tail);
    }

    /* run all property triggers based on current state of the properties */
    queue_builtin_action(queue_property_triggers_action, "queue_property_triggers");

#if BOOTCHART
    queue_builtin_action(bootchart_init_action, "bootchart_init");
#endif

    for(;;) {
        int nr, i, timeout = -1;

        execute_one_command();
        restart_processes();

        if (!property_set_fd_init && get_property_set_fd() > 0) {
            ufds[fd_count].fd = get_property_set_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            property_set_fd_init = 1;
        }
        if (!signal_fd_init && get_signal_fd() > 0) {
            ufds[fd_count].fd = get_signal_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            signal_fd_init = 1;
        }
        if (!keychord_fd_init && get_keychord_fd() > 0) {
            ufds[fd_count].fd = get_keychord_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            keychord_fd_init = 1;
        }

        if (process_needs_restart) {
            timeout = (process_needs_restart - gettime()) * 1000;
            if (timeout < 0)
                timeout = 0;
        }

        if (!action_queue_empty() || cur_action)
            timeout = 0;

#if BOOTCHART
        if (bootchart_count > 0) {
            if (timeout < 0 || timeout > BOOTCHART_POLLING_MS)
                timeout = BOOTCHART_POLLING_MS;
            if (bootchart_step() < 0 || --bootchart_count == 0) {
                bootchart_finish();
                bootchart_count = 0;
            }
        }
#endif

        nr = poll(ufds, fd_count, timeout);
        if (nr <= 0)
            continue;

        for (i = 0; i < fd_count; i++) {
            if (ufds[i].revents & POLLIN) {
                if (ufds[i].fd == get_property_set_fd())
                    handle_property_set_fd();
                else if (ufds[i].fd == get_keychord_fd())
                    handle_keychord();
                else if (ufds[i].fd == get_signal_fd())
                    handle_signal();
            }
        }
    }

    return 0;
}
Exemplo n.º 18
0
int main(int argc, char **argv)
{
    int fd_count = 0;
    struct pollfd ufds[4];
    char *tmpdev;
    char* debuggable;
    char tmp[32];
    int property_set_fd_init = 0;
    int signal_fd_init = 0;
    int keychord_fd_init = 0;
    bool is_charger = false;

    klog_set_level(LOG_DEFAULT_LEVEL);
    if (!strcmp(basename(argv[0]), "ueventd"))
        return ueventd_main(argc, argv);

    if (!strcmp(basename(argv[0]), "watchdogd"))
        return watchdogd_main(argc, argv);

    /* clear the umask */
    umask(0);

        /* Get the basic filesystem setup we need put
         * together in the initramdisk on / and then we'll
         * let the rc file figure out the rest.
         */
    mkdir("/dev", 0755);
    mkdir("/proc", 0755);
    mkdir("/sys", 0755);

    mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
    mkdir("/dev/pts", 0755);
    mkdir("/dev/socket", 0755);
    mount("devpts", "/dev/pts", "devpts", 0, NULL);
    mount("proc", "/proc", "proc", 0, NULL);
    mount("sysfs", "/sys", "sysfs", 0, NULL);

#ifdef INIT_ENG_BUILD
    mount("debugfs", "/sys/kernel/debug", "debugfs", 0, NULL);
#endif
        /* indicate that booting is in progress to background fw loaders, etc */
    close(open("/dev/.booting", O_WRONLY | O_CREAT, 0000));

        /* We must have some place other than / to create the
         * device nodes for kmsg and null, otherwise we won't
         * be able to remount / read-only later on.
         * Now that tmpfs is mounted on /dev, we can actually
         * talk to the outside world.
         */
    //open_devnull_stdio();
    klog_init();
    property_init();

    get_hardware_name(hardware, &revision);

    process_kernel_cmdline();

#ifdef HAVE_SELINUX
    union selinux_callback cb;
    cb.func_log = klog_write;
    selinux_set_callback(SELINUX_CB_LOG, cb);

    cb.func_audit = audit_callback;
    selinux_set_callback(SELINUX_CB_AUDIT, cb);

    INFO("loading selinux policy\n");
    if (selinux_enabled) {
        if (selinux_android_load_policy() < 0) {
            selinux_enabled = 0;
            INFO("SELinux: Disabled due to failed policy load\n");
        } else {
            selinux_init_all_handles();
        }
    } else {
        INFO("SELinux:  Disabled by command line option\n");
    }
    /* These directories were necessarily created before initial policy load
     * and therefore need their security context restored to the proper value.
     * This must happen before /dev is populated by ueventd.
     */
    restorecon("/dev");
    restorecon("/dev/socket");
#endif

    is_charger = !strcmp(bootmode, "charger");

    INFO("property init\n");
    if (!is_charger)
        property_load_boot_defaults();

#ifdef HAVE_AEE_FEATURE
    INFO("reading AEE config file\n");
#ifndef PARTIAL_BUILD
	init_parse_config_file("/init.aee.mtk.rc");
#else
	init_parse_config_file("/init.aee.customer.rc");
#endif // PARTIAL_BUILD

#endif // HAVE_AEE_FEATURE
    INFO("reading config file\n");

#ifdef USE_BUILT_IN_FACTORY
    ERROR("USE_BUILT_IN_FACTORY");
    if (is_factory_boot())
    {
        ERROR("This is factory boot");
        property_set("sys.mtk.no.factoryimage","1");
        init_parse_config_file("/factory_init.rc");
            INFO("reading project config file\n");
        init_parse_config_file("/factory_init.project.rc");
    }
    else
    {
        if(is_meta_boot())
        {
            ERROR("Parsing meta_init.rc ...\n");
            init_parse_config_file("/meta_init.rc");
            INFO("reading project config file\n");
            init_parse_config_file("/meta_init.project.rc");
            init_parse_config_file("/meta_init.modem.rc");
        }
        else if(is_advanced_meta_boot())
        {
            ERROR("Parsing advanced_meta_init.rc ...\n");
            init_parse_config_file("/advanced_meta_init.rc");
            INFO("reading project config file\n");
            init_parse_config_file("/advanced_meta_init.project.rc");
#ifdef MTK_FAT_ON_NAND
            printf("reading init.fon.rc file\n");
            init_parse_config_file("/init.fon.rc");
#endif
        }
        #if defined (MTK_KERNEL_POWER_OFF_CHARGING_SUPPORT)
	else if (is_kernel_power_off_charging_boot())
    {
        ERROR("Parsing init.charging.rc ...\n");
        if (init_parse_config_file("/init.charging.rc") < 0)
        {
            init_parse_config_file("/init.rc");
            INFO("reading project config file\n");
            init_parse_config_file("/init.project.rc");
            init_parse_config_file("/init.modem.rc");
	    }
	}
	#endif
        else
        {
            printf("Parsing init.rc ...\n");
            init_parse_config_file("/init.rc");
            INFO("reading project config file\n");
            init_parse_config_file("/init.project.rc");
            init_parse_config_file("/init.modem.rc");
#ifdef MTK_FAT_ON_NAND
            printf("reading init.fon.rc file\n");
            init_parse_config_file("/init.fon.rc");
#endif
        }
    }
#else
    if(is_meta_boot())
    {
        ERROR("Parsing meta_init.rc ...\n");
        init_parse_config_file("/meta_init.rc");
        INFO("reading project config file\n");
        init_parse_config_file("/meta_init.project.rc");
        init_parse_config_file("/meta_init.modem.rc");
    }
    else if(is_advanced_meta_boot())
    {
        ERROR("Parsing advanced_meta_init.rc ...\n");
        init_parse_config_file("/advanced_meta_init.rc");
        INFO("reading project config file\n");
        init_parse_config_file("/advanced_meta_init.project.rc");
    }
    else
    {
        printf("Parsing init.rc ...\n");
        init_parse_config_file("/init.rc");
        INFO("reading project config file\n");
        init_parse_config_file("/init.project.rc");
        init_parse_config_file("/init.modem.rc");
    }
#endif
#ifdef MTK_SHARED_SDCARD
    if(is_support_sdcard_share_boot())
    {
#ifdef MTK_2SDCARD_SWAP
        printf("Parsing init.ssd_sdswap.rc ...\n");
        init_parse_config_file("/init.ssd_nomuser.rc");
#else
        printf("Parsing init.ssd.rc ...\n");
        init_parse_config_file("/init.ssd.rc");
#endif
    }
    else 
    {
        printf("Parsing init.no_ssd.rc ...\n");
        init_parse_config_file("/init.no_ssd.rc");
    }
#else 
    printf("Parsing init.no_ssd.rc ...\n");
    init_parse_config_file("/init.no_ssd.rc");
#endif

#ifndef INIT_ENG_BUILD
    property_set("ro.mtprof.disable", "1");
#endif

    if(is_support_protected_data_boot())
    {       	    
	printf("Parsing init.protect.rc ...\n");  
        init_parse_config_file("/init.protect.rc");
    }
    snprintf(tmp, sizeof(tmp), "/init.%s.rc", hardware);
    init_parse_config_file(tmp);

    action_for_each_trigger("early-init", action_add_queue_tail);

    queue_builtin_action(wait_for_coldboot_done_action, "wait_for_coldboot_done");
    queue_builtin_action(keychord_init_action, "keychord_init");
    queue_builtin_action(console_init_action, "console_init");

    /* execute all the boot actions to get us started */
    action_for_each_trigger("init", action_add_queue_tail);

    /* skip mounting filesystems in charger mode */
    if (!is_charger) {
        queue_builtin_action(queue_fs_property_triggers_action, "queue_fs_propety_triggers");
        action_for_each_trigger("early-fs", action_add_queue_tail);
        action_for_each_trigger("fs", action_add_queue_tail);
        action_for_each_trigger("post-fs", action_add_queue_tail);
        action_for_each_trigger("post-fs-data", action_add_queue_tail);
    }

    queue_builtin_action(property_service_init_action, "property_service_init");
    queue_builtin_action(signal_init_action, "signal_init");
    queue_builtin_action(check_startup_action, "check_startup");

    queue_builtin_action(queue_early_property_triggers_action, "queue_early_propety_triggers");
    if (is_charger) {
        action_for_each_trigger("charger", action_add_queue_tail);
    }
#if defined (MTK_KERNEL_POWER_OFF_CHARGING_SUPPORT)
    else if (is_kernel_power_off_charging_boot()){
	action_for_each_trigger("ipo", action_add_queue_tail);
    } 
#endif
    else {
        action_for_each_trigger("early-boot", action_add_queue_tail);
        action_for_each_trigger("boot", action_add_queue_tail);
    }

        /* run all property triggers based on current state of the properties */
    queue_builtin_action(queue_property_triggers_action, "queue_property_triggers");

    /* change USB function by meta_com_id */
#ifdef USE_BUILT_IN_FACTORY
    if (is_meta_boot() || is_factory_boot()) {
        queue_builtin_action(queue_com_triggers_action, "queue_com_triggers");
    }
#else
    if (is_meta_boot()) {
        queue_builtin_action(queue_com_triggers_action, "queue_com_triggers");
    }
#endif


#if BOOTCHART
    queue_builtin_action(bootchart_init_action, "bootchart_init");
#endif

    for(;;) {
        int nr, i, timeout = -1;

        execute_one_command();
        restart_processes();

        if (!property_set_fd_init && get_property_set_fd() > 0) {
            ufds[fd_count].fd = get_property_set_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            property_set_fd_init = 1;
        }
        if (!signal_fd_init && get_signal_fd() > 0) {
            ufds[fd_count].fd = get_signal_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            signal_fd_init = 1;
        }
        if (!keychord_fd_init && get_keychord_fd() > 0) {
            ufds[fd_count].fd = get_keychord_fd();
            ufds[fd_count].events = POLLIN;
            ufds[fd_count].revents = 0;
            fd_count++;
            keychord_fd_init = 1;
        }

        if (process_needs_restart) {
            timeout = (process_needs_restart - gettime()) * 1000;
            if (timeout < 0)
                timeout = 0;
        }

        if (!action_queue_empty() || cur_action)
            timeout = 0;

#if BOOTCHART
        if (bootchart_count > 0) {
            if (timeout < 0 || timeout > BOOTCHART_POLLING_MS)
                timeout = BOOTCHART_POLLING_MS;
            if (bootchart_step() < 0 || --bootchart_count == 0) {
                bootchart_finish();
                bootchart_count = 0;
            }
        }
#endif

        nr = poll(ufds, fd_count, timeout);
        if (nr <= 0)
            continue;

        for (i = 0; i < fd_count; i++) {
            if (ufds[i].revents == POLLIN) {
                if (ufds[i].fd == get_property_set_fd())
                    handle_property_set_fd();
                else if (ufds[i].fd == get_keychord_fd())
                    handle_keychord();
                else if (ufds[i].fd == get_signal_fd())
                    handle_signal();
            }
        }
    }

    return 0;
}
Exemplo n.º 19
0
/*
 * This function might request a reboot, in which case it will
 * not return.
 */
int do_mount_all(int nargs, char **args)
{
    pid_t pid;
    int ret = -1;
    int child_ret = -1;
    int status;
    char boot_mode[PROP_VALUE_MAX] = {0};
    struct fstab *fstab;

    if (nargs != 2) {
        return -1;
    }

    /*
     * Call fs_mgr_mount_all() to mount all filesystems.  We fork(2) and
     * do the call in the child to provide protection to the main init
     * process if anything goes wrong (crash or memory leak), and wait for
     * the child to finish in the parent.
     */
    pid = fork();
    if (pid > 0) {
        /* Parent.  Wait for the child to return */
        int wp_ret = TEMP_FAILURE_RETRY(waitpid(pid, &status, 0));
        if (wp_ret < 0) {
            /* Unexpected error code. We will continue anyway. */
            NOTICE("waitpid failed rc=%d: %s\n", wp_ret, strerror(errno));
        }

        if (WIFEXITED(status)) {
            ret = WEXITSTATUS(status);
        } else {
            ret = -1;
        }
    } else if (pid == 0) {
        /* child, call fs_mgr_mount_all() */
        klog_set_level(6);  /* So we can see what fs_mgr_mount_all() does */
        fstab = fs_mgr_read_fstab(args[1]);
        child_ret = fs_mgr_mount_all(fstab);
        fs_mgr_free_fstab(fstab);
        if (child_ret == -1) {
            ERROR("fs_mgr_mount_all returned an error\n");
        }
        _exit(child_ret);
    } else {
        /* fork failed, return an error */
        return -1;
    }

    if (ret == FS_MGR_MNTALL_DEV_NEEDS_ENCRYPTION) {
        property_set("vold.decrypt", "trigger_encryption");
    } else if (ret == FS_MGR_MNTALL_DEV_MIGHT_BE_ENCRYPTED) {
        property_set("ro.crypto.state", "encrypted");
        property_set("ro.crypto.type", "block");
        property_set("vold.decrypt", "trigger_default_encryption");
    } else if (ret == FS_MGR_MNTALL_DEV_NOT_ENCRYPTED) {
        property_set("ro.crypto.state", "unencrypted");
        /* If fs_mgr determined this is an unencrypted device and we are
         * not booting into ffbm(fast factory boot mode),then trigger
	 * that action.
         */
        property_get("ro.bootmode", boot_mode);
        if (strncmp(boot_mode, "ffbm", 4))
            action_for_each_trigger("nonencrypted", action_add_queue_tail);
    } else if (ret == FS_MGR_MNTALL_DEV_NEEDS_RECOVERY) {
        /* Setup a wipe via recovery, and reboot into recovery */
        ERROR("fs_mgr_mount_all suggested recovery, so wiping data via recovery.\n");
        ret = wipe_data_via_recovery();
        /* If reboot worked, there is no return. */
    } else if (ret == FS_MGR_MNTALL_DEV_DEFAULT_FILE_ENCRYPTED) {
        if (e4crypt_install_keyring()) {
            return -1;
        }
        property_set("ro.crypto.state", "encrypted");
        property_set("ro.crypto.type", "file");

        // Although encrypted, we have device key, so we do not need to
        // do anything different from the nonencrypted case.
        property_get("ro.bootmode", boot_mode);
        if (strncmp(boot_mode, "ffbm", 4))
            action_for_each_trigger("nonencrypted", action_add_queue_tail);
    } else if (ret == FS_MGR_MNTALL_DEV_NON_DEFAULT_FILE_ENCRYPTED) {
        if (e4crypt_install_keyring()) {
            return -1;
        }
        property_set("ro.crypto.state", "encrypted");
        property_set("ro.crypto.type", "file");
        property_set("vold.decrypt", "trigger_restart_min_framework");
    } else if (ret > 0) {
        ERROR("fs_mgr_mount_all returned unexpected error %d\n", ret);
    }
    /* else ... < 0: error */

    return ret;
}
Exemplo n.º 20
0
int main(int argc, char *argv[])
{
    int i;
    int res = 1;
    int cmd = CMD_NONE;
    int stdout_fd;
    char footer_location[256];
    struct fstab *fstab;
    struct fstab_part *p;
    char *argument = NULL;

    klog_init();

    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    mrom_set_log_tag("trampoline_encmnt");
    mrom_set_dir("/mrom_enc/");

    for(i = 1; i < argc; ++i)
    {
        if(!strcmp(argv[i], "-h") || !strcmp(argv[i], "--help"))
        {
            print_help(argv);
            return 0;
        }
        else if(cmd == CMD_NONE)
        {
            if(strcmp(argv[i], "decrypt") == 0)
                cmd = CMD_DECRYPT;
            else if(strcmp(argv[i], "remove") == 0)
                cmd = CMD_REMOVE;
            else if(strcmp(argv[i], "pwtype") == 0)
                cmd = CMD_PWTYPE;
        }
        else if(!argument)
        {
            argument = argv[i];
        }
    }

    if(argc == 1 || cmd == CMD_NONE)
    {
        print_help(argv);
        return 0;
    }

    fstab = fstab_auto_load();
    if(!fstab)
    {
        ERROR("Failed to load fstab!");
        return 1;
    }

    p = fstab_find_first_by_path(fstab, "/data");
    if(!p)
    {
        ERROR("Failed to find /data partition in fstab\n");
        goto exit;
    }

    strcpy(footer_location, "");

    if(p->options != NULL && get_footer_from_opts(footer_location,
            sizeof(footer_location), p->options) < 0)
        goto exit;

    if(p->options2 != NULL && strcmp(footer_location, "") == 0 &&
            get_footer_from_opts(footer_location, sizeof(footer_location),
            p->options2) < 0)
        goto exit;

    INFO("Setting encrypted partition data to %s %s %s\n", p->device, footer_location, p->type);
    set_partition_data(p->device, footer_location, p->type);

    // cryptfs prints informations, we don't want that
    stdout_fd = dup(1);
    freopen("/dev/null", "ae", stdout);

    switch(cmd)
    {
        case CMD_PWTYPE:
            if(handle_pwtype(stdout_fd) < 0)
                goto exit;
            break;
        case CMD_DECRYPT:
            if(handle_decrypt(stdout_fd, argument) < 0)
                goto exit;
            break;
        case CMD_REMOVE:
            if(handle_remove() < 0)
                goto exit;
            break;
    }

    res = 0;
exit:
    fstab_destroy(fstab);
    return res;
}
Exemplo n.º 21
0
int main(int argc, const char *argv[])
{
    int i;
    const char *rom_to_boot = NULL;

    for(i = 1; i < argc; ++i)
    {
        if(strcmp(argv[i], "-v") == 0)
        {
            printf("%d%s\n", VERSION_MULTIROM, VERSION_DEV_FIX);
            fflush(stdout);
            return 0;
        }
        else if(strncmp(argv[i], "--boot-rom=", sizeof("--boot-rom")) == 0)
        {
            rom_to_boot = argv[i] + sizeof("--boot-rom");
        }
    }

    srand(time(0));
    klog_init();

    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    mrom_set_log_tag("multirom");

    ERROR("Running MultiROM v%d%s\n", VERSION_MULTIROM, VERSION_DEV_FIX);

    // root is mounted read only in android and MultiROM uses
    // it to store some temp files, so remount it.
    // Yes, there is better solution to this.
    if(rom_to_boot)
        mount(NULL, "/", NULL, MS_REMOUNT, NULL);

    int exit = multirom(rom_to_boot);

    if(rom_to_boot)
        mount(NULL, "/", NULL, MS_RDONLY | MS_REMOUNT, NULL);

    if(exit >= 0)
    {
        if(exit & EXIT_REBOOT_RECOVERY)
            do_reboot(REBOOT_RECOVERY);
        else if(exit & EXIT_REBOOT_BOOTLOADER)
            do_reboot(REBOOT_BOOTLOADER);
        else if(exit & EXIT_SHUTDOWN)
            do_reboot(REBOOT_SHUTDOWN);
        else if(exit & EXIT_REBOOT)
            do_reboot(REBOOT_SYSTEM);

        if(exit & EXIT_KEXEC)
        {
            do_kexec();
            return 0;
        }

        // indicates trampoline to keep /realdata mounted
        if(!(exit & EXIT_UMOUNT))
            close(open(KEEP_REALDATA, O_WRONLY | O_CREAT, 0000));
    }

    vt_set_mode(0);

    return 0;
}
Exemplo n.º 22
0
int main(int argc, char *argv[])
{
    int i, res;
    static char *const cmd[] = { "/init", NULL };
    struct fstab *fstab = NULL;
    char *inject_path = NULL;
    char *mrom_dir = NULL;
    int force_inject = 0;

    for(i = 1; i < argc; ++i)
    {
        if(strcmp(argv[i], "-v") == 0)
        {
            printf("%d\n", VERSION_TRAMPOLINE);
            fflush(stdout);
            return 0;
        }
        else if(strstartswith(argv[i], "--inject="))
            inject_path = argv[i] + strlen("--inject=");
        else if(strstartswith(argv[i], "--mrom_dir="))
            mrom_dir = argv[i] + strlen("--mrom_dir=");
        else if(strcmp(argv[i], "-f") == 0)
            force_inject = 1;
    }

    if(inject_path)
    {
        if(!mrom_dir)
        {
            printf("--mrom_dir=[path to multirom's data dir] needs to be specified!\n");
            fflush(stdout);
            return 1;
        }

        mrom_set_dir(mrom_dir);
        mrom_set_log_tag("trampoline_inject");
        return inject_bootimg(inject_path, force_inject);
    }

    umask(000);

    // Init only the little we need, leave the rest for real init
    mkdir("/dev", 0755);
    mkdir("/dev/pts", 0755);
    mkdir("/dev/socket", 0755);
    mkdir("/proc", 0755);
    mkdir("/sys", 0755);

    mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755");
    mount("devpts", "/dev/pts", "devpts", 0, NULL);
    mount("proc", "/proc", "proc", 0, NULL);
    mount("sysfs", "/sys", "sysfs", 0, NULL);
    mount("pstore", "/sys/fs/pstore", "pstore", 0, NULL);

#if MR_USE_DEBUGFS_MOUNT
    // Mount the debugfs kernel sysfs
    mkdir("/sys/kernel/debug", 0755);
    mount("debugfs", "/sys/kernel/debug", "debugfs", 0, NULL);
#endif

    klog_init();
    // output all messages to dmesg,
    // but it is possible to filter out INFO messages
    klog_set_level(6);

    mrom_set_log_tag("trampoline");
    INFO("Running trampoline v%d\n", VERSION_TRAMPOLINE);

    if(is_charger_mode())
    {
        INFO("Charger mode detected, skipping multirom\n");
        goto run_main_init;
    }

#if MR_DEVICE_HOOKS >= 3
    tramp_hook_before_device_init();
#endif

    INFO("Initializing devices...\n");
    devices_init();
    INFO("Done initializing\n");

    if(wait_for_file("/dev/graphics/fb0", 5) < 0)
    {
        ERROR("Waiting too long for fb0");
        goto exit;
    }

#ifdef MR_POPULATE_BY_NAME_PATH
    //nkk71 M7 hack
    Populate_ByName_using_emmc();
#endif

    fstab = fstab_auto_load();
    if(!fstab)
        goto exit;

#if 0
    fstab_dump(fstab); //debug
#endif

    // mount and run multirom from sdcard
    if(mount_and_run(fstab) < 0 && mrom_is_second_boot())
    {
        ERROR("This is second boot and we couldn't mount /data, reboot!\n");
        sync();
        android_reboot(ANDROID_RB_RESTART, 0, 0);
        while(1)
            sleep(1);
    }

exit:
    if(fstab)
        fstab_destroy(fstab);

    // close and destroy everything
    devices_close();

run_main_init:
    umount("/dev/pts");
    rmdir("/dev/pts");
    rmdir("/dev/socket");

    if(access(KEEP_REALDATA, F_OK) < 0)
    {
        umount(REALDATA);
        umount("/dev");
        rmdir(REALDATA);
        encryption_destroy();
    }

    encryption_cleanup();

#if MR_USE_DEBUGFS_MOUNT
    umount("/sys/kernel/debug");
#endif

    umount("/proc");
    umount("/sys/fs/pstore");
    umount("/sys");

    INFO("Running main_init\n");

    fixup_symlinks();

    chmod("/main_init", EXEC_MASK);
    rename("/main_init", "/init");

    res = execve(cmd[0], cmd, NULL);
    ERROR("execve returned %d %d %s\n", res, errno, strerror(errno));
    return 0;
}
Exemplo n.º 23
0
int ueventd_main(int argc, char **argv)
{
    struct pollfd ufd;
    int nr;
    char tmp[32];

    /*
     * init sets the umask to 077 for forked processes. We need to
     * create files with exact permissions, without modification by
     * the umask.
     */
    umask(000);

    /* Prevent fire-and-forget children from becoming zombies.
     * If we should need to wait() for some children in the future
     * (as opposed to none right now), double-forking here instead
     * of ignoring SIGCHLD may be the better solution.
     */
    signal(SIGCHLD, SIG_IGN);

    open_devnull_stdio();
    klog_init();
#if LOG_UEVENTS
    /* Ensure we're at a logging level that will show the events */
    if (klog_get_level() < KLOG_INFO_LEVEL) {
        klog_set_level(KLOG_INFO_LEVEL);
    }
#endif

    union selinux_callback cb;
    cb.func_log = log_callback;
    selinux_set_callback(SELINUX_CB_LOG, cb);

    INFO("starting ueventd\n");

    /* Respect hardware passed in through the kernel cmd line. Here we will look
     * for androidboot.hardware param in kernel cmdline, and save its value in
     * hardware[]. */
    import_kernel_cmdline(0, import_kernel_nv);

    get_hardware_name(hardware, &revision);

    ueventd_parse_config_file("/ueventd.rc");

    snprintf(tmp, sizeof(tmp), "/ueventd.%s.rc", hardware);
    ueventd_parse_config_file(tmp);

    device_init();

    ufd.events = POLLIN;
    ufd.fd = get_device_fd();

    while(1) {
        ufd.revents = 0;
        nr = poll(&ufd, 1, -1);
        if (nr <= 0)
            continue;
        if (ufd.revents & POLLIN)
               handle_device_fd();
    }
}