aboutsummaryrefslogtreecommitdiff
path: root/builtin
diff options
context:
space:
mode:
authorJeff King <peff@peff.net>2017-09-27 02:02:27 -0400
committerJunio C Hamano <gitster@pobox.com>2017-09-27 15:46:05 +0900
commit8a1a8d2ad1b41a0a28d37d1d21ee9620a23e91eb (patch)
tree28698b53f71c3eb11b85d795d071759138e2b8db /builtin
parent228740b67b55f4ee23637bd1472a73ae50efe93a (diff)
downloadgit-8a1a8d2ad1b41a0a28d37d1d21ee9620a23e91eb.tar.gz
git-8a1a8d2ad1b41a0a28d37d1d21ee9620a23e91eb.tar.xz
worktree: check the result of read_in_full()
We try to read "len" bytes into a buffer and just assume that it happened correctly. In practice this should usually be the case, since we just stat'd the file to get the length. But we could be fooled by transient errors or by other processes racily truncating the file. Let's be more careful. There's a slim chance this could catch a real error, but it also prevents people and tools from getting worried while reading the code. Signed-off-by: Jeff King <peff@peff.net> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Diffstat (limited to 'builtin')
-rw-r--r--builtin/worktree.c19
1 files changed, 18 insertions, 1 deletions
diff --git a/builtin/worktree.c b/builtin/worktree.c
index 2f4a4ef9c..7b9307aa5 100644
--- a/builtin/worktree.c
+++ b/builtin/worktree.c
@@ -40,6 +40,7 @@ static int prune_worktree(const char *id, struct strbuf *reason)
char *path;
int fd;
size_t len;
+ ssize_t read_result;
if (!is_directory(git_path("worktrees/%s", id))) {
strbuf_addf(reason, _("Removing worktrees/%s: not a valid directory"), id);
@@ -59,8 +60,24 @@ static int prune_worktree(const char *id, struct strbuf *reason)
}
len = xsize_t(st.st_size);
path = xmallocz(len);
- read_in_full(fd, path, len);
+
+ read_result = read_in_full(fd, path, len);
+ if (read_result < 0) {
+ strbuf_addf(reason, _("Removing worktrees/%s: unable to read gitdir file (%s)"),
+ id, strerror(errno));
+ close(fd);
+ free(path);
+ return 1;
+ }
close(fd);
+
+ if (read_result != len) {
+ strbuf_addf(reason,
+ _("Removing worktrees/%s: short read (expected %"PRIuMAX" bytes, read %"PRIuMAX")"),
+ id, (uintmax_t)len, (uintmax_t)read_result);
+ free(path);
+ return 1;
+ }
while (len && (path[len - 1] == '\n' || path[len - 1] == '\r'))
len--;
if (!len) {