summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJunio C Hamano <gitster@pobox.com>2017-02-02 21:36:55 (GMT)
committerJunio C Hamano <gitster@pobox.com>2017-02-02 21:36:56 (GMT)
commitce050477fbb58d02b83830597be1e87c15553071 (patch)
tree5a9798ba47714c9eb972f405a8816168f1d672e4
parenta482cf446f2ced7fdd67faa2b3a55bfd5caf7d58 (diff)
parentc755015f79ac03bb5afa0754c30e937887fc68ab (diff)
downloadgit-ce050477fbb58d02b83830597be1e87c15553071.zip
git-ce050477fbb58d02b83830597be1e87c15553071.tar.gz
git-ce050477fbb58d02b83830597be1e87c15553071.tar.bz2
Merge branch 'hv/mingw-help-is-executable'
"git help" enumerates executable files in $PATH; the implementation of "is this file executable?" on Windows has been optimized. * hv/mingw-help-is-executable: help: improve is_executable() on Windows
-rw-r--r--help.c21
1 files changed, 18 insertions, 3 deletions
diff --git a/help.c b/help.c
index 53e2a67..bc6cd19 100644
--- a/help.c
+++ b/help.c
@@ -105,7 +105,22 @@ static int is_executable(const char *name)
return 0;
#if defined(GIT_WINDOWS_NATIVE)
-{ /* cannot trust the executable bit, peek into the file instead */
+ /*
+ * On Windows there is no executable bit. The file extension
+ * indicates whether it can be run as an executable, and Git
+ * has special-handling to detect scripts and launch them
+ * through the indicated script interpreter. We test for the
+ * file extension first because virus scanners may make
+ * it quite expensive to open many files.
+ */
+ if (ends_with(name, ".exe"))
+ return S_IXUSR;
+
+{
+ /*
+ * Now that we know it does not have an executable extension,
+ * peek into the file instead.
+ */
char buf[3] = { 0 };
int n;
int fd = open(name, O_RDONLY);
@@ -113,8 +128,8 @@ static int is_executable(const char *name)
if (fd >= 0) {
n = read(fd, buf, 2);
if (n == 2)
- /* DOS executables start with "MZ" */
- if (!strcmp(buf, "#!") || !strcmp(buf, "MZ"))
+ /* look for a she-bang */
+ if (!strcmp(buf, "#!"))
st.st_mode |= S_IXUSR;
close(fd);
}