]> granicus.if.org Git - vim/commitdiff
patch 8.1.1473: new resolve() implementation causes problem for plugins v8.1.1473
authorBram Moolenaar <Bram@vim.org>
Thu, 6 Jun 2019 10:22:41 +0000 (12:22 +0200)
committerBram Moolenaar <Bram@vim.org>
Thu, 6 Jun 2019 10:22:41 +0000 (12:22 +0200)
Problem:    New resolve() implementation causes problem for plugins.
Solution:   Only resolve a resparse point after checking it is needed. (Ken
            Takata, closes #4492)

src/os_mswin.c
src/testdir/test_functions.vim
src/version.c

index 2b878f77cf6a3bccadbe7b56b71033c683e02d72..ced065b0d3175b5dd876e7a3773eae63edf4cdfe 100644 (file)
@@ -1753,6 +1753,39 @@ typedef BOOL (WINAPI *pfnGetVolumeInformationByHandleW)(
        DWORD   nFileSystemNameSize);
 static pfnGetVolumeInformationByHandleW pGetVolumeInformationByHandleW = NULL;
 
+# define is_path_sep(c)            ((c) == L'\\' || (c) == L'/')
+
+    static int
+is_reparse_point_included(LPCWSTR fname)
+{
+    LPCWSTR    p = fname, q;
+    WCHAR      buf[MAX_PATH];
+    DWORD      attr;
+
+    if (isalpha(p[0]) && p[1] == L':' && is_path_sep(p[2]))
+       p += 3;
+    else if (is_path_sep(p[0]) && is_path_sep(p[1]))
+       p += 2;
+
+    while (*p != L'\0')
+    {
+       q = wcspbrk(p, L"\\/");
+       if (q == NULL)
+           p = q = fname + wcslen(fname);
+       else
+           p = q + 1;
+       if (q - fname >= MAX_PATH)
+           return FALSE;
+       wcsncpy(buf, fname, q - fname);
+       buf[q - fname] = L'\0';
+       attr = GetFileAttributesW(buf);
+       if (attr != INVALID_FILE_ATTRIBUTES
+               && (attr & FILE_ATTRIBUTE_REPARSE_POINT) != 0)
+           return TRUE;
+    }
+    return FALSE;
+}
+
     static char_u *
 resolve_reparse_point(char_u *fname)
 {
@@ -1787,6 +1820,12 @@ resolve_reparse_point(char_u *fname)
     if (p == NULL)
        goto fail;
 
+    if (!is_reparse_point_included(p))
+    {
+       vim_free(p);
+       goto fail;
+    }
+
     h = CreateFileW(p, 0, 0, NULL, OPEN_EXISTING,
            FILE_FLAG_BACKUP_SEMANTICS, NULL);
     vim_free(p);
index cc1ee8b6138c747c09d3bf1de3d365b807b9d55b..a2e4da6c76237568f48eaaadfdbe823800dbb540 100644 (file)
@@ -276,6 +276,7 @@ func Test_resolve_win32()
   " test for symbolic link to a file
   new Xfile
   wq
+  call assert_equal('Xfile', resolve('Xfile'))
   silent !mklink Xlink Xfile
   if !v:shell_error
     call assert_equal(s:normalize_fname(getcwd() . '\Xfile'), s:normalize_fname(resolve('./Xlink')))
@@ -333,11 +334,14 @@ func Test_resolve_win32()
 
   " test for reparse point
   call mkdir('Xdir')
+  call assert_equal('Xdir', resolve('Xdir'))
   silent !mklink /D Xdirlink Xdir
   if !v:shell_error
     w Xdir/text.txt
+    call assert_equal('Xdir/text.txt', resolve('Xdir/text.txt'))
     call assert_equal(s:normalize_fname(getcwd() . '\Xdir\text.txt'), s:normalize_fname(resolve('Xdirlink\text.txt')))
     call assert_equal(s:normalize_fname(getcwd() . '\Xdir'), s:normalize_fname(resolve('Xdirlink')))
+    call delete('Xdirlink')
   else
     echomsg 'skipped test for reparse point'
   endif
index ca2e17498e8a1c7cb880a9cb4bc6d61ef7455479..cd138ab9c3a312d2470fac0264bdea0597e3370e 100644 (file)
@@ -767,6 +767,8 @@ static char *(features[]) =
 
 static int included_patches[] =
 {   /* Add new patch number below this line */
+/**/
+    1473,
 /**/
     1472,
 /**/