summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlex Deymo <deymo@google.com>2015-10-12 17:48:28 -0700
committerAlex Deymo <deymo@google.com>2015-10-12 18:04:37 -0700
commite1526cf39d321fff908a1b95143cc0f9fff52738 (patch)
tree3e0bd10ebdf1a7b8457d5cad1e52c7255968a01c
parenta09afd999331d0b648a368f29c2cf45c0e011e28 (diff)
downloadbsdiff-e1526cf39d321fff908a1b95143cc0f9fff52738.tar.gz
Ran clang-format on all the Chromium OS sources.
The source code has mixed style guides. The new introduced extents and exfile modules had 4-spaces indents but one tab instead of two indents probably due to bad editor cofiguration. These modules were first introduced as local patches to the .ebuild file but later merged in the git repository. This patch fixes the style guide on all the files added by Chromium OS (all the source files execpt bsdiff.c and bspatch.c). The remaining file should be converted over to the Chromium style guide when parts of it are modified. A .clang-format file is included in this patch to help with that process. Bug: None Test: `make all test && ./unittests`; mm Change-Id: Ief3c557cb35aae67871a5ccde8486af651b84a35
-rw-r--r--.clang-format4
-rw-r--r--bsdiff.h5
-rw-r--r--bsdiff_main.c4
-rw-r--r--bspatch.h11
-rw-r--r--bspatch_main.c8
-rw-r--r--exfile.c560
-rw-r--r--exfile.h20
-rw-r--r--extents.c146
-rw-r--r--extents.h4
-rw-r--r--test_utils.cc5
-rw-r--r--test_utils.h12
-rw-r--r--testrunner.cc2
12 files changed, 392 insertions, 389 deletions
diff --git a/.clang-format b/.clang-format
new file mode 100644
index 0000000..998f530
--- /dev/null
+++ b/.clang-format
@@ -0,0 +1,4 @@
+BasedOnStyle: Chromium
+
+MaxEmptyLinesToKeep: 2
+AllowShortBlocksOnASingleLine: true
diff --git a/bsdiff.h b/bsdiff.h
index f797b13..e7012f8 100644
--- a/bsdiff.h
+++ b/bsdiff.h
@@ -10,11 +10,12 @@
extern "C" {
#endif
-int bsdiff(const char* old_filename, const char* new_filename,
+int bsdiff(const char* old_filename,
+ const char* new_filename,
const char* patch_filename);
#ifdef __cplusplus
}
#endif
-#endif /* _BSDIFF_BSDIFF_H_ */
+#endif /* _BSDIFF_BSDIFF_H_ */
diff --git a/bsdiff_main.c b/bsdiff_main.c
index 49491bf..4a42f6b 100644
--- a/bsdiff_main.c
+++ b/bsdiff_main.c
@@ -7,8 +7,8 @@
#include "bsdiff.h"
-int main(int argc, char *argv[]) {
- if (argc!=4)
+int main(int argc, char* argv[]) {
+ if (argc != 4)
errx(1, "usage: %s oldfile newfile patchfile\n", argv[0]);
return bsdiff(argv[1], argv[2], argv[3]);
diff --git a/bspatch.h b/bspatch.h
index 8071cc4..81c4d5b 100644
--- a/bspatch.h
+++ b/bspatch.h
@@ -10,13 +10,14 @@
extern "C" {
#endif
-int bspatch(
- const char* old_filename, const char* new_filename,
- const char* patch_filename,
- const char* old_extents, const char* new_extents);
+int bspatch(const char* old_filename,
+ const char* new_filename,
+ const char* patch_filename,
+ const char* old_extents,
+ const char* new_extents);
#ifdef __cplusplus
}
#endif
-#endif /* _BSDIFF_BSPATCH_H_ */
+#endif /* _BSDIFF_BSPATCH_H_ */
diff --git a/bspatch_main.c b/bspatch_main.c
index a5442e9..b799186 100644
--- a/bspatch_main.c
+++ b/bspatch_main.c
@@ -7,11 +7,11 @@
#include "bspatch.h"
-#define USAGE_TEMPLATE_STR \
- "usage: %s oldfile newfile patchfile [old-extents new-extents]\n" \
- "with extents taking the form \"off_1:len_1,...,off_n:len_n\"\n"
+#define USAGE_TEMPLATE_STR \
+ "usage: %s oldfile newfile patchfile [old-extents new-extents]\n" \
+ "with extents taking the form \"off_1:len_1,...,off_n:len_n\"\n"
-int main(int argc, char * argv[]) {
+int main(int argc, char* argv[]) {
const char* old_extents = NULL;
const char* new_extents = NULL;
diff --git a/exfile.c b/exfile.c
index 945d66f..4a40d0b 100644
--- a/exfile.c
+++ b/exfile.c
@@ -53,38 +53,38 @@
/* Extent prefix length. */
typedef struct {
- size_t prec; /* total length of preceding extents */
- size_t total; /* total length including current extent */
+ size_t prec; /* total length of preceding extents */
+ size_t total; /* total length including current extent */
} prefix_len_t;
/* Extent file logical modes. Used as index to the mapping from logical modes
* to open(2) and fopen(3) modes below. */
typedef enum {
- EXFILE_MODE_RO,
- EXFILE_MODE_WO,
- EXFILE_MODE_RW,
- EXFILE_MODE_MAX /* sentinel */
+ EXFILE_MODE_RO,
+ EXFILE_MODE_WO,
+ EXFILE_MODE_RW,
+ EXFILE_MODE_MAX /* sentinel */
} exfile_mode_t;
/* An extent file control object (aka "cookie"). */
typedef struct {
- int fd; /* underlying file descriptor */
- size_t ex_count; /* number of extents (non-zero) */
- ex_t *ex_arr; /* array of extents */
- prefix_len_t *prefix_len_arr; /* total lengths of extent prefixes */
- void (*ex_free)(void *); /* extent array free function */
- size_t total_ex_len; /* total length of all extents (constant) */
- off_t curr_file_pos; /* current underlying file position */
- size_t curr_ex_idx; /* current extent index */
- size_t curr_ex_pos; /* current position within extent */
- off_t curr_pos; /* current logical file position */
+ int fd; /* underlying file descriptor */
+ size_t ex_count; /* number of extents (non-zero) */
+ ex_t* ex_arr; /* array of extents */
+ prefix_len_t* prefix_len_arr; /* total lengths of extent prefixes */
+ void (*ex_free)(void*); /* extent array free function */
+ size_t total_ex_len; /* total length of all extents (constant) */
+ off_t curr_file_pos; /* current underlying file position */
+ size_t curr_ex_idx; /* current extent index */
+ size_t curr_ex_pos; /* current position within extent */
+ off_t curr_pos; /* current logical file position */
} exfile_t;
/* Mapping from fopen(3) modes to extent file logical modes. */
static const struct {
- const char *fopen_mode;
- exfile_mode_t mode;
+ const char* fopen_mode;
+ exfile_mode_t mode;
} fopen_mode_to_mode[] = {
{"r", EXFILE_MODE_RO},
{"r+", EXFILE_MODE_RW},
@@ -105,220 +105,210 @@ static const int mode_to_open_flags[EXFILE_MODE_MAX] = {
* the extent that contains the location |pos|. Uses an array |prefix_len_arr|
* of corresponding prefix lengths. The total complexity is O(log(D)), where D
* is the distance between the returned extent index and |init_ex_idx|. */
-static size_t
-ex_arr_search(size_t ex_count, const ex_t *ex_arr,
- const prefix_len_t *prefix_len_arr, size_t pos,
- size_t init_ex_idx)
-{
- assert(ex_arr && ex_count);
- const ssize_t last_ex_idx = ex_count - 1;
- assert(init_ex_idx <= ex_count);
- assert(pos < prefix_len_arr[last_ex_idx].total);
- if (init_ex_idx == ex_count)
- init_ex_idx = last_ex_idx; /* adjustment for purposes of the search below */
-
- /* First, search in exponentially increasing leaps from the current extent,
- * until an interval bounding the target position was obtained. Here i and j
- * are the left and right (inclusive) index boundaries, respectively. */
- ssize_t i = init_ex_idx;
- ssize_t j = i;
- size_t leap = 1;
- /* Go left, as needed. */
- while (i > 0 && pos < prefix_len_arr[i].prec) {
- j = i - 1;
- if ((i -= leap) < 0)
- i = 0;
- leap <<= 1;
- }
- /* Go right, as needed. */
- while (j < last_ex_idx && pos >= prefix_len_arr[j].total) {
- i = j + 1;
- if ((j += leap) > last_ex_idx)
- j = last_ex_idx;
- leap <<= 1;
- }
-
- /* Then, perform a binary search between i and j. */
- size_t k = 0;
- while (1) {
- k = (i + j) / 2;
- if (pos < prefix_len_arr[k].prec)
- j = k - 1;
- else if (pos >= prefix_len_arr[k].total)
- i = k + 1;
- else
- break;
- }
-
- return k;
+static size_t ex_arr_search(size_t ex_count,
+ const ex_t* ex_arr,
+ const prefix_len_t* prefix_len_arr,
+ size_t pos,
+ size_t init_ex_idx) {
+ assert(ex_arr && ex_count);
+ const ssize_t last_ex_idx = ex_count - 1;
+ assert(init_ex_idx <= ex_count);
+ assert(pos < prefix_len_arr[last_ex_idx].total);
+ if (init_ex_idx == ex_count)
+ init_ex_idx = last_ex_idx; /* adjustment for purposes of the search below */
+
+ /* First, search in exponentially increasing leaps from the current extent,
+ * until an interval bounding the target position was obtained. Here i and j
+ * are the left and right (inclusive) index boundaries, respectively. */
+ ssize_t i = init_ex_idx;
+ ssize_t j = i;
+ size_t leap = 1;
+ /* Go left, as needed. */
+ while (i > 0 && pos < prefix_len_arr[i].prec) {
+ j = i - 1;
+ if ((i -= leap) < 0)
+ i = 0;
+ leap <<= 1;
+ }
+ /* Go right, as needed. */
+ while (j < last_ex_idx && pos >= prefix_len_arr[j].total) {
+ i = j + 1;
+ if ((j += leap) > last_ex_idx)
+ j = last_ex_idx;
+ leap <<= 1;
+ }
+
+ /* Then, perform a binary search between i and j. */
+ size_t k = 0;
+ while (1) {
+ k = (i + j) / 2;
+ if (pos < prefix_len_arr[k].prec)
+ j = k - 1;
+ else if (pos >= prefix_len_arr[k].total)
+ i = k + 1;
+ else
+ break;
+ }
+
+ return k;
}
/* Performs I/O operations (either read or write) on an extent file, advancing
* through consecutive extents and updating the logical/physical file position
* as we go. */
-static ssize_t
-exfile_io(exfile_t *xf, int do_read, char *buf, size_t size)
-{
- if (xf->curr_ex_idx == xf->ex_count)
- return 0; /* end-of-extent-file */
-
- /* Reading or writing? */
- typedef ssize_t (io_func_t)(int, void *, size_t);
- io_func_t *io_func;
- ssize_t error_ret_val;
- if (do_read) {
- io_func = read;
- error_ret_val = -1;
- } else {
- io_func = (io_func_t *)write;
- error_ret_val = 0; /* must not return a negative value when writing */
+static ssize_t exfile_io(exfile_t* xf, int do_read, char* buf, size_t size) {
+ if (xf->curr_ex_idx == xf->ex_count)
+ return 0; /* end-of-extent-file */
+
+ /* Reading or writing? */
+ typedef ssize_t(io_func_t)(int, void*, size_t);
+ io_func_t* io_func;
+ ssize_t error_ret_val;
+ if (do_read) {
+ io_func = read;
+ error_ret_val = -1;
+ } else {
+ io_func = (io_func_t*)write;
+ error_ret_val = 0; /* must not return a negative value when writing */
+ }
+
+ /* Start processing data along extents. */
+ const ex_t* curr_ex = xf->ex_arr + xf->curr_ex_idx;
+ assert(curr_ex->len >= xf->curr_ex_pos);
+ size_t curr_ex_rem_len = curr_ex->len - xf->curr_ex_pos;
+ ssize_t total_bytes = 0;
+ while (size) {
+ /* Advance to the next extent of non-zero length. */
+ while (curr_ex_rem_len == 0) {
+ xf->curr_ex_idx++;
+ xf->curr_ex_pos = 0;
+ if (xf->curr_ex_idx == xf->ex_count)
+ return total_bytes; /* end-of-extent-file */
+ curr_ex++;
+ curr_ex_rem_len = curr_ex->len;
}
- /* Start processing data along extents. */
- const ex_t *curr_ex = xf->ex_arr + xf->curr_ex_idx;
- assert(curr_ex->len >= xf->curr_ex_pos);
- size_t curr_ex_rem_len = curr_ex->len - xf->curr_ex_pos;
- ssize_t total_bytes = 0;
- while (size) {
- /* Advance to the next extent of non-zero length. */
- while (curr_ex_rem_len == 0) {
- xf->curr_ex_idx++;
- xf->curr_ex_pos = 0;
- if (xf->curr_ex_idx == xf->ex_count)
- return total_bytes; /* end-of-extent-file */
- curr_ex++;
- curr_ex_rem_len = curr_ex->len;
- }
-
- const int is_real_ex = (curr_ex->off >= 0);
-
- /* Seek to the correct file position, as necessary. */
- if (is_real_ex) {
- const off_t file_pos = curr_ex->off + xf->curr_ex_pos;
- if (xf->curr_file_pos != file_pos) {
- if (lseek(xf->fd, file_pos, SEEK_SET) == (off_t)-1) {
- xf->curr_file_pos = -1; /* unknown file position */
- return total_bytes ? total_bytes : error_ret_val;
- }
- xf->curr_file_pos = file_pos;
- }
- }
-
- /* Process data to the end of the current extent or the requested
- * count, whichever is smaller. */
- size_t io_count = (size < curr_ex_rem_len ? size : curr_ex_rem_len);
- ssize_t io_bytes = io_count;
- if (is_real_ex)
- io_bytes = io_func(xf->fd, buf, io_count);
- else if (do_read)
- memset(buf, 0, io_count);
-
- /* Stop on error. */
- if (io_bytes < 0) {
- if (total_bytes == 0)
- total_bytes = error_ret_val;
- break;
- }
-
- /* Update read state. */
- total_bytes += io_bytes;
- if (is_real_ex)
- xf->curr_file_pos += io_bytes;
- xf->curr_ex_pos += io_bytes;
- xf->curr_pos += io_bytes;
-
- /* If we didn't read the whole extent, finish; delegate handling of
- * partial read/write back to the caller. */
- if ((curr_ex_rem_len -= io_bytes) > 0)
- break;
-
- /* Update total count and buffer pointer. */
- size -= io_bytes;
- buf += io_bytes;
+ const int is_real_ex = (curr_ex->off >= 0);
+
+ /* Seek to the correct file position, as necessary. */
+ if (is_real_ex) {
+ const off_t file_pos = curr_ex->off + xf->curr_ex_pos;
+ if (xf->curr_file_pos != file_pos) {
+ if (lseek(xf->fd, file_pos, SEEK_SET) == (off_t)-1) {
+ xf->curr_file_pos = -1; /* unknown file position */
+ return total_bytes ? total_bytes : error_ret_val;
+ }
+ xf->curr_file_pos = file_pos;
+ }
}
- return total_bytes;
+ /* Process data to the end of the current extent or the requested
+ * count, whichever is smaller. */
+ size_t io_count = (size < curr_ex_rem_len ? size : curr_ex_rem_len);
+ ssize_t io_bytes = io_count;
+ if (is_real_ex)
+ io_bytes = io_func(xf->fd, buf, io_count);
+ else if (do_read)
+ memset(buf, 0, io_count);
+
+ /* Stop on error. */
+ if (io_bytes < 0) {
+ if (total_bytes == 0)
+ total_bytes = error_ret_val;
+ break;
+ }
+
+ /* Update read state. */
+ total_bytes += io_bytes;
+ if (is_real_ex)
+ xf->curr_file_pos += io_bytes;
+ xf->curr_ex_pos += io_bytes;
+ xf->curr_pos += io_bytes;
+
+ /* If we didn't read the whole extent, finish; delegate handling of
+ * partial read/write back to the caller. */
+ if ((curr_ex_rem_len -= io_bytes) > 0)
+ break;
+
+ /* Update total count and buffer pointer. */
+ size -= io_bytes;
+ buf += io_bytes;
+ }
+
+ return total_bytes;
}
/* Reads up to |size| bytes from an extent file into |buf|. This implements the
* cookie_read_function_t interface and is a thin wrapper around exfile_io()
* (see above). Returns the number of bytes read, or -1 on error. */
-static ssize_t
-exfile_read(void *cookie, char *buf, size_t size)
-{
- return exfile_io((exfile_t *)cookie, TRUE, buf, size);
+static ssize_t exfile_read(void* cookie, char* buf, size_t size) {
+ return exfile_io((exfile_t*)cookie, TRUE, buf, size);
}
/* Writes up to |size| bytes from |buf| to an extent file. This implements the
* cookie_write_function_t interface and is a thin wrapper around exfile_io()
* (see above). Returns the number of bytes written; must NOT return a negative
* value. */
-static ssize_t
-exfile_write(void *cookie, const char *buf, size_t size)
-{
- return exfile_io((exfile_t *)cookie, FALSE, (char *)buf, size);
+static ssize_t exfile_write(void* cookie, const char* buf, size_t size) {
+ return exfile_io((exfile_t*)cookie, FALSE, (char*)buf, size);
}
/* Performs seek on an extent file, repositioning it to the value of |*pos_p|
* according to |whence|. This implements the cookie_seek_function_t interface.
* On success, stores the resulting logical position measured in bytes along
* contiguous extents into |*pos_p| and returns 0; otherwise returns -1. */
-static int
-exfile_seek(void *cookie, off64_t *pos_p, int whence)
-{
- exfile_t *xf = (exfile_t *)cookie;
-
- /* Compute the absolute logical target position. */
- off64_t new_pos = *pos_p;
- if (whence == SEEK_CUR)
- new_pos += xf->curr_pos;
- else if (whence == SEEK_END)
- new_pos += xf->total_ex_len;
-
- /* Ensure that the target position is valid. Note that repositioning the
- * file right past the last extent is considered valid, in line with normal
- * seek behavior, although no write (nor read) can be performed there. */
- if (new_pos < 0 || new_pos > (off64_t)xf->total_ex_len)
- return -1;
-
- if (new_pos != (off64_t)xf->curr_pos) {
- /* Find the extend that contains the requested logical position; handle
- * special case upfront, for efficiency. */
- size_t new_ex_idx = 0;
- if (new_pos == (off64_t)xf->total_ex_len)
- new_ex_idx = xf->ex_count;
- else if (new_pos)
- new_ex_idx = ex_arr_search(xf->ex_count, xf->ex_arr,
- xf->prefix_len_arr, new_pos,
- xf->curr_ex_idx);
-
- /* Set the logical position markers. */
- xf->curr_ex_idx = new_ex_idx;
- xf->curr_ex_pos =
- (new_ex_idx < xf->ex_count ?
- (size_t)(new_pos - xf->prefix_len_arr[new_ex_idx].prec) : 0);
- xf->curr_pos = (off_t)new_pos;
- }
-
- *pos_p = new_pos;
- return 0;
+static int exfile_seek(void* cookie, off64_t* pos_p, int whence) {
+ exfile_t* xf = (exfile_t*)cookie;
+
+ /* Compute the absolute logical target position. */
+ off64_t new_pos = *pos_p;
+ if (whence == SEEK_CUR)
+ new_pos += xf->curr_pos;
+ else if (whence == SEEK_END)
+ new_pos += xf->total_ex_len;
+
+ /* Ensure that the target position is valid. Note that repositioning the
+ * file right past the last extent is considered valid, in line with normal
+ * seek behavior, although no write (nor read) can be performed there. */
+ if (new_pos < 0 || new_pos > (off64_t)xf->total_ex_len)
+ return -1;
+
+ if (new_pos != (off64_t)xf->curr_pos) {
+ /* Find the extend that contains the requested logical position; handle
+ * special case upfront, for efficiency. */
+ size_t new_ex_idx = 0;
+ if (new_pos == (off64_t)xf->total_ex_len)
+ new_ex_idx = xf->ex_count;
+ else if (new_pos)
+ new_ex_idx = ex_arr_search(xf->ex_count, xf->ex_arr, xf->prefix_len_arr,
+ new_pos, xf->curr_ex_idx);
+
+ /* Set the logical position markers. */
+ xf->curr_ex_idx = new_ex_idx;
+ xf->curr_ex_pos =
+ (new_ex_idx < xf->ex_count
+ ? (size_t)(new_pos - xf->prefix_len_arr[new_ex_idx].prec)
+ : 0);
+ xf->curr_pos = (off_t)new_pos;
+ }
+
+ *pos_p = new_pos;
+ return 0;
}
/* Closes an open extent file. This implements the cookie_close_function_t
* interface. Always returns 0 (success). */
-static int
-exfile_close(void *cookie)
-{
- exfile_t *xf = (exfile_t *)cookie;
- if (xf) {
- if (xf->fd >= 0)
- close(xf->fd);
- free(xf->prefix_len_arr);
- if (xf->ex_free)
- xf->ex_free(xf->ex_arr);
- free(xf);
- }
- return 0;
+static int exfile_close(void* cookie) {
+ exfile_t* xf = (exfile_t*)cookie;
+ if (xf) {
+ if (xf->fd >= 0)
+ close(xf->fd);
+ free(xf->prefix_len_arr);
+ if (xf->ex_free)
+ xf->ex_free(xf->ex_arr);
+ free(xf);
+ }
+ return 0;
}
static const cookie_io_functions_t cookie_io_funcs = {
@@ -328,90 +318,94 @@ static const cookie_io_functions_t cookie_io_funcs = {
.close = exfile_close,
};
-static FILE *
-exfile_open(int fd, const char *path, const char *fopen_mode, ex_t *ex_arr,
- size_t ex_count, void (*ex_free)(void *))
-{
- /* Argument sanity check. */
- if (!(ex_arr && ex_count && (fd >= 0 || path) && (fd < 0 || !path)))
- return NULL;
-
- /* Validate mode argument. */
- exfile_mode_t mode = EXFILE_MODE_MAX;
- size_t i;
- for (i = 0; i < arraysize(fopen_mode_to_mode); i++)
- if (!strcmp(fopen_mode_to_mode[i].fopen_mode, fopen_mode)) {
- mode = fopen_mode_to_mode[i].mode;
- break;
- }
- if (mode == EXFILE_MODE_MAX)
- return NULL;
-
- /* Open the underlying file, if not already provided. */
- int do_close_fd = FALSE;
- if (fd < 0) {
- if ((fd = open(path, mode_to_open_flags[mode])) < 0)
- return NULL;
- do_close_fd = TRUE;
+static FILE* exfile_open(int fd,
+ const char* path,
+ const char* fopen_mode,
+ ex_t* ex_arr,
+ size_t ex_count,
+ void (*ex_free)(void*)) {
+ /* Argument sanity check. */
+ if (!(ex_arr && ex_count && (fd >= 0 || path) && (fd < 0 || !path)))
+ return NULL;
+
+ /* Validate mode argument. */
+ exfile_mode_t mode = EXFILE_MODE_MAX;
+ size_t i;
+ for (i = 0; i < arraysize(fopen_mode_to_mode); i++)
+ if (!strcmp(fopen_mode_to_mode[i].fopen_mode, fopen_mode)) {
+ mode = fopen_mode_to_mode[i].mode;
+ break;
}
-
- /* Allocate memory and open file streams, for both the underlying file and
- * the handle returned to the caller. */
- exfile_t *xf = NULL;
- prefix_len_t *prefix_len_arr = NULL;
- FILE *handle = NULL;
- if (!((xf = (exfile_t *)calloc(1, sizeof(exfile_t))) &&
- (prefix_len_arr =
- (prefix_len_t *)malloc(sizeof(prefix_len_t) * ex_count)) &&
- (handle = fopencookie(xf, fopen_mode, cookie_io_funcs)))) {
- /* If a file was opened above, close it. */
- if (do_close_fd)
- close(fd);
- if (xf)
- xf->fd = -1; /* invalidate prior to calling exfile_close() */
-
- free(prefix_len_arr);
- if (handle)
- fclose(handle); /* will call exfile_close already */
- else
- exfile_close(xf);
- return NULL;
- }
-
- /* Compute the prefix lengths. */
- size_t prefix_len = 0;
- for (i = 0; i < ex_count; i++) {
- prefix_len_arr[i].prec = prefix_len;
- prefix_len += ex_arr[i].len;
- prefix_len_arr[i].total = prefix_len;
- }
-
- /* Configure control object, including physical/logical file position. */
- xf->fd = fd;
- xf->ex_count = ex_count;
- xf->ex_arr = ex_arr;
- xf->prefix_len_arr = prefix_len_arr;
- xf->ex_free = ex_free;
- xf->total_ex_len = prefix_len_arr[ex_count - 1].total;
- xf->curr_file_pos = lseek(fd, 0, SEEK_CUR);
- xf->curr_ex_idx = 0;
- xf->curr_ex_pos = 0;
- xf->curr_pos = 0;
-
- /* Return the external stream handle. */
- return handle;
+ if (mode == EXFILE_MODE_MAX)
+ return NULL;
+
+ /* Open the underlying file, if not already provided. */
+ int do_close_fd = FALSE;
+ if (fd < 0) {
+ if ((fd = open(path, mode_to_open_flags[mode])) < 0)
+ return NULL;
+ do_close_fd = TRUE;
+ }
+
+ /* Allocate memory and open file streams, for both the underlying file and
+ * the handle returned to the caller. */
+ exfile_t* xf = NULL;
+ prefix_len_t* prefix_len_arr = NULL;
+ FILE* handle = NULL;
+ if (!((xf = (exfile_t*)calloc(1, sizeof(exfile_t))) &&
+ (prefix_len_arr =
+ (prefix_len_t*)malloc(sizeof(prefix_len_t) * ex_count)) &&
+ (handle = fopencookie(xf, fopen_mode, cookie_io_funcs)))) {
+ /* If a file was opened above, close it. */
+ if (do_close_fd)
+ close(fd);
+ if (xf)
+ xf->fd = -1; /* invalidate prior to calling exfile_close() */
+
+ free(prefix_len_arr);
+ if (handle)
+ fclose(handle); /* will call exfile_close already */
+ else
+ exfile_close(xf);
+ return NULL;
+ }
+
+ /* Compute the prefix lengths. */
+ size_t prefix_len = 0;
+ for (i = 0; i < ex_count; i++) {
+ prefix_len_arr[i].prec = prefix_len;
+ prefix_len += ex_arr[i].len;
+ prefix_len_arr[i].total = prefix_len;
+ }
+
+ /* Configure control object, including physical/logical file position. */
+ xf->fd = fd;
+ xf->ex_count = ex_count;
+ xf->ex_arr = ex_arr;
+ xf->prefix_len_arr = prefix_len_arr;
+ xf->ex_free = ex_free;
+ xf->total_ex_len = prefix_len_arr[ex_count - 1].total;
+ xf->curr_file_pos = lseek(fd, 0, SEEK_CUR);
+ xf->curr_ex_idx = 0;
+ xf->curr_ex_pos = 0;
+ xf->curr_pos = 0;
+
+ /* Return the external stream handle. */
+ return handle;
}
-FILE *
-exfile_fopen(const char *path, const char *fopen_mode, ex_t *ex_arr,
- size_t ex_count, void (*ex_free)(void *))
-{
- return exfile_open(-1, path, fopen_mode, ex_arr, ex_count, ex_free);
+FILE* exfile_fopen(const char* path,
+ const char* fopen_mode,
+ ex_t* ex_arr,
+ size_t ex_count,
+ void (*ex_free)(void*)) {
+ return exfile_open(-1, path, fopen_mode, ex_arr, ex_count, ex_free);
}
-FILE *
-exfile_fdopen(int fd, const char *fopen_mode, ex_t *ex_arr,
- size_t ex_count, void (*ex_free)(void *))
-{
- return exfile_open(fd, NULL, fopen_mode, ex_arr, ex_count, ex_free);
+FILE* exfile_fdopen(int fd,
+ const char* fopen_mode,
+ ex_t* ex_arr,
+ size_t ex_count,
+ void (*ex_free)(void*)) {
+ return exfile_open(fd, NULL, fopen_mode, ex_arr, ex_count, ex_free);
}
diff --git a/exfile.h b/exfile.h
index b09e456..e109f04 100644
--- a/exfile.h
+++ b/exfile.h
@@ -27,8 +27,8 @@
/* An extent, defined by an offset and a length. */
typedef struct {
- off_t off; /* the extent offset; negative indicates a sparse extent */
- size_t len; /* the extent length */
+ off_t off; /* the extent offset; negative indicates a sparse extent */
+ size_t len; /* the extent length */
} ex_t;
@@ -40,14 +40,20 @@ typedef struct {
* deallocate the extent array once the file object is closed. Returns a FILE
* pointer that can be used with ordinary stream functions (e.g. fread), or
* NULL if opening the file has failed. */
-FILE *exfile_fopen(const char *path, const char *fopen_mode, ex_t *ex_arr,
- size_t ex_count, void (*ex_free)(void *));
+FILE* exfile_fopen(const char* path,
+ const char* fopen_mode,
+ ex_t* ex_arr,
+ size_t ex_count,
+ void (*ex_free)(void*));
/* Associates an extent file stream with an already open file descriptor |fd|.
* The |fopen_mode| argument is as decribed above and must be compatible with
* the mode of |fd|. All other arguments, behaviors and return values are as
* those of exfile_fopen (see above). */
-FILE *exfile_fdopen(int fd, const char *fopen_mode, ex_t *ex_arr,
- size_t ex_count, void (*ex_free)(void *));
+FILE* exfile_fdopen(int fd,
+ const char* fopen_mode,
+ ex_t* ex_arr,
+ size_t ex_count,
+ void (*ex_free)(void*));
-#endif /* _BSDIFF_EXFILE_H_ */
+#endif /* _BSDIFF_EXFILE_H_ */
diff --git a/extents.c b/extents.c
index 5f99e85..5718cee 100644
--- a/extents.c
+++ b/extents.c
@@ -17,7 +17,7 @@
/* Minimum/maximum values for arbitrary integer types. */
#define UNSIGNED_INT_MAX(t) (~((t)0))
#define SIGNED_INT_MAX(t) ((t)((uintmax_t)UNSIGNED_INT_MAX(t) >> 1))
-#define MAX(a,b) ((a) > (b) ? (a) : (b))
+#define MAX(a, b) ((a) > (b) ? (a) : (b))
#define INT_TYPE_MAX(t) MAX(UNSIGNED_INT_MAX(t), SIGNED_INT_MAX(t))
/* The maximum accepted value for a given integer type when parsed as a signed
@@ -30,11 +30,11 @@
* still permitting values up to 2^62, which is more than enough for all
* practical purposes. */
#define LLONG_MAX_BOUND(s) \
- ((uintmax_t)(s) < (uintmax_t)LLONG_MAX ? (long long)(s) : LLONG_MAX)
+ ((uintmax_t)(s) < (uintmax_t)LLONG_MAX ? (long long)(s) : LLONG_MAX)
#define MAX_ALLOWED(t) LLONG_MAX_BOUND(INT_TYPE_MAX(t))
/* Get the type of a struct field. */
-#define FIELD_TYPE(t, f) typeof(((t *)0)->f)
+#define FIELD_TYPE(t, f) typeof(((t*)0)->f)
/* Reads a long long integer from |s| into |*val_p|. Returns a pointer to the
@@ -43,22 +43,24 @@
* |min_val| or greater than |max_val|; (c) the delimiter character is not
* |delim|, or the string ends although |may_end| is false. In any of these
* cases, returns NULL. */
-const char *
-read_llong(const char *s, long long *val_p, long long min_val,
- long long max_val, char delim, int may_end)
-{
- assert(val_p);
- const char *next_s;
- errno = 0;
- long long val = strtoll(s, (char **)&next_s, 10);
- if (((val == LLONG_MAX || val == LLONG_MIN) && errno == ERANGE) ||
- next_s == s || val < min_val || val > max_val ||
- (*next_s ? *next_s != delim : !may_end))
- return NULL; /* bad value or delimiter */
- *val_p = val;
- if (*next_s)
- next_s++; /* skip delimeter */
- return next_s;
+const char* read_llong(const char* s,
+ long long* val_p,
+ long long min_val,
+ long long max_val,
+ char delim,
+ int may_end) {
+ assert(val_p);
+ const char* next_s;
+ errno = 0;
+ long long val = strtoll(s, (char**)&next_s, 10);
+ if (((val == LLONG_MAX || val == LLONG_MIN) && errno == ERANGE) ||
+ next_s == s || val < min_val || val > max_val ||
+ (*next_s ? *next_s != delim : !may_end))
+ return NULL; /* bad value or delimiter */
+ *val_p = val;
+ if (*next_s)
+ next_s++; /* skip delimeter */
+ return next_s;
}
@@ -68,63 +70,59 @@ read_llong(const char *s, long long *val_p, long long min_val,
* |ex_count| extents into |ex_arr|, which must be of at least this size.
* Returns the number of correctly parsed extents, or -1 if a malformed extent
* was found. */
-static ssize_t
-extents_read(const char *ex_str, ex_t *ex_arr, size_t ex_count)
-{
- size_t i;
- size_t last_i = ex_count - 1;
- if (!ex_arr) {
- ex_count = SIZE_MAX;
- last_i = 0;
+static ssize_t extents_read(const char* ex_str, ex_t* ex_arr, size_t ex_count) {
+ size_t i;
+ size_t last_i = ex_count - 1;
+ if (!ex_arr) {
+ ex_count = SIZE_MAX;
+ last_i = 0;
+ }
+ for (i = 0; *ex_str && i < ex_count; i++) {
+ long long raw_off = 0, raw_len = 0;
+ if (!((ex_str =
+ read_llong(ex_str, &raw_off, -1,
+ MAX_ALLOWED(FIELD_TYPE(ex_t, off)), ':', FALSE)) &&
+ (ex_str = read_llong(ex_str, &raw_len, 1,
+ MAX_ALLOWED(FIELD_TYPE(ex_t, len)), ',',
+ i >= last_i))))
+ return -1; /* parsing error */
+ if (ex_arr) {
+ ex_arr[i].off = raw_off;
+ ex_arr[i].len = raw_len;
}
- for (i = 0; *ex_str && i < ex_count; i++) {
- long long raw_off = 0, raw_len = 0;
- if (!((ex_str = read_llong(ex_str, &raw_off, -1,
- MAX_ALLOWED(FIELD_TYPE(ex_t, off)),
- ':', FALSE)) &&
- (ex_str = read_llong(ex_str, &raw_len, 1,
- MAX_ALLOWED(FIELD_TYPE(ex_t, len)),
- ',', i >= last_i))))
- return -1; /* parsing error */
- if (ex_arr) {
- ex_arr[i].off = raw_off;
- ex_arr[i].len = raw_len;
- }
- }
- return i;
+ }
+ return i;
}
-ex_t *
-extents_parse(const char *ex_str, ex_t *ex_arr, size_t *ex_count_p)
-{
- /* Sanity checks: a string must be provided; if an array is provided, an
- * array count must be given as well. */
- if (!ex_str || (ex_arr && !ex_count_p))
- return NULL;
-
- /* Parse string and count extents. */
- ssize_t ret = extents_read(ex_str, NULL, 0);
- if (ret < 0)
- return NULL; /* parsing error */
- size_t ex_count = (size_t)ret;
-
- /* Input is good, commit to extent count. */
- if (ex_count_p) {
- size_t alloc_ex_count = *ex_count_p;
- *ex_count_p = ex_count;
- if (ex_arr && alloc_ex_count < ex_count)
- return NULL; /* insufficient allocated space */
- }
- if (ex_count == 0)
- return NULL; /* no extents, nothing to do */
-
- /* Allocate extent array, if needed. */
- if (!(ex_arr || (ex_arr = (ex_t *)malloc(sizeof(ex_t) * ex_count))))
- return NULL; /* allocation failed */
-
- /* Populate the extent array. */
- extents_read(ex_str, ex_arr, ex_count);
-
- return ex_arr;
+ex_t* extents_parse(const char* ex_str, ex_t* ex_arr, size_t* ex_count_p) {
+ /* Sanity checks: a string must be provided; if an array is provided, an
+ * array count must be given as well. */
+ if (!ex_str || (ex_arr && !ex_count_p))
+ return NULL;
+
+ /* Parse string and count extents. */
+ ssize_t ret = extents_read(ex_str, NULL, 0);
+ if (ret < 0)
+ return NULL; /* parsing error */
+ size_t ex_count = (size_t)ret;
+
+ /* Input is good, commit to extent count. */
+ if (ex_count_p) {
+ size_t alloc_ex_count = *ex_count_p;
+ *ex_count_p = ex_count;
+ if (ex_arr && alloc_ex_count < ex_count)
+ return NULL; /* insufficient allocated space */
+ }
+ if (ex_count == 0)
+ return NULL; /* no extents, nothing to do */
+
+ /* Allocate extent array, if needed. */
+ if (!(ex_arr || (ex_arr = (ex_t*)malloc(sizeof(ex_t) * ex_count))))
+ return NULL; /* allocation failed */
+
+ /* Populate the extent array. */
+ extents_read(ex_str, ex_arr, ex_count);
+
+ return ex_arr;
}
diff --git a/extents.h b/extents.h
index f0c795e..d69b65f 100644
--- a/extents.h
+++ b/extents.h
@@ -21,6 +21,6 @@
* NULL but still store the number of parsed extents. Otherwise, returns NULL
* and does not store anything. If a new array was allocated, then it should be
* deallocated with free(3). */
-ex_t *extents_parse(const char *ex_str, ex_t *ex_arr, size_t *ex_count_p);
+ex_t* extents_parse(const char* ex_str, ex_t* ex_arr, size_t* ex_count_p);
-#endif /* _BSDIFF_EXTENTS_H_ */
+#endif /* _BSDIFF_EXTENTS_H_ */
diff --git a/test_utils.cc b/test_utils.cc
index b7540e6..2ad8fc8 100644
--- a/test_utils.cc
+++ b/test_utils.cc
@@ -25,13 +25,12 @@ const string PrependTmpdir(const string& path) {
if (path[0] == '/')
return path;
- const char *tmpdir = getenv("TMPDIR");
+ const char* tmpdir = getenv("TMPDIR");
const string prefix = (tmpdir && *tmpdir ? tmpdir : "/tmp");
return prefix + "/" + path;
}
-bool MakeTempFile(const string& base_filename_template,
- string* filename) {
+bool MakeTempFile(const string& base_filename_template, string* filename) {
const string filename_template = PrependTmpdir(base_filename_template);
vector<char> result(filename_template.size() + 1, '\0');
memcpy(result.data(), filename_template.data(), filename_template.size());
diff --git a/test_utils.h b/test_utils.h
index 52cebab..186d9e6 100644
--- a/test_utils.h
+++ b/test_utils.h
@@ -8,12 +8,12 @@
#include <string>
#include <vector>
-#define TEST_AND_RETURN_FALSE(_x) \
- do { \
- if (!static_cast<bool>(_x)) { \
- fprintf(stderr, "%s failed.", #_x); \
- return false; \
- } \
+#define TEST_AND_RETURN_FALSE(_x) \
+ do { \
+ if (!static_cast<bool>(_x)) { \
+ fprintf(stderr, "%s failed.", #_x); \
+ return false; \
+ } \
} while (0)
namespace test_utils {
diff --git a/testrunner.cc b/testrunner.cc
index 40710fd..44f0b5e 100644
--- a/testrunner.cc
+++ b/testrunner.cc
@@ -4,7 +4,7 @@
#include <gtest/gtest.h>
-int main(int argc, char **argv) {
+int main(int argc, char** argv) {
::testing::InitGoogleTest(&argc, argv);
return RUN_ALL_TESTS();
}