diff options
author | Linus Torvalds <torvalds@g5.osdl.org> | 2005-07-03 10:40:38 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@g5.osdl.org> | 2005-07-03 10:40:38 -0700 |
commit | c33303839c76c41c9f85e5bd3f7b04fab60c38ca (patch) | |
tree | 38f671a7da0a9bd9886f437ef45fe269ee7767b4 /fsck-cache.c | |
parent | 6da4016aea2dc5bf311fea160bd8ef96ca82b999 (diff) | |
download | git-c33303839c76c41c9f85e5bd3f7b04fab60c38ca.tar.gz git-c33303839c76c41c9f85e5bd3f7b04fab60c38ca.tar.xz |
Make git-fsck-cache check HEAD integrity
In particular, check that it's a symlink, and points to refs/heads/. We
depend on that these days not only for "git checkout", but also because
fsck and others only check for references in the .git/refs/
subdirectory, not things like HEAD itself.
Diffstat (limited to 'fsck-cache.c')
-rw-r--r-- | fsck-cache.c | 26 |
1 files changed, 26 insertions, 0 deletions
diff --git a/fsck-cache.c b/fsck-cache.c index 9867fa658..e42264e6c 100644 --- a/fsck-cache.c +++ b/fsck-cache.c @@ -342,6 +342,31 @@ static void fsck_object_dir(const char *path) fsck_sha1_list(); } +static int fsck_head_link(void) +{ + int fd, count; + char hex[40]; + unsigned char sha1[20]; + static char path[PATH_MAX], link[PATH_MAX]; + const char *git_dir = gitenv(GIT_DIR_ENVIRONMENT) ? : DEFAULT_GIT_DIR_ENVIRONMENT; + + snprintf(path, sizeof(path), "%s/HEAD", git_dir); + if (readlink(path, link, sizeof(link)) < 0) + return error("HEAD is not a symlink"); + if (strncmp("refs/heads/", link, 11)) + return error("HEAD points to something strange (%s)", link); + fd = open(path, O_RDONLY); + if (fd < 0) + return error("HEAD: %s", strerror(errno)); + count = read(fd, hex, sizeof(hex)); + close(fd); + if (count < 0) + return error("HEAD: %s", strerror(errno)); + if (count < 40 || get_sha1_hex(hex, sha1)) + return error("HEAD: not a valid git pointer"); + return 0; +} + int main(int argc, char **argv) { int i, heads; @@ -382,6 +407,7 @@ int main(int argc, char **argv) if (standalone) unsetenv("GIT_ALTERNATE_OBJECT_DIRECTORIES"); + fsck_head_link(); fsck_object_dir(get_object_directory()); if (check_full) { int j; |