aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorElliott Hughes2015-04-28 19:24:24 -0500
committerElliott Hughes2015-04-29 19:46:43 -0500
commit7bad7c4646ee8fd8d6e6ed0ffd3ddbb0c1b41a2f (patch)
treee2c357667b0e76e6fa5a43c7a7951c872c373e9c
parent8c389e9c769c8632cf16c0794f1e84f49996077c (diff)
downloadplatform-bootable-recovery-7bad7c4646ee8fd8d6e6ed0ffd3ddbb0c1b41a2f.tar.gz
platform-bootable-recovery-7bad7c4646ee8fd8d6e6ed0ffd3ddbb0c1b41a2f.tar.xz
platform-bootable-recovery-7bad7c4646ee8fd8d6e6ed0ffd3ddbb0c1b41a2f.zip
Check all lseek calls succeed.
Also add missing TEMP_FAILURE_RETRYs on read, write, and lseek. Bug: http://b/20625546 Change-Id: I03b198e11c1921b35518ee2dd005a7cfcf4fd94b
-rw-r--r--adb_install.cpp2
-rw-r--r--applypatch/applypatch.c51
-rw-r--r--fuse_sdcard_provider.c16
-rw-r--r--fuse_sideload.c16
-rw-r--r--minui/events.cpp3
-rw-r--r--minzip/SysUtil.c10
-rw-r--r--minzip/Zip.c6
-rw-r--r--mtdutils/flash_image.c8
-rw-r--r--mtdutils/mtdutils.c54
-rw-r--r--mtdutils/mtdutils.h2
-rw-r--r--tools/ota/check-lost+found.c2
-rw-r--r--ui.cpp2
-rw-r--r--uncrypt/uncrypt.c20
-rw-r--r--updater/blockimg.c48
14 files changed, 112 insertions, 128 deletions
diff --git a/adb_install.cpp b/adb_install.cpp
index ebd4cac0..e3b94ea5 100644
--- a/adb_install.cpp
+++ b/adb_install.cpp
@@ -42,7 +42,7 @@ set_usb_driver(bool enabled) {
42 ui->Print("failed to open driver control: %s\n", strerror(errno)); 42 ui->Print("failed to open driver control: %s\n", strerror(errno));
43 return; 43 return;
44 } 44 }
45 if (write(fd, enabled ? "1" : "0", 1) < 0) { 45 if (TEMP_FAILURE_RETRY(write(fd, enabled ? "1" : "0", 1)) == -1) {
46 ui->Print("failed to set driver control: %s\n", strerror(errno)); 46 ui->Print("failed to set driver control: %s\n", strerror(errno));
47 } 47 }
48 if (close(fd) < 0) { 48 if (close(fd) < 0) {
diff --git a/applypatch/applypatch.c b/applypatch/applypatch.c
index 2c86e098..6f02a38e 100644
--- a/applypatch/applypatch.c
+++ b/applypatch/applypatch.c
@@ -422,20 +422,19 @@ int WriteToPartition(unsigned char* data, size_t len,
422 int attempt; 422 int attempt;
423 423
424 for (attempt = 0; attempt < 2; ++attempt) { 424 for (attempt = 0; attempt < 2; ++attempt) {
425 lseek(fd, start, SEEK_SET); 425 if (TEMP_FAILURE_RETRY(lseek(fd, start, SEEK_SET)) == -1) {
426 printf("failed seek on %s: %s\n",
427 partition, strerror(errno));
428 return -1;
429 }
426 while (start < len) { 430 while (start < len) {
427 size_t to_write = len - start; 431 size_t to_write = len - start;
428 if (to_write > 1<<20) to_write = 1<<20; 432 if (to_write > 1<<20) to_write = 1<<20;
429 433
430 ssize_t written = write(fd, data+start, to_write); 434 ssize_t written = TEMP_FAILURE_RETRY(write(fd, data+start, to_write));
431 if (written < 0) { 435 if (written == -1) {
432 if (errno == EINTR) { 436 printf("failed write writing to %s: %s\n", partition, strerror(errno));
433 written = 0; 437 return -1;
434 } else {
435 printf("failed write writing to %s (%s)\n",
436 partition, strerror(errno));
437 return -1;
438 }
439 } 438 }
440 start += written; 439 start += written;
441 } 440 }
@@ -460,13 +459,20 @@ int WriteToPartition(unsigned char* data, size_t len,
460 // won't just be reading the cache. 459 // won't just be reading the cache.
461 sync(); 460 sync();
462 int dc = open("/proc/sys/vm/drop_caches", O_WRONLY); 461 int dc = open("/proc/sys/vm/drop_caches", O_WRONLY);
463 write(dc, "3\n", 2); 462 if (TEMP_FAILURE_RETRY(write(dc, "3\n", 2)) == -1) {
463 printf("write to /proc/sys/vm/drop_caches failed: %s\n", strerror(errno));
464 } else {
465 printf(" caches dropped\n");
466 }
464 close(dc); 467 close(dc);
465 sleep(1); 468 sleep(1);
466 printf(" caches dropped\n");
467 469
468 // verify 470 // verify
469 lseek(fd, 0, SEEK_SET); 471 if (TEMP_FAILURE_RETRY(lseek(fd, 0, SEEK_SET)) == -1) {
472 printf("failed to seek back to beginning of %s: %s\n",
473 partition, strerror(errno));
474 return -1;
475 }
470 unsigned char buffer[4096]; 476 unsigned char buffer[4096];
471 start = len; 477 start = len;
472 size_t p; 478 size_t p;
@@ -476,15 +482,12 @@ int WriteToPartition(unsigned char* data, size_t len,
476 482
477 size_t so_far = 0; 483 size_t so_far = 0;
478 while (so_far < to_read) { 484 while (so_far < to_read) {
479 ssize_t read_count = read(fd, buffer+so_far, to_read-so_far); 485 ssize_t read_count =
480 if (read_count < 0) { 486 TEMP_FAILURE_RETRY(read(fd, buffer+so_far, to_read-so_far));
481 if (errno == EINTR) { 487 if (read_count == -1) {
482 read_count = 0; 488 printf("verify read error %s at %zu: %s\n",
483 } else { 489 partition, p, strerror(errno));
484 printf("verify read error %s at %zu: %s\n", 490 return -1;
485 partition, p, strerror(errno));
486 return -1;
487 }
488 } 491 }
489 if ((size_t)read_count < to_read) { 492 if ((size_t)read_count < to_read) {
490 printf("short verify read %s at %zu: %zd %zu %s\n", 493 printf("short verify read %s at %zu: %zd %zu %s\n",
@@ -625,8 +628,8 @@ ssize_t FileSink(const unsigned char* data, ssize_t len, void* token) {
625 ssize_t done = 0; 628 ssize_t done = 0;
626 ssize_t wrote; 629 ssize_t wrote;
627 while (done < (ssize_t) len) { 630 while (done < (ssize_t) len) {
628 wrote = write(fd, data+done, len-done); 631 wrote = TEMP_FAILURE_RETRY(write(fd, data+done, len-done));
629 if (wrote <= 0) { 632 if (wrote == -1) {
630 printf("error writing %d bytes: %s\n", (int)(len-done), strerror(errno)); 633 printf("error writing %d bytes: %s\n", (int)(len-done), strerror(errno));
631 return done; 634 return done;
632 } 635 }
diff --git a/fuse_sdcard_provider.c b/fuse_sdcard_provider.c
index ca8c914f..4565c7b5 100644
--- a/fuse_sdcard_provider.c
+++ b/fuse_sdcard_provider.c
@@ -36,19 +36,17 @@ struct file_data {
36static int read_block_file(void* cookie, uint32_t block, uint8_t* buffer, uint32_t fetch_size) { 36static int read_block_file(void* cookie, uint32_t block, uint8_t* buffer, uint32_t fetch_size) {
37 struct file_data* fd = (struct file_data*)cookie; 37 struct file_data* fd = (struct file_data*)cookie;
38 38
39 if (lseek(fd->fd, block * fd->block_size, SEEK_SET) < 0) { 39 off64_t offset = ((off64_t) block) * fd->block_size;
40 printf("seek on sdcard failed: %s\n", strerror(errno)); 40 if (TEMP_FAILURE_RETRY(lseek64(fd->fd, offset, SEEK_SET)) == -1) {
41 fprintf(stderr, "seek on sdcard failed: %s\n", strerror(errno));
41 return -EIO; 42 return -EIO;
42 } 43 }
43 44
44 while (fetch_size > 0) { 45 while (fetch_size > 0) {
45 ssize_t r = read(fd->fd, buffer, fetch_size); 46 ssize_t r = TEMP_FAILURE_RETRY(read(fd->fd, buffer, fetch_size));
46 if (r < 0) { 47 if (r == -1) {
47 if (r != -EINTR) { 48 fprintf(stderr, "read on sdcard failed: %s\n", strerror(errno));
48 printf("read on sdcard failed: %s\n", strerror(errno)); 49 return -EIO;
49 return -EIO;
50 }
51 r = 0;
52 } 50 }
53 fetch_size -= r; 51 fetch_size -= r;
54 buffer += r; 52 buffer += r;
diff --git a/fuse_sideload.c b/fuse_sideload.c
index 1dd84e97..48e6cc53 100644
--- a/fuse_sideload.c
+++ b/fuse_sideload.c
@@ -442,14 +442,12 @@ int run_fuse_sideload(struct provider_vtab* vtab, void* cookie,
442 } 442 }
443 uint8_t request_buffer[sizeof(struct fuse_in_header) + PATH_MAX*8]; 443 uint8_t request_buffer[sizeof(struct fuse_in_header) + PATH_MAX*8];
444 for (;;) { 444 for (;;) {
445 ssize_t len = read(fd.ffd, request_buffer, sizeof(request_buffer)); 445 ssize_t len = TEMP_FAILURE_RETRY(read(fd.ffd, request_buffer, sizeof(request_buffer)));
446 if (len < 0) { 446 if (len == -1) {
447 if (errno != EINTR) { 447 perror("read request");
448 perror("read request"); 448 if (errno == ENODEV) {
449 if (errno == ENODEV) { 449 result = -1;
450 result = -1; 450 break;
451 break;
452 }
453 } 451 }
454 continue; 452 continue;
455 } 453 }
@@ -508,7 +506,7 @@ int run_fuse_sideload(struct provider_vtab* vtab, void* cookie,
508 outhdr.len = sizeof(outhdr); 506 outhdr.len = sizeof(outhdr);
509 outhdr.error = result; 507 outhdr.error = result;
510 outhdr.unique = hdr->unique; 508 outhdr.unique = hdr->unique;
511 write(fd.ffd, &outhdr, sizeof(outhdr)); 509 TEMP_FAILURE_RETRY(write(fd.ffd, &outhdr, sizeof(outhdr)));
512 } 510 }
513 } 511 }
514 512
diff --git a/minui/events.cpp b/minui/events.cpp
index 2d47a587..3b2262a4 100644
--- a/minui/events.cpp
+++ b/minui/events.cpp
@@ -15,6 +15,7 @@
15 */ 15 */
16 16
17#include <dirent.h> 17#include <dirent.h>
18#include <errno.h>
18#include <fcntl.h> 19#include <fcntl.h>
19#include <stdio.h> 20#include <stdio.h>
20#include <stdlib.h> 21#include <stdlib.h>
@@ -165,7 +166,7 @@ void ev_dispatch(void) {
165 166
166int ev_get_input(int fd, uint32_t epevents, input_event* ev) { 167int ev_get_input(int fd, uint32_t epevents, input_event* ev) {
167 if (epevents & EPOLLIN) { 168 if (epevents & EPOLLIN) {
168 ssize_t r = read(fd, ev, sizeof(*ev)); 169 ssize_t r = TEMP_FAILURE_RETRY(read(fd, ev, sizeof(*ev)));
169 if (r == sizeof(*ev)) { 170 if (r == sizeof(*ev)) {
170 return 0; 171 return 0;
171 } 172 }
diff --git a/minzip/SysUtil.c b/minzip/SysUtil.c
index ac6f5c33..b160c9e3 100644
--- a/minzip/SysUtil.c
+++ b/minzip/SysUtil.c
@@ -27,11 +27,13 @@ static int getFileStartAndLength(int fd, off_t *start_, size_t *length_)
27 assert(start_ != NULL); 27 assert(start_ != NULL);
28 assert(length_ != NULL); 28 assert(length_ != NULL);
29 29
30 start = lseek(fd, 0L, SEEK_CUR); 30 // TODO: isn't start always 0 for the single call site? just use fstat instead?
31 end = lseek(fd, 0L, SEEK_END);
32 (void) lseek(fd, start, SEEK_SET);
33 31
34 if (start == (off_t) -1 || end == (off_t) -1) { 32 start = TEMP_FAILURE_RETRY(lseek(fd, 0L, SEEK_CUR));
33 end = TEMP_FAILURE_RETRY(lseek(fd, 0L, SEEK_END));
34
35 if (TEMP_FAILURE_RETRY(lseek(fd, start, SEEK_SET)) == -1 ||
36 start == (off_t) -1 || end == (off_t) -1) {
35 LOGE("could not determine length of file\n"); 37 LOGE("could not determine length of file\n");
36 return -1; 38 return -1;
37 } 39 }
diff --git a/minzip/Zip.c b/minzip/Zip.c
index d3ff79be..40712e03 100644
--- a/minzip/Zip.c
+++ b/minzip/Zip.c
@@ -675,13 +675,11 @@ static bool writeProcessFunction(const unsigned char *data, int dataLen,
675 } 675 }
676 ssize_t soFar = 0; 676 ssize_t soFar = 0;
677 while (true) { 677 while (true) {
678 ssize_t n = write(fd, data+soFar, dataLen-soFar); 678 ssize_t n = TEMP_FAILURE_RETRY(write(fd, data+soFar, dataLen-soFar));
679 if (n <= 0) { 679 if (n <= 0) {
680 LOGE("Error writing %zd bytes from zip file from %p: %s\n", 680 LOGE("Error writing %zd bytes from zip file from %p: %s\n",
681 dataLen-soFar, data+soFar, strerror(errno)); 681 dataLen-soFar, data+soFar, strerror(errno));
682 if (errno != EINTR) { 682 return false;
683 return false;
684 }
685 } else if (n > 0) { 683 } else if (n > 0) {
686 soFar += n; 684 soFar += n;
687 if (soFar == dataLen) return true; 685 if (soFar == dataLen) return true;
diff --git a/mtdutils/flash_image.c b/mtdutils/flash_image.c
index 5657dfc8..36ffa131 100644
--- a/mtdutils/flash_image.c
+++ b/mtdutils/flash_image.c
@@ -72,7 +72,7 @@ int main(int argc, char **argv) {
72 if (fd < 0) die("error opening %s", argv[2]); 72 if (fd < 0) die("error opening %s", argv[2]);
73 73
74 char header[HEADER_SIZE]; 74 char header[HEADER_SIZE];
75 int headerlen = read(fd, header, sizeof(header)); 75 int headerlen = TEMP_FAILURE_RETRY(read(fd, header, sizeof(header)));
76 if (headerlen <= 0) die("error reading %s header", argv[2]); 76 if (headerlen <= 0) die("error reading %s header", argv[2]);
77 77
78 MtdReadContext *in = mtd_read_partition(partition); 78 MtdReadContext *in = mtd_read_partition(partition);
@@ -104,7 +104,7 @@ int main(int argc, char **argv) {
104 if (wrote != headerlen) die("error writing %s", argv[1]); 104 if (wrote != headerlen) die("error writing %s", argv[1]);
105 105
106 int len; 106 int len;
107 while ((len = read(fd, buf, sizeof(buf))) > 0) { 107 while ((len = TEMP_FAILURE_RETRY(read(fd, buf, sizeof(buf)))) > 0) {
108 wrote = mtd_write_data(out, buf, len); 108 wrote = mtd_write_data(out, buf, len);
109 if (wrote != len) die("error writing %s", argv[1]); 109 if (wrote != len) die("error writing %s", argv[1]);
110 } 110 }
@@ -125,13 +125,13 @@ int main(int argc, char **argv) {
125 if (mtd_partition_info(partition, NULL, &block_size, NULL)) 125 if (mtd_partition_info(partition, NULL, &block_size, NULL))
126 die("error getting %s block size", argv[1]); 126 die("error getting %s block size", argv[1]);
127 127
128 if (lseek(fd, headerlen, SEEK_SET) != headerlen) 128 if (TEMP_FAILURE_RETRY(lseek(fd, headerlen, SEEK_SET)) != headerlen)
129 die("error rewinding %s", argv[2]); 129 die("error rewinding %s", argv[2]);
130 130
131 int left = block_size - headerlen; 131 int left = block_size - headerlen;
132 while (left < 0) left += block_size; 132 while (left < 0) left += block_size;
133 while (left > 0) { 133 while (left > 0) {
134 len = read(fd, buf, left > (int)sizeof(buf) ? (int)sizeof(buf) : left); 134 len = TEMP_FAILURE_RETRY(read(fd, buf, left > (int)sizeof(buf) ? (int)sizeof(buf) : left));
135 if (len <= 0) die("error reading %s", argv[2]); 135 if (len <= 0) die("error reading %s", argv[2]);
136 if (mtd_write_data(out, buf, len) != len) 136 if (mtd_write_data(out, buf, len) != len)
137 die("error writing %s", argv[1]); 137 die("error writing %s", argv[1]);
diff --git a/mtdutils/mtdutils.c b/mtdutils/mtdutils.c
index 9a17e38d..cc303344 100644
--- a/mtdutils/mtdutils.c
+++ b/mtdutils/mtdutils.c
@@ -108,7 +108,7 @@ mtd_scan_partitions()
108 if (fd < 0) { 108 if (fd < 0) {
109 goto bail; 109 goto bail;
110 } 110 }
111 nbytes = read(fd, buf, sizeof(buf) - 1); 111 nbytes = TEMP_FAILURE_RETRY(read(fd, buf, sizeof(buf) - 1));
112 close(fd); 112 close(fd);
113 if (nbytes < 0) { 113 if (nbytes < 0) {
114 goto bail; 114 goto bail;
@@ -279,12 +279,6 @@ MtdReadContext *mtd_read_partition(const MtdPartition *partition)
279 return ctx; 279 return ctx;
280} 280}
281 281
282// Seeks to a location in the partition. Don't mix with reads of
283// anything other than whole blocks; unpredictable things will result.
284void mtd_read_skip_to(const MtdReadContext* ctx, size_t offset) {
285 lseek64(ctx->fd, offset, SEEK_SET);
286}
287
288static int read_block(const MtdPartition *partition, int fd, char *data) 282static int read_block(const MtdPartition *partition, int fd, char *data)
289{ 283{
290 struct mtd_ecc_stats before, after; 284 struct mtd_ecc_stats before, after;
@@ -293,13 +287,18 @@ static int read_block(const MtdPartition *partition, int fd, char *data)
293 return -1; 287 return -1;
294 } 288 }
295 289
296 loff_t pos = lseek64(fd, 0, SEEK_CUR); 290 loff_t pos = TEMP_FAILURE_RETRY(lseek64(fd, 0, SEEK_CUR));
291 if (pos == -1) {
292 printf("mtd: read_block: couldn't SEEK_CUR: %s\n", strerror(errno));
293 return -1;
294 }
297 295
298 ssize_t size = partition->erase_size; 296 ssize_t size = partition->erase_size;
299 int mgbb; 297 int mgbb;
300 298
301 while (pos + size <= (int) partition->size) { 299 while (pos + size <= (int) partition->size) {
302 if (lseek64(fd, pos, SEEK_SET) != pos || read(fd, data, size) != size) { 300 if (TEMP_FAILURE_RETRY(lseek64(fd, pos, SEEK_SET)) != pos ||
301 TEMP_FAILURE_RETRY(read(fd, data, size)) != size) {
303 printf("mtd: read error at 0x%08llx (%s)\n", 302 printf("mtd: read error at 0x%08llx (%s)\n",
304 pos, strerror(errno)); 303 pos, strerror(errno));
305 } else if (ioctl(fd, ECCGETSTATS, &after)) { 304 } else if (ioctl(fd, ECCGETSTATS, &after)) {
@@ -409,8 +408,11 @@ static int write_block(MtdWriteContext *ctx, const char *data)
409 const MtdPartition *partition = ctx->partition; 408 const MtdPartition *partition = ctx->partition;
410 int fd = ctx->fd; 409 int fd = ctx->fd;
411 410
412 off_t pos = lseek(fd, 0, SEEK_CUR); 411 off_t pos = TEMP_FAILURE_RETRY(lseek(fd, 0, SEEK_CUR));
413 if (pos == (off_t) -1) return 1; 412 if (pos == (off_t) -1) {
413 printf("mtd: write_block: couldn't SEEK_CUR: %s\n", strerror(errno));
414 return -1;
415 }
414 416
415 ssize_t size = partition->erase_size; 417 ssize_t size = partition->erase_size;
416 while (pos + size <= (int) partition->size) { 418 while (pos + size <= (int) partition->size) {
@@ -435,15 +437,15 @@ static int write_block(MtdWriteContext *ctx, const char *data)
435 pos, strerror(errno)); 437 pos, strerror(errno));
436 continue; 438 continue;
437 } 439 }
438 if (lseek(fd, pos, SEEK_SET) != pos || 440 if (TEMP_FAILURE_RETRY(lseek(fd, pos, SEEK_SET)) != pos ||
439 write(fd, data, size) != size) { 441 TEMP_FAILURE_RETRY(write(fd, data, size)) != size) {
440 printf("mtd: write error at 0x%08lx (%s)\n", 442 printf("mtd: write error at 0x%08lx (%s)\n",
441 pos, strerror(errno)); 443 pos, strerror(errno));
442 } 444 }
443 445
444 char verify[size]; 446 char verify[size];
445 if (lseek(fd, pos, SEEK_SET) != pos || 447 if (TEMP_FAILURE_RETRY(lseek(fd, pos, SEEK_SET)) != pos ||
446 read(fd, verify, size) != size) { 448 TEMP_FAILURE_RETRY(read(fd, verify, size)) != size) {
447 printf("mtd: re-read error at 0x%08lx (%s)\n", 449 printf("mtd: re-read error at 0x%08lx (%s)\n",
448 pos, strerror(errno)); 450 pos, strerror(errno));
449 continue; 451 continue;
@@ -512,8 +514,11 @@ off_t mtd_erase_blocks(MtdWriteContext *ctx, int blocks)
512 ctx->stored = 0; 514 ctx->stored = 0;
513 } 515 }
514 516
515 off_t pos = lseek(ctx->fd, 0, SEEK_CUR); 517 off_t pos = TEMP_FAILURE_RETRY(lseek(ctx->fd, 0, SEEK_CUR));
516 if ((off_t) pos == (off_t) -1) return pos; 518 if ((off_t) pos == (off_t) -1) {
519 printf("mtd_erase_blocks: couldn't SEEK_CUR: %s\n", strerror(errno));
520 return -1;
521 }
517 522
518 const int total = (ctx->partition->size - pos) / ctx->partition->erase_size; 523 const int total = (ctx->partition->size - pos) / ctx->partition->erase_size;
519 if (blocks < 0) blocks = total; 524 if (blocks < 0) blocks = total;
@@ -554,18 +559,3 @@ int mtd_write_close(MtdWriteContext *ctx)
554 free(ctx); 559 free(ctx);
555 return r; 560 return r;
556} 561}
557
558/* Return the offset of the first good block at or after pos (which
559 * might be pos itself).
560 */
561off_t mtd_find_write_start(MtdWriteContext *ctx, off_t pos) {
562 int i;
563 for (i = 0; i < ctx->bad_block_count; ++i) {
564 if (ctx->bad_block_offsets[i] == pos) {
565 pos += ctx->partition->erase_size;
566 } else if (ctx->bad_block_offsets[i] > pos) {
567 return pos;
568 }
569 }
570 return pos;
571}
diff --git a/mtdutils/mtdutils.h b/mtdutils/mtdutils.h
index 2708c431..8059d6a4 100644
--- a/mtdutils/mtdutils.h
+++ b/mtdutils/mtdutils.h
@@ -49,12 +49,10 @@ typedef struct MtdWriteContext MtdWriteContext;
49MtdReadContext *mtd_read_partition(const MtdPartition *); 49MtdReadContext *mtd_read_partition(const MtdPartition *);
50ssize_t mtd_read_data(MtdReadContext *, char *data, size_t data_len); 50ssize_t mtd_read_data(MtdReadContext *, char *data, size_t data_len);
51void mtd_read_close(MtdReadContext *); 51void mtd_read_close(MtdReadContext *);
52void mtd_read_skip_to(const MtdReadContext *, size_t offset);
53 52
54MtdWriteContext *mtd_write_partition(const MtdPartition *); 53MtdWriteContext *mtd_write_partition(const MtdPartition *);
55ssize_t mtd_write_data(MtdWriteContext *, const char *data, size_t data_len); 54ssize_t mtd_write_data(MtdWriteContext *, const char *data, size_t data_len);
56off_t mtd_erase_blocks(MtdWriteContext *, int blocks); /* 0 ok, -1 for all */ 55off_t mtd_erase_blocks(MtdWriteContext *, int blocks); /* 0 ok, -1 for all */
57off_t mtd_find_write_start(MtdWriteContext *ctx, off_t pos);
58int mtd_write_close(MtdWriteContext *); 56int mtd_write_close(MtdWriteContext *);
59 57
60#ifdef __cplusplus 58#ifdef __cplusplus
diff --git a/tools/ota/check-lost+found.c b/tools/ota/check-lost+found.c
index cbf79262..8ce12d39 100644
--- a/tools/ota/check-lost+found.c
+++ b/tools/ota/check-lost+found.c
@@ -78,7 +78,7 @@ int main(int argc __attribute__((unused)), char **argv __attribute__((unused)))
78 snprintf(fn, sizeof(fn), "%s/%s", kPartitions[i], "dirty"); 78 snprintf(fn, sizeof(fn), "%s/%s", kPartitions[i], "dirty");
79 fd = open(fn, O_WRONLY|O_CREAT, 0444); 79 fd = open(fn, O_WRONLY|O_CREAT, 0444);
80 if (fd >= 0) { // Don't sweat it if we can't write the file. 80 if (fd >= 0) { // Don't sweat it if we can't write the file.
81 write(fd, fn, sizeof(fn)); // write, you know, some data 81 TEMP_FAILURE_RETRY(write(fd, fn, sizeof(fn))); // write, you know, some data
82 close(fd); 82 close(fd);
83 unlink(fn); 83 unlink(fn);
84 } 84 }
diff --git a/ui.cpp b/ui.cpp
index dca325fe..1a0b079c 100644
--- a/ui.cpp
+++ b/ui.cpp
@@ -251,7 +251,7 @@ bool RecoveryUI::IsUsbConnected() {
251 251
252 char buf; 252 char buf;
253 // USB is connected if android_usb state is CONNECTED or CONFIGURED. 253 // USB is connected if android_usb state is CONNECTED or CONFIGURED.
254 int connected = (read(fd, &buf, 1) == 1) && (buf == 'C'); 254 int connected = (TEMP_FAILURE_RETRY(read(fd, &buf, 1)) == 1) && (buf == 'C');
255 if (close(fd) < 0) { 255 if (close(fd) < 0) {
256 printf("failed to close /sys/class/android_usb/android0/state: %s\n", 256 printf("failed to close /sys/class/android_usb/android0/state: %s\n",
257 strerror(errno)); 257 strerror(errno));
diff --git a/uncrypt/uncrypt.c b/uncrypt/uncrypt.c
index aa75210b..da035dfb 100644
--- a/uncrypt/uncrypt.c
+++ b/uncrypt/uncrypt.c
@@ -65,12 +65,15 @@ static struct fstab* fstab = NULL;
65static int write_at_offset(unsigned char* buffer, size_t size, 65static int write_at_offset(unsigned char* buffer, size_t size,
66 int wfd, off64_t offset) 66 int wfd, off64_t offset)
67{ 67{
68 lseek64(wfd, offset, SEEK_SET); 68 if (TEMP_FAILURE_RETRY(lseek64(wfd, offset, SEEK_SET)) == -1) {
69 ALOGE("error seeking to offset %lld: %s\n", offset, strerror(errno));
70 return -1;
71 }
69 size_t written = 0; 72 size_t written = 0;
70 while (written < size) { 73 while (written < size) {
71 ssize_t wrote = write(wfd, buffer + written, size - written); 74 ssize_t wrote = TEMP_FAILURE_RETRY(write(wfd, buffer + written, size - written));
72 if (wrote < 0) { 75 if (wrote == -1) {
73 ALOGE("error writing offset %lld: %s\n", offset, strerror(errno)); 76 ALOGE("error writing offset %lld: %s\n", (offset + written), strerror(errno));
74 return -1; 77 return -1;
75 } 78 }
76 written += wrote; 79 written += wrote;
@@ -275,8 +278,9 @@ int produce_block_map(const char* path, const char* map_file, const char* blk_de
275 if (encrypted) { 278 if (encrypted) {
276 size_t so_far = 0; 279 size_t so_far = 0;
277 while (so_far < sb.st_blksize && pos < sb.st_size) { 280 while (so_far < sb.st_blksize && pos < sb.st_size) {
278 ssize_t this_read = read(fd, buffers[tail] + so_far, sb.st_blksize - so_far); 281 ssize_t this_read =
279 if (this_read < 0) { 282 TEMP_FAILURE_RETRY(read(fd, buffers[tail] + so_far, sb.st_blksize - so_far));
283 if (this_read == -1) {
280 ALOGE("failed to read: %s\n", strerror(errno)); 284 ALOGE("failed to read: %s\n", strerror(errno));
281 return -1; 285 return -1;
282 } 286 }
@@ -340,8 +344,8 @@ void wipe_misc() {
340 size_t written = 0; 344 size_t written = 0;
341 size_t size = sizeof(zeroes); 345 size_t size = sizeof(zeroes);
342 while (written < size) { 346 while (written < size) {
343 ssize_t w = write(fd, zeroes, size-written); 347 ssize_t w = TEMP_FAILURE_RETRY(write(fd, zeroes, size-written));
344 if (w < 0 && errno != EINTR) { 348 if (w == -1) {
345 ALOGE("zero write failed: %s\n", strerror(errno)); 349 ALOGE("zero write failed: %s\n", strerror(errno));
346 return; 350 return;
347 } else { 351 } else {
diff --git a/updater/blockimg.c b/updater/blockimg.c
index d5344f99..532e7b84 100644
--- a/updater/blockimg.c
+++ b/updater/blockimg.c
@@ -113,13 +113,12 @@ static int range_overlaps(RangeSet* r1, RangeSet* r2) {
113static int read_all(int fd, uint8_t* data, size_t size) { 113static int read_all(int fd, uint8_t* data, size_t size) {
114 size_t so_far = 0; 114 size_t so_far = 0;
115 while (so_far < size) { 115 while (so_far < size) {
116 ssize_t r = read(fd, data+so_far, size-so_far); 116 ssize_t r = TEMP_FAILURE_RETRY(read(fd, data+so_far, size-so_far));
117 if (r < 0 && errno != EINTR) { 117 if (r == -1) {
118 fprintf(stderr, "read failed: %s\n", strerror(errno)); 118 fprintf(stderr, "read failed: %s\n", strerror(errno));
119 return -1; 119 return -1;
120 } else {
121 so_far += r;
122 } 120 }
121 so_far += r;
123 } 122 }
124 return 0; 123 return 0;
125} 124}
@@ -127,13 +126,12 @@ static int read_all(int fd, uint8_t* data, size_t size) {
127static int write_all(int fd, const uint8_t* data, size_t size) { 126static int write_all(int fd, const uint8_t* data, size_t size) {
128 size_t written = 0; 127 size_t written = 0;
129 while (written < size) { 128 while (written < size) {
130 ssize_t w = write(fd, data+written, size-written); 129 ssize_t w = TEMP_FAILURE_RETRY(write(fd, data+written, size-written));
131 if (w < 0 && errno != EINTR) { 130 if (w == -1) {
132 fprintf(stderr, "write failed: %s\n", strerror(errno)); 131 fprintf(stderr, "write failed: %s\n", strerror(errno));
133 return -1; 132 return -1;
134 } else {
135 written += w;
136 } 133 }
134 written += w;
137 } 135 }
138 136
139 if (fsync(fd) == -1) { 137 if (fsync(fd) == -1) {
@@ -144,19 +142,13 @@ static int write_all(int fd, const uint8_t* data, size_t size) {
144 return 0; 142 return 0;
145} 143}
146 144
147static int check_lseek(int fd, off64_t offset, int whence) { 145static bool check_lseek(int fd, off64_t offset, int whence) {
148 while (true) { 146 off64_t rc = TEMP_FAILURE_RETRY(lseek64(fd, offset, whence));
149 off64_t ret = lseek64(fd, offset, whence); 147 if (rc == -1) {
150 if (ret < 0) { 148 fprintf(stderr, "lseek64 failed: %s\n", strerror(errno));
151 if (errno != EINTR) { 149 return false;
152 fprintf(stderr, "lseek64 failed: %s\n", strerror(errno));
153 return -1;
154 }
155 } else {
156 break;
157 }
158 } 150 }
159 return 0; 151 return true;
160} 152}
161 153
162static void allocate(size_t size, uint8_t** buffer, size_t* buffer_alloc) { 154static void allocate(size_t size, uint8_t** buffer, size_t* buffer_alloc) {
@@ -213,8 +205,8 @@ static ssize_t RangeSinkWrite(const uint8_t* data, ssize_t size, void* token) {
213 rss->p_remain = (rss->tgt->pos[rss->p_block * 2 + 1] - 205 rss->p_remain = (rss->tgt->pos[rss->p_block * 2 + 1] -
214 rss->tgt->pos[rss->p_block * 2]) * BLOCKSIZE; 206 rss->tgt->pos[rss->p_block * 2]) * BLOCKSIZE;
215 207
216 if (check_lseek(rss->fd, (off64_t)rss->tgt->pos[rss->p_block*2] * BLOCKSIZE, 208 if (!check_lseek(rss->fd, (off64_t)rss->tgt->pos[rss->p_block*2] * BLOCKSIZE,
217 SEEK_SET) == -1) { 209 SEEK_SET)) {
218 break; 210 break;
219 } 211 }
220 } else { 212 } else {
@@ -306,7 +298,7 @@ static int ReadBlocks(RangeSet* src, uint8_t* buffer, int fd) {
306 } 298 }
307 299
308 for (i = 0; i < src->count; ++i) { 300 for (i = 0; i < src->count; ++i) {
309 if (check_lseek(fd, (off64_t) src->pos[i * 2] * BLOCKSIZE, SEEK_SET) == -1) { 301 if (!check_lseek(fd, (off64_t) src->pos[i * 2] * BLOCKSIZE, SEEK_SET)) {
310 return -1; 302 return -1;
311 } 303 }
312 304
@@ -332,7 +324,7 @@ static int WriteBlocks(RangeSet* tgt, uint8_t* buffer, int fd) {
332 } 324 }
333 325
334 for (i = 0; i < tgt->count; ++i) { 326 for (i = 0; i < tgt->count; ++i) {
335 if (check_lseek(fd, (off64_t) tgt->pos[i * 2] * BLOCKSIZE, SEEK_SET) == -1) { 327 if (!check_lseek(fd, (off64_t) tgt->pos[i * 2] * BLOCKSIZE, SEEK_SET)) {
336 return -1; 328 return -1;
337 } 329 }
338 330
@@ -1217,7 +1209,7 @@ static int PerformCommandZero(CommandParameters* params) {
1217 1209
1218 if (params->canwrite) { 1210 if (params->canwrite) {
1219 for (i = 0; i < tgt->count; ++i) { 1211 for (i = 0; i < tgt->count; ++i) {
1220 if (check_lseek(params->fd, (off64_t) tgt->pos[i * 2] * BLOCKSIZE, SEEK_SET) == -1) { 1212 if (!check_lseek(params->fd, (off64_t) tgt->pos[i * 2] * BLOCKSIZE, SEEK_SET)) {
1221 goto pczout; 1213 goto pczout;
1222 } 1214 }
1223 1215
@@ -1271,7 +1263,7 @@ static int PerformCommandNew(CommandParameters* params) {
1271 rss.p_block = 0; 1263 rss.p_block = 0;
1272 rss.p_remain = (tgt->pos[1] - tgt->pos[0]) * BLOCKSIZE; 1264 rss.p_remain = (tgt->pos[1] - tgt->pos[0]) * BLOCKSIZE;
1273 1265
1274 if (check_lseek(params->fd, (off64_t) tgt->pos[0] * BLOCKSIZE, SEEK_SET) == -1) { 1266 if (!check_lseek(params->fd, (off64_t) tgt->pos[0] * BLOCKSIZE, SEEK_SET)) {
1275 goto pcnout; 1267 goto pcnout;
1276 } 1268 }
1277 1269
@@ -1367,7 +1359,7 @@ static int PerformCommandDiff(CommandParameters* params) {
1367 rss.p_block = 0; 1359 rss.p_block = 0;
1368 rss.p_remain = (tgt->pos[1] - tgt->pos[0]) * BLOCKSIZE; 1360 rss.p_remain = (tgt->pos[1] - tgt->pos[0]) * BLOCKSIZE;
1369 1361
1370 if (check_lseek(params->fd, (off64_t) tgt->pos[0] * BLOCKSIZE, SEEK_SET) == -1) { 1362 if (!check_lseek(params->fd, (off64_t) tgt->pos[0] * BLOCKSIZE, SEEK_SET)) {
1371 goto pcdout; 1363 goto pcdout;
1372 } 1364 }
1373 1365
@@ -1906,7 +1898,7 @@ Value* RangeSha1Fn(const char* name, State* state, int argc, Expr* argv[]) {
1906 1898
1907 int i, j; 1899 int i, j;
1908 for (i = 0; i < rs->count; ++i) { 1900 for (i = 0; i < rs->count; ++i) {
1909 if (check_lseek(fd, (off64_t)rs->pos[i*2] * BLOCKSIZE, SEEK_SET) == -1) { 1901 if (!check_lseek(fd, (off64_t)rs->pos[i*2] * BLOCKSIZE, SEEK_SET)) {
1910 ErrorAbort(state, "failed to seek %s: %s", blockdev_filename->data, 1902 ErrorAbort(state, "failed to seek %s: %s", blockdev_filename->data,
1911 strerror(errno)); 1903 strerror(errno));
1912 goto done; 1904 goto done;