summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--compat/mingw.c23
-rwxr-xr-xt/t7063-status-untracked-cache.sh21
2 files changed, 28 insertions, 16 deletions
diff --git a/compat/mingw.c b/compat/mingw.c
index 03af369b2b..58f347d6ae 100644
--- a/compat/mingw.c
+++ b/compat/mingw.c
@@ -961,9 +961,11 @@ static inline void time_t_to_filetime(time_t t, FILETIME *ft)
int mingw_utime (const char *file_name, const struct utimbuf *times)
{
FILETIME mft, aft;
- int fh, rc;
+ int rc;
DWORD attrs;
wchar_t wfilename[MAX_PATH];
+ HANDLE osfilehandle;
+
if (xutftowcs_path(wfilename, file_name) < 0)
return -1;
@@ -975,7 +977,17 @@ int mingw_utime (const char *file_name, const struct utimbuf *times)
SetFileAttributesW(wfilename, attrs & ~FILE_ATTRIBUTE_READONLY);
}
- if ((fh = _wopen(wfilename, O_RDWR | O_BINARY)) < 0) {
+ osfilehandle = CreateFileW(wfilename,
+ FILE_WRITE_ATTRIBUTES,
+ 0 /*FileShare.None*/,
+ NULL,
+ OPEN_EXISTING,
+ (attrs != INVALID_FILE_ATTRIBUTES &&
+ (attrs & FILE_ATTRIBUTE_DIRECTORY)) ?
+ FILE_FLAG_BACKUP_SEMANTICS : 0,
+ NULL);
+ if (osfilehandle == INVALID_HANDLE_VALUE) {
+ errno = err_win_to_posix(GetLastError());
rc = -1;
goto revert_attrs;
}
@@ -987,12 +999,15 @@ int mingw_utime (const char *file_name, const struct utimbuf *times)
GetSystemTimeAsFileTime(&mft);
aft = mft;
}
- if (!SetFileTime((HANDLE)_get_osfhandle(fh), NULL, &aft, &mft)) {
+
+ if (!SetFileTime(osfilehandle, NULL, &aft, &mft)) {
errno = EINVAL;
rc = -1;
} else
rc = 0;
- close(fh);
+
+ if (osfilehandle != INVALID_HANDLE_VALUE)
+ CloseHandle(osfilehandle);
revert_attrs:
if (attrs != INVALID_FILE_ATTRIBUTES &&
diff --git a/t/t7063-status-untracked-cache.sh b/t/t7063-status-untracked-cache.sh
index a0c123b0a7..ca90ee805e 100755
--- a/t/t7063-status-untracked-cache.sh
+++ b/t/t7063-status-untracked-cache.sh
@@ -90,6 +90,9 @@ test_expect_success 'setup' '
cd worktree &&
mkdir done dtwo dthree &&
touch one two three done/one dtwo/two dthree/three &&
+ test-tool chmtime =-300 one two three done/one dtwo/two dthree/three &&
+ test-tool chmtime =-300 done dtwo dthree &&
+ test-tool chmtime =-300 . &&
git add one two done/one &&
: >.git/info/exclude &&
git update-index --untracked-cache &&
@@ -142,7 +145,6 @@ two
EOF
test_expect_success 'status first time (empty cache)' '
- avoid_racy &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../actual &&
@@ -166,7 +168,6 @@ test_expect_success 'untracked cache after first status' '
'
test_expect_success 'status second time (fully populated cache)' '
- avoid_racy &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../actual &&
@@ -190,8 +191,8 @@ test_expect_success 'untracked cache after second status' '
'
test_expect_success 'modify in root directory, one dir invalidation' '
- avoid_racy &&
: >four &&
+ test-tool chmtime =-240 four &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../actual &&
@@ -241,7 +242,6 @@ EOF
'
test_expect_success 'new .gitignore invalidates recursively' '
- avoid_racy &&
echo four >.gitignore &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
@@ -292,7 +292,6 @@ EOF
'
test_expect_success 'new info/exclude invalidates everything' '
- avoid_racy &&
echo three >>.git/info/exclude &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
@@ -520,14 +519,14 @@ test_expect_success 'create/modify files, some of which are gitignored' '
echo three >done/three && # three is gitignored
echo four >done/four && # four is gitignored at a higher level
echo five >done/five && # five is not gitignored
- echo test >base && #we need to ensure that the root dir is touched
- rm base &&
+ test-tool chmtime =-180 done/two done/three done/four done/five done &&
+ # we need to ensure that the root dir is touched (in the past);
+ test-tool chmtime =-180 . &&
sync_mtime
'
test_expect_success 'test sparse status with untracked cache' '
: >../trace.output &&
- avoid_racy &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../status.actual &&
iuc status --porcelain >../status.iuc &&
@@ -570,7 +569,6 @@ EOF
'
test_expect_success 'test sparse status again with untracked cache' '
- avoid_racy &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../status.actual &&
@@ -597,11 +595,11 @@ EOF
test_expect_success 'set up for test of subdir and sparse checkouts' '
mkdir done/sub &&
mkdir done/sub/sub &&
- echo "sub" > done/sub/sub/file
+ echo "sub" > done/sub/sub/file &&
+ test-tool chmtime =-120 done/sub/sub/file done/sub/sub done/sub done
'
test_expect_success 'test sparse status with untracked cache and subdir' '
- avoid_racy &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../status.actual &&
@@ -651,7 +649,6 @@ EOF
'
test_expect_success 'test sparse status again with untracked cache and subdir' '
- avoid_racy &&
: >../trace.output &&
GIT_TRACE2_PERF="$TRASH_DIRECTORY/trace.output" \
git status --porcelain >../status.actual &&