diff options
| author | Ken Sumrall <ksumrall@android.com> | 2012-10-03 13:54:01 -0700 | 
|---|---|---|
| committer | Android Git Automerger <android-git-automerger@android.com> | 2012-10-03 13:54:01 -0700 | 
| commit | e17c821e36163695f6d5024a71f8e706bda65fd6 (patch) | |
| tree | 68bb55a4ef05616297b67bd3ab555059bfe0eff8 | |
| parent | 449a7d0d78ceb71e478e77ac4d339272dee78c1b (diff) | |
| parent | 608634a1cb68ca89bb033d476d43b58b2e487cf7 (diff) | |
| download | system_core-e17c821e36163695f6d5024a71f8e706bda65fd6.zip system_core-e17c821e36163695f6d5024a71f8e706bda65fd6.tar.gz system_core-e17c821e36163695f6d5024a71f8e706bda65fd6.tar.bz2 | |
am 608634a1: am 48f3b576: Merge "Update fastboot to wipe ext4 partitions before flashing" into jb-mr1-dev
* commit '608634a1cb68ca89bb033d476d43b58b2e487cf7':
  Update fastboot to wipe ext4 partitions before flashing
| -rw-r--r-- | fastboot/engine.c | 33 | ||||
| -rw-r--r-- | fastboot/fastboot.c | 62 | ||||
| -rw-r--r-- | fastboot/fastboot.h | 3 | 
3 files changed, 90 insertions, 8 deletions
| diff --git a/fastboot/engine.c b/fastboot/engine.c index 8d7b68a..7a55260 100644 --- a/fastboot/engine.c +++ b/fastboot/engine.c @@ -144,6 +144,39 @@ struct generator {      { "ext4", generate_ext4_image, cleanup_image }  }; +/* Return true if this partition is supported by the fastboot format command. + * It is also used to determine if we should first erase a partition before + * flashing it with an ext4 filesystem.  See needs_erase() + * + * Not all devices report the filesystem type, so don't report any errors, + * just return false. + */ +int fb_format_supported(usb_handle *usb, const char *partition) +{ +    char response[FB_RESPONSE_SZ+1]; +    struct generator *generator = NULL; +    int status; +    unsigned int i; + +    status = fb_getvar(usb, response, "partition-type:%s", partition); +    if (status) { +        return 0; +    } + +    for (i = 0; i < ARRAY_SIZE(generators); i++) { +        if (!strncmp(generators[i].fs_type, response, FB_RESPONSE_SZ)) { +            generator = &generators[i]; +            break; +        } +    } + +    if (generator) { +        return 1; +    } + +    return 0; +} +  static int cb_default(Action *a, int status, char *resp)  {      if (status) { diff --git a/fastboot/fastboot.c b/fastboot/fastboot.c index 06a6a13..3de6d7d 100644 --- a/fastboot/fastboot.c +++ b/fastboot/fastboot.c @@ -287,7 +287,10 @@ void usage(void)              "  help                                     show this help message\n"              "\n"              "options:\n" -            "  -w                                       erase userdata and cache\n" +            "  -w                                       erase userdata and cache (and format\n" +            "                                           if supported by partition type)\n" +            "  -u                                       do not first erase partition before\n" +            "                                           formatting\n"              "  -s <specific device>                     specify device serial number\n"              "                                           or path to device port\n"              "  -l                                       with \"devices\", lists device paths\n" @@ -562,6 +565,18 @@ static int64_t get_sparse_limit(struct usb_handle *usb, int64_t size)      return 0;  } +/* Until we get lazy inode table init working in make_ext4fs, we need to + * erase partitions of type ext4 before flashing a filesystem so no stale + * inodes are left lying around.  Otherwise, e2fsck gets very upset. + */ +static int needs_erase(const char *part) +{ +    /* The function fb_format_supported() currently returns the value +     * we want, so just call it. +     */ +     return fb_format_supported(usb, part); +} +  void do_flash(usb_handle *usb, const char *pname, const char *fname)  {      int64_t sz64; @@ -597,7 +612,7 @@ void do_update_signature(zipfile_t zip, char *fn)      fb_queue_command("signature", "installing signature");  } -void do_update(char *fn) +void do_update(char *fn, int erase_first)  {      void *zdata;      unsigned zsize; @@ -635,17 +650,26 @@ void do_update(char *fn)      data = unzip_file(zip, "boot.img", &sz);      if (data == 0) die("update package missing boot.img");      do_update_signature(zip, "boot.sig"); +    if (erase_first && needs_erase("boot")) { +        fb_queue_erase("boot"); +    }      fb_queue_flash("boot", data, sz);      data = unzip_file(zip, "recovery.img", &sz);      if (data != 0) {          do_update_signature(zip, "recovery.sig"); +        if (erase_first && needs_erase("recovery")) { +            fb_queue_erase("recovery"); +        }          fb_queue_flash("recovery", data, sz);      }      data = unzip_file(zip, "system.img", &sz);      if (data == 0) die("update package missing system.img");      do_update_signature(zip, "system.sig"); +    if (erase_first && needs_erase("system")) { +        fb_queue_erase("system"); +    }      fb_queue_flash("system", data, sz);  } @@ -667,7 +691,7 @@ void do_send_signature(char *fn)      fb_queue_command("signature", "installing signature");  } -void do_flashall(void) +void do_flashall(int erase_first)  {      char *fname;      void *data; @@ -687,12 +711,18 @@ void do_flashall(void)      data = load_file(fname, &sz);      if (data == 0) die("could not load boot.img: %s", strerror(errno));      do_send_signature(fname); +    if (erase_first && needs_erase("boot")) { +        fb_queue_erase("boot"); +    }      fb_queue_flash("boot", data, sz);      fname = find_item("recovery", product);      data = load_file(fname, &sz);      if (data != 0) {          do_send_signature(fname); +        if (erase_first && needs_erase("recovery")) { +            fb_queue_erase("recovery"); +        }          fb_queue_flash("recovery", data, sz);      } @@ -700,6 +730,9 @@ void do_flashall(void)      data = load_file(fname, &sz);      if (data == 0) die("could not load system.img: %s", strerror(errno));      do_send_signature(fname); +    if (erase_first && needs_erase("system")) { +        fb_queue_erase("system"); +    }      fb_queue_flash("system", data, sz);  } @@ -770,6 +803,7 @@ int main(int argc, char **argv)      int wants_wipe = 0;      int wants_reboot = 0;      int wants_reboot_bootloader = 0; +    int erase_first = 1;      void *data;      unsigned sz;      unsigned page_size = 2048; @@ -782,7 +816,7 @@ int main(int argc, char **argv)      serial = getenv("ANDROID_SERIAL");      while (1) { -        c = getopt_long(argc, argv, "wb:n:s:S:lp:c:i:m:h", &longopts, NULL); +        c = getopt_long(argc, argv, "wub:n:s:S:lp:c:i:m:h", &longopts, NULL);          if (c < 0) {              break;          } @@ -791,6 +825,9 @@ int main(int argc, char **argv)          case 'w':              wants_wipe = 1;              break; +        case 'u': +            erase_first = 0; +            break;          case 'b':              base_addr = strtoul(optarg, 0, 16);              break; @@ -864,10 +901,18 @@ int main(int argc, char **argv)              skip(2);          } else if(!strcmp(*argv, "erase")) {              require(2); + +            if (fb_format_supported(usb, argv[1])) { +                fprintf(stderr, "******** Did you mean to fastboot format this partition?\n"); +            } +              fb_queue_erase(argv[1]);              skip(2);          } else if(!strcmp(*argv, "format")) {              require(2); +            if (erase_first && needs_erase(argv[1])) { +                fb_queue_erase(argv[1]); +            }              fb_queue_format(argv[1], 0);              skip(2);          } else if(!strcmp(*argv, "signature")) { @@ -915,6 +960,9 @@ int main(int argc, char **argv)                  skip(2);              }              if (fname == 0) die("cannot determine image filename for '%s'", pname); +            if (erase_first && needs_erase(pname)) { +                fb_queue_erase(pname); +            }              do_flash(usb, pname, fname);          } else if(!strcmp(*argv, "flash:raw")) {              char *pname = argv[1]; @@ -932,14 +980,14 @@ int main(int argc, char **argv)              fb_queue_flash(pname, data, sz);          } else if(!strcmp(*argv, "flashall")) {              skip(1); -            do_flashall(); +            do_flashall(erase_first);              wants_reboot = 1;          } else if(!strcmp(*argv, "update")) {              if (argc > 1) { -                do_update(argv[1]); +                do_update(argv[1], erase_first);                  skip(2);              } else { -                do_update("update.zip"); +                do_update("update.zip", erase_first);                  skip(1);              }              wants_reboot = 1; diff --git a/fastboot/fastboot.h b/fastboot/fastboot.h index b4cf195..c1b2964 100644 --- a/fastboot/fastboot.h +++ b/fastboot/fastboot.h @@ -45,7 +45,8 @@ char *fb_get_error(void);  /* engine.c - high level command queue engine */  int fb_getvar(struct usb_handle *usb, char *response, const char *fmt, ...); -void fb_queue_flash(const char *ptn, void *data, unsigned sz);; +int fb_format_supported(usb_handle *usb, const char *partition); +void fb_queue_flash(const char *ptn, void *data, unsigned sz);  void fb_queue_flash_sparse(const char *ptn, struct sparse_file *s, unsigned sz);  void fb_queue_erase(const char *ptn);  void fb_queue_format(const char *ptn, int skip_if_not_supported); | 
