diff options
Diffstat (limited to 'fastboot')
-rw-r--r-- | fastboot/Android.mk | 2 | ||||
-rw-r--r-- | fastboot/engine.c | 40 | ||||
-rw-r--r-- | fastboot/fastboot.c | 75 | ||||
-rw-r--r-- | fastboot/fastboot.h | 9 | ||||
-rw-r--r-- | fastboot/usb_osx.c | 6 |
5 files changed, 95 insertions, 37 deletions
diff --git a/fastboot/Android.mk b/fastboot/Android.mk index 34380ec..3c5538f 100644 --- a/fastboot/Android.mk +++ b/fastboot/Android.mk @@ -50,7 +50,7 @@ endif LOCAL_STATIC_LIBRARIES := $(EXTRA_STATIC_LIBS) libzipfile libunz include $(BUILD_HOST_EXECUTABLE) -$(call dist-for-goals,droid,$(LOCAL_BUILT_MODULE)) +$(call dist-for-goals,dist_files,$(LOCAL_BUILT_MODULE)) ifeq ($(HOST_OS),linux) include $(CLEAR_VARS) diff --git a/fastboot/engine.c b/fastboot/engine.c index 48073ee..6d94035 100644 --- a/fastboot/engine.c +++ b/fastboot/engine.c @@ -69,6 +69,7 @@ struct Action Action *next; char cmd[64]; + const char *prod; void *data; unsigned size; @@ -183,6 +184,16 @@ static int cb_check(Action *a, int status, char *resp, int invert) return status; } + if (a->prod) { + if (strcmp(a->prod, cur_product) != 0) { + double split = now(); + fprintf(stderr,"IGNORE, product is %s required only for %s [%7.3fs]\n", + cur_product, a->prod, (split - a->start)); + a->start = split; + return 0; + } + } + yes = match(resp, value, count); if (invert) yes = !yes; @@ -214,10 +225,12 @@ static int cb_reject(Action *a, int status, char *resp) return cb_check(a, status, resp, 1); } -void fb_queue_require(const char *var, int invert, unsigned nvalues, const char **value) +void fb_queue_require(const char *prod, const char *var, + int invert, unsigned nvalues, const char **value) { Action *a; a = queue_action(OP_QUERY, "getvar:%s", var); + a->prod = prod; a->data = value; a->size = nvalues; a->msg = mkmsg("checking %s", var); @@ -244,6 +257,25 @@ void fb_queue_display(const char *var, const char *prettyname) a->func = cb_display; } +static int cb_save(Action *a, int status, char *resp) +{ + if (status) { + fprintf(stderr, "%s FAILED (%s)\n", a->cmd, resp); + return status; + } + strncpy(a->data, resp, a->size); + return 0; +} + +void fb_queue_query_save(const char *var, char *dest, unsigned dest_size) +{ + Action *a; + a = queue_action(OP_QUERY, "getvar:%s", var); + a->data = (void *)dest; + a->size = dest_size; + a->func = cb_save; +} + static int cb_do_nothing(Action *a, int status, char *resp) { fprintf(stderr,"\n"); @@ -277,11 +309,11 @@ void fb_queue_notice(const char *notice) a->data = (void*) notice; } -void fb_execute_queue(usb_handle *usb) +int fb_execute_queue(usb_handle *usb) { Action *a; char resp[FB_RESPONSE_SZ+1]; - int status; + int status = 0; a = action_list; resp[FB_RESPONSE_SZ] = 0; @@ -314,5 +346,5 @@ void fb_execute_queue(usb_handle *usb) } fprintf(stderr,"finished. total time: %.3fs\n", (now() - start)); + return status; } - diff --git a/fastboot/fastboot.c b/fastboot/fastboot.c index 14048a1..4a2de20 100644 --- a/fastboot/fastboot.c +++ b/fastboot/fastboot.c @@ -9,7 +9,7 @@ * notice, this list of conditions and the following disclaimer. * * Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in - * the documentation and/or other materials provided with the + * the documentation and/or other materials provided with the * distribution. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS @@ -19,7 +19,7 @@ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS - * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF @@ -42,6 +42,8 @@ #include "fastboot.h" +char cur_product[FB_RESPONSE_SZ + 1]; + void bootimg_set_cmdline(boot_img_hdr *h, const char *cmdline); boot_img_hdr *mkbootimg(void *kernel, unsigned kernel_size, @@ -68,7 +70,7 @@ void die(const char *fmt, ...) fprintf(stderr,"\n"); va_end(ap); exit(1); -} +} void get_my_path(char *path); @@ -99,13 +101,13 @@ char *find_item(const char *item, const char *product) "../../../target/product/%s/%s", product, fn); return strdup(path); } - + dir = getenv("ANDROID_PRODUCT_OUT"); if((dir == 0) || (dir[0] == 0)) { die("neither -p product specified nor ANDROID_PRODUCT_OUT set"); return 0; } - + sprintf(path, "%s/%s", dir, fn); return strdup(path); } @@ -189,12 +191,12 @@ usb_handle *open_device(void) int announce = 1; if(usb) return usb; - + for(;;) { usb = usb_open(match_fastboot); if(usb) return usb; if(announce) { - announce = 0; + announce = 0; fprintf(stderr,"< waiting for device >\n"); } sleep(1); @@ -226,6 +228,7 @@ void usage(void) " continue continue with autoboot\n" " reboot reboot device normally\n" " reboot-bootloader reboot device into bootloader\n" + " help show this help message\n" "\n" "options:\n" " -w erase userdata and cache\n" @@ -236,7 +239,6 @@ void usage(void) " -b <base_addr> specify a custom kernel base address\n" " -n <page size> specify the nand page size. default: 2048\n" ); - exit(1); } void *load_bootable_image(unsigned page_size, const char *kernel, const char *ramdisk, @@ -257,16 +259,16 @@ void *load_bootable_image(unsigned page_size, const char *kernel, const char *ra fprintf(stderr, "cannot load '%s'\n", kernel); return 0; } - + /* is this actually a boot image? */ if(!memcmp(kdata, BOOT_MAGIC, BOOT_MAGIC_SIZE)) { if(cmdline) bootimg_set_cmdline((boot_img_hdr*) kdata, cmdline); - + if(ramdisk) { fprintf(stderr, "cannot boot a boot.img *and* ramdisk\n"); return 0; } - + *sz = ksize; return kdata; } @@ -288,7 +290,7 @@ void *load_bootable_image(unsigned page_size, const char *kernel, const char *ra if(cmdline) bootimg_set_cmdline((boot_img_hdr*) bdata, cmdline); fprintf(stderr,"creating boot image - %d bytes\n", bsize); *sz = bsize; - + return bdata; } @@ -297,7 +299,7 @@ void *unzip_file(zipfile_t zip, const char *name, unsigned *sz) void *data; zipentry_t entry; unsigned datasz; - + entry = lookup_zipentry(zip, name); if (entry == NULL) { fprintf(stderr, "archive does not contain '%s'\n", name); @@ -340,16 +342,25 @@ static int setup_requirement_line(char *name) { char *val[MAX_OPTIONS]; const char **out; + char *prod = NULL; unsigned n, count; char *x; int invert = 0; - + if (!strncmp(name, "reject ", 7)) { name += 7; invert = 1; } else if (!strncmp(name, "require ", 8)) { name += 8; invert = 0; + } else if (!strncmp(name, "require-for-product:", 20)) { + // Get the product and point name past it + prod = name + 20; + name = strchr(name, ' '); + if (!name) return -1; + *name = 0; + name += 1; + invert = 0; } x = strchr(name, '='); @@ -363,10 +374,10 @@ static int setup_requirement_line(char *name) *x = 0; val[count] = x + 1; } - + name = strip(name); for(n = 0; n < count; n++) val[n] = strip(val[n]); - + name = strip(name); if (name == 0) return -1; @@ -381,7 +392,7 @@ static int setup_requirement_line(char *name) if (out[n] == 0) return -1; } - fb_queue_require(name, invert, n, out); + fb_queue_require(prod, name, invert, n, out); return 0; } @@ -432,6 +443,8 @@ void do_update(char *fn) queue_info_dump(); + fb_queue_query_save("product", cur_product, sizeof(cur_product)); + zdata = load_file(fn, &zsize); if (zdata == 0) die("failed to load '%s'", fn); @@ -477,11 +490,11 @@ void do_send_signature(char *fn) void *data; unsigned sz; char *xtn; - + xtn = strrchr(fn, '.'); if (!xtn) return; if (strcmp(xtn, ".img")) return; - + strcpy(xtn,".sig"); data = load_file(fn, &sz); strcpy(xtn,".img"); @@ -498,6 +511,8 @@ void do_flashall(void) queue_info_dump(); + fb_queue_query_save("product", cur_product, sizeof(cur_product)); + fname = find_item("info", product); if (fname == 0) die("cannot find android-info.txt"); data = load_file(fname, &sz); @@ -521,18 +536,18 @@ void do_flashall(void) data = load_file(fname, &sz); if (data == 0) die("could not load system.img"); do_send_signature(fname); - fb_queue_flash("system", data, sz); + fb_queue_flash("system", data, sz); } #define skip(n) do { argc -= (n); argv += (n); } while (0) -#define require(n) do { if (argc < (n)) usage(); } while (0) +#define require(n) do { if (argc < (n)) {usage(); exit(1);}} while (0) int do_oem_command(int argc, char **argv) { int i; char command[256]; if (argc <= 1) return 0; - + command[0] = 0; while(1) { strcat(command,*argv); @@ -541,7 +556,7 @@ int do_oem_command(int argc, char **argv) strcat(command," "); } - fb_queue_command(command,""); + fb_queue_command(command,""); return 0; } @@ -553,11 +568,12 @@ int main(int argc, char **argv) void *data; unsigned sz; unsigned page_size = 2048; + int status; skip(1); if (argc == 0) { usage(); - return 0; + return 1; } if (!strcmp(*argv, "devices")) { @@ -565,6 +581,12 @@ int main(int argc, char **argv) return 0; } + if (!strcmp(*argv, "help")) { + usage(); + return 0; + } + + serial = getenv("ANDROID_SERIAL"); while (argc > 0) { @@ -689,6 +711,7 @@ int main(int argc, char **argv) argc = do_oem_command(argc, argv); } else { usage(); + return 1; } } @@ -704,6 +727,6 @@ int main(int argc, char **argv) usb = open_device(); - fb_execute_queue(usb); - return 0; + status = fb_execute_queue(usb); + return (status) ? 1 : 0; } diff --git a/fastboot/fastboot.h b/fastboot/fastboot.h index a36c569..9e043fe 100644 --- a/fastboot/fastboot.h +++ b/fastboot/fastboot.h @@ -43,15 +43,20 @@ char *fb_get_error(void); /* engine.c - high level command queue engine */ void fb_queue_flash(const char *ptn, void *data, unsigned sz);; void fb_queue_erase(const char *ptn); -void fb_queue_require(const char *var, int invert, unsigned nvalues, const char **value); +void fb_queue_require(const char *prod, const char *var, int invert, + unsigned nvalues, const char **value); void fb_queue_display(const char *var, const char *prettyname); +void fb_queue_query_save(const char *var, char *dest, unsigned dest_size); void fb_queue_reboot(void); void fb_queue_command(const char *cmd, const char *msg); void fb_queue_download(const char *name, void *data, unsigned size); void fb_queue_notice(const char *notice); -void fb_execute_queue(usb_handle *usb); +int fb_execute_queue(usb_handle *usb); /* util stuff */ void die(const char *fmt, ...); +/* Current product */ +extern char cur_product[FB_RESPONSE_SZ + 1]; + #endif diff --git a/fastboot/usb_osx.c b/fastboot/usb_osx.c index 9488687..570a456 100644 --- a/fastboot/usb_osx.c +++ b/fastboot/usb_osx.c @@ -231,8 +231,7 @@ static int try_interfaces(IOUSBDeviceInterface182 **dev, usb_handle *handle) { kr = (*interface)->ClearPipeStallBothEnds(interface, handle->bulkIn); if (kr != 0) { - ERR("could not clear input pipe; result %d", kr); - return -1; + ERR("could not clear input pipe; result %x, ignoring...\n", kr); } } @@ -240,8 +239,7 @@ static int try_interfaces(IOUSBDeviceInterface182 **dev, usb_handle *handle) { kr = (*interface)->ClearPipeStallBothEnds(interface, handle->bulkOut); if (kr != 0) { - ERR("could not clear output pipe; result %d", kr); - return -1; + ERR("could not clear output pipe; result %x, ignoring....\n", kr); } } |