forked from aniani/vim
patch 8.0.1708: mkdir with 'p' flag fails on existing directory
Problem: Mkdir with 'p' flag fails on existing directory, which is
different from the mkdir shell command.
Solution: Don't fail if the directory already exists. (James McCoy,
closes #2775)
This commit is contained in:
@@ -6138,6 +6138,8 @@ mkdir({name} [, {path} [, {prot}]])
|
|||||||
Example: >
|
Example: >
|
||||||
:call mkdir($HOME . "/tmp/foo/bar", "p", 0700)
|
:call mkdir($HOME . "/tmp/foo/bar", "p", 0700)
|
||||||
< This function is not available in the |sandbox|.
|
< This function is not available in the |sandbox|.
|
||||||
|
There is no error if the directory already exists and the "p"
|
||||||
|
flag is passed (since patch 8.0.1708).
|
||||||
Not available on all systems. To check use: >
|
Not available on all systems. To check use: >
|
||||||
:if exists("*mkdir")
|
:if exists("*mkdir")
|
||||||
<
|
<
|
||||||
|
|||||||
@@ -8057,9 +8057,8 @@ f_mkdir(typval_T *argvars, typval_T *rettv)
|
|||||||
|
|
||||||
dir = get_tv_string_buf(&argvars[0], buf);
|
dir = get_tv_string_buf(&argvars[0], buf);
|
||||||
if (*dir == NUL)
|
if (*dir == NUL)
|
||||||
rettv->vval.v_number = FAIL;
|
return;
|
||||||
else
|
|
||||||
{
|
|
||||||
if (*gettail(dir) == NUL)
|
if (*gettail(dir) == NUL)
|
||||||
/* remove trailing slashes */
|
/* remove trailing slashes */
|
||||||
*gettail_sep(dir) = NUL;
|
*gettail_sep(dir) = NUL;
|
||||||
@@ -8067,12 +8066,23 @@ f_mkdir(typval_T *argvars, typval_T *rettv)
|
|||||||
if (argvars[1].v_type != VAR_UNKNOWN)
|
if (argvars[1].v_type != VAR_UNKNOWN)
|
||||||
{
|
{
|
||||||
if (argvars[2].v_type != VAR_UNKNOWN)
|
if (argvars[2].v_type != VAR_UNKNOWN)
|
||||||
|
{
|
||||||
prot = (int)get_tv_number_chk(&argvars[2], NULL);
|
prot = (int)get_tv_number_chk(&argvars[2], NULL);
|
||||||
if (prot != -1 && STRCMP(get_tv_string(&argvars[1]), "p") == 0)
|
if (prot == -1)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (STRCMP(get_tv_string(&argvars[1]), "p") == 0)
|
||||||
|
{
|
||||||
|
if (mch_isdir(dir))
|
||||||
|
{
|
||||||
|
/* With the "p" flag it's OK if the dir already exists. */
|
||||||
|
rettv->vval.v_number = OK;
|
||||||
|
return;
|
||||||
|
}
|
||||||
mkdir_recurse(dir, prot);
|
mkdir_recurse(dir, prot);
|
||||||
}
|
}
|
||||||
rettv->vval.v_number = prot == -1 ? FAIL : vim_mkdir_emsg(dir, prot);
|
|
||||||
}
|
}
|
||||||
|
rettv->vval.v_number = vim_mkdir_emsg(dir, prot);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|||||||
@@ -25,3 +25,20 @@ func Test_nocatch_restore_silent_emsg()
|
|||||||
let c5 = nr2char(screenchar(&lines, 5))
|
let c5 = nr2char(screenchar(&lines, 5))
|
||||||
call assert_equal('wrong', c1 . c2 . c3 . c4 . c5)
|
call assert_equal('wrong', c1 . c2 . c3 . c4 . c5)
|
||||||
endfunc
|
endfunc
|
||||||
|
|
||||||
|
func Test_mkdir_p()
|
||||||
|
call mkdir('Xmkdir/nested', 'p')
|
||||||
|
call assert_true(isdirectory('Xmkdir/nested'))
|
||||||
|
try
|
||||||
|
" Trying to make existing directories doesn't error
|
||||||
|
call mkdir('Xmkdir', 'p')
|
||||||
|
call mkdir('Xmkdir/nested', 'p')
|
||||||
|
catch /E739:/
|
||||||
|
call assert_report('mkdir(..., "p") failed for an existing directory')
|
||||||
|
endtry
|
||||||
|
" 'p' doesn't suppress real errors
|
||||||
|
call writefile([], 'Xfile')
|
||||||
|
call assert_fails('call mkdir("Xfile", "p")', 'E739')
|
||||||
|
call delete('Xfile')
|
||||||
|
call delete('Xmkdir', 'rf')
|
||||||
|
endfunc
|
||||||
|
|||||||
@@ -762,6 +762,8 @@ static char *(features[]) =
|
|||||||
|
|
||||||
static int included_patches[] =
|
static int included_patches[] =
|
||||||
{ /* Add new patch number below this line */
|
{ /* Add new patch number below this line */
|
||||||
|
/**/
|
||||||
|
1708,
|
||||||
/**/
|
/**/
|
||||||
1707,
|
1707,
|
||||||
/**/
|
/**/
|
||||||
|
|||||||
Reference in New Issue
Block a user