From: Francis De Brabandere <francisdb@gmail.com> Wrap DeleteFileW, honouring the Force flag by clearing the readonly attribute before retrying. --- dlls/scrrun/filesystem.c | 13 ++++++-- dlls/scrrun/tests/filesystem.c | 60 ++++++++++++++++++++++++++++++++++ 2 files changed, 71 insertions(+), 2 deletions(-) diff --git a/dlls/scrrun/filesystem.c b/dlls/scrrun/filesystem.c index af76f0cf4d8..1fb4c502297 100644 --- a/dlls/scrrun/filesystem.c +++ b/dlls/scrrun/filesystem.c @@ -3143,8 +3143,17 @@ static HRESULT WINAPI file_get_Type(IFile *iface, BSTR *pbstrType) static HRESULT WINAPI file_Delete(IFile *iface, VARIANT_BOOL Force) { struct file *This = impl_from_IFile(iface); - FIXME("(%p)->(%x)\n", This, Force); - return E_NOTIMPL; + + TRACE("(%p)->(%x)\n", This, Force); + + if (!DeleteFileW(This->path)) + { + if (!Force || !SetFileAttributesW(This->path, FILE_ATTRIBUTE_NORMAL) + || !DeleteFileW(This->path)) + return create_error(GetLastError()); + } + + return S_OK; } static HRESULT WINAPI file_Copy(IFile *iface, BSTR Destination, VARIANT_BOOL OverWriteFiles) diff --git a/dlls/scrrun/tests/filesystem.c b/dlls/scrrun/tests/filesystem.c index 9b5abdf5c97..6443cc4ecab 100644 --- a/dlls/scrrun/tests/filesystem.c +++ b/dlls/scrrun/tests/filesystem.c @@ -3135,6 +3135,65 @@ static void test_DoOpenPipeStream(void) ITextStream_Release(stream_write); } +static void test_File_Delete(void) +{ + WCHAR pathW[MAX_PATH]; + IFile *file; + BSTR path; + HRESULT hr; + HANDLE hf; + DWORD attrs; + + get_temp_path(NULL, pathW); + hf = CreateFileW(pathW, GENERIC_WRITE, 0, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL); + if (hf == INVALID_HANDLE_VALUE) + { + skip("Can't create temporary file\n"); + return; + } + CloseHandle(hf); + + path = SysAllocString(pathW); + hr = IFileSystem3_GetFile(fs3, path, &file); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IFile_Delete(file, VARIANT_FALSE); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + attrs = GetFileAttributesW(pathW); + ok(attrs == INVALID_FILE_ATTRIBUTES, "expected file to be deleted\n"); + + IFile_Release(file); + SysFreeString(path); + + hf = CreateFileW(pathW, GENERIC_WRITE, 0, NULL, CREATE_NEW, FILE_ATTRIBUTE_READONLY, NULL); + if (hf == INVALID_HANDLE_VALUE) + { + skip("Can't create temporary readonly file\n"); + return; + } + CloseHandle(hf); + + path = SysAllocString(pathW); + hr = IFileSystem3_GetFile(fs3, path, &file); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + hr = IFile_Delete(file, VARIANT_FALSE); + ok(hr == CTL_E_PERMISSIONDENIED, "Unexpected hr %#lx.\n", hr); + + attrs = GetFileAttributesW(pathW); + ok(attrs != INVALID_FILE_ATTRIBUTES, "file should still exist\n"); + + hr = IFile_Delete(file, VARIANT_TRUE); + ok(hr == S_OK, "Unexpected hr %#lx.\n", hr); + + attrs = GetFileAttributesW(pathW); + ok(attrs == INVALID_FILE_ATTRIBUTES, "expected file to be deleted\n"); + + IFile_Release(file); + SysFreeString(path); +} + START_TEST(filesystem) { HRESULT hr; @@ -3184,6 +3243,7 @@ START_TEST(filesystem) test_GetSpecialFolder(); test_MoveFile(); test_MoveFolder(); + test_File_Delete(); test_DoOpenPipeStream(); IFileSystem3_Release(fs3); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/10680