X-Git-Url: http://git.archive.openwrt.org/?p=project%2Ffstools.git;a=blobdiff_plain;f=jffs2reset.c;h=97fd0ab51b5fd9d97a84f6729b6804b35a99da7b;hp=13edf1e2a8ec83c5cf4885310a6ef00839c54b8b;hb=5b61e27d36e5bbf40825a4ae14920efe47d36f02;hpb=142e693368ab09c7d10305fbff1550692d803630 diff --git a/jffs2reset.c b/jffs2reset.c index 13edf1e..97fd0ab 100644 --- a/jffs2reset.c +++ b/jffs2reset.c @@ -14,6 +14,8 @@ #include #include #include +#include +#include #include #include @@ -21,103 +23,59 @@ #include #include #include +#include + #include "libfstools/libfstools.h" #include "libfstools/volume.h" -static int -handle_rmdir(const char *dir) -{ - struct dirent *dt; - struct stat st; - DIR *d; - int fd; - - d = opendir(dir); - if (!d) - return -1; - - fd = dirfd(d); - - while ((dt = readdir(d)) != NULL) { - if (fstatat(fd, dt->d_name, &st, AT_SYMLINK_NOFOLLOW) || S_ISDIR(st.st_mode)) - continue; - - unlinkat(fd, dt->d_name, 0); - } - - closedir(d); - rmdir(dir); - - return 0; -} +static int jffs2_mark(struct volume *v); static int -ask_user(int argc, char **argv) +ask_user(void) { - if ((argc < 2) || strcmp(argv[1], "-y")) { - fprintf(stderr, "This will erase all settings and remove any installed packages. Are you sure? [N/y]\n"); - if (getchar() != 'y') - return -1; - } + ULOG_WARN("This will erase all settings and remove any installed packages. Are you sure? [N/y]\n"); + if (getchar() != 'y') + return -1; return 0; - } -static int -jffs2_reset(int argc, char **argv) +static int jffs2_reset(struct volume *v, int reset) { - struct volume *v; char *mp; - if (ask_user(argc, argv)) - return -1; - - if (find_filesystem("overlay")) { - fprintf(stderr, "overlayfs not found\n"); - return -1; - } - - v = volume_find("rootfs_data"); - if (!v) { - fprintf(stderr, "no rootfs_data was found\n"); - return -1; - } - mp = find_mount_point(v->blk, 1); if (mp) { - fprintf(stderr, "%s is mounted as %s, only erasing files\n", v->blk, mp); - foreachdir(mp, handle_rmdir); + ULOG_INFO("%s is mounted as %s, only erasing files\n", v->blk, mp); + fs_state_set("/overlay", FS_STATE_PENDING); + overlay_delete(mp, false); mount(mp, "/", NULL, MS_REMOUNT, 0); } else { - fprintf(stderr, "%s is not mounted, erasing it\n", v->blk); - volume_erase_all(v); + ULOG_INFO("%s is not mounted\n", v->blk); + return jffs2_mark(v); + } + + if (reset) { + sync(); + sleep(2); + reboot(RB_AUTOBOOT); + while (1) + ; } return 0; } -static int -jffs2_mark(int argc, char **argv) +static int jffs2_mark(struct volume *v) { __u32 deadc0de = __cpu_to_be32(0xdeadc0de); - struct volume *v; size_t sz; int fd; - if (ask_user(argc, argv)) - return -1; - - v = volume_find("rootfs_data"); - if (!v) { - fprintf(stderr, "no rootfs_data was found\n"); - return -1; - } - fd = open(v->blk, O_WRONLY); - fprintf(stderr, "%s - marking with deadc0de\n", v->blk); + ULOG_INFO("%s will be erased on next mount\n", v->blk); if (!fd) { - fprintf(stderr, "opening %s failed\n", v->blk); + ULOG_ERR("opening %s failed\n", v->blk); return -1; } @@ -125,7 +83,7 @@ jffs2_mark(int argc, char **argv) close(fd); if (sz != 4) { - fprintf(stderr, "writing %s failed: %s\n", v->blk, strerror(errno)); + ULOG_ERR("writing %s failed: %s\n", v->blk, strerror(errno)); return -1; } @@ -134,7 +92,40 @@ jffs2_mark(int argc, char **argv) int main(int argc, char **argv) { + struct volume *v; + int ch, yes = 0, reset = 0; + while ((ch = getopt(argc, argv, "yr")) != -1) { + switch(ch) { + case 'y': + yes = 1; + break; + case 'r': + reset = 1; + break; + } + + } + + if (!yes && ask_user()) + return -1; + + /* + * TODO: Currently this only checks if kernel supports OverlayFS. We + * should check if there is a mount point using it with rootfs_data + * as upperdir. + */ + if (find_filesystem("overlay")) { + ULOG_ERR("overlayfs not supported by kernel\n"); + return -1; + } + + v = volume_find("rootfs_data"); + if (!v) { + ULOG_ERR("MTD partition 'rootfs_data' not found\n"); + return -1; + } + if (!strcmp(*argv, "jffs2mark")) - return jffs2_mark(argc, argv); - return jffs2_reset(argc, argv); + return jffs2_mark(v); + return jffs2_reset(v, reset); }