peass-ng/PEASS-ng · error · DirectoryNotEmptyException
ERROR_DIR_NOT_EMPTY
ERROR_DIR_NOT_EMPTY
Error message
({145}) The directory is not empty: [{pathLp}] What it means
DeleteDirectoryNative throws DirectoryNotEmptyException (Win32 error 145, ERROR_DIR_NOT_EMPTY) when the native RemoveDirectory call fails because the directory still contains entries. This surfaces from Directory.Delete when recursive=false (or recursion failed to empty it), since non-recursive deletion only works on empty directories. It wraps the OS error with the offending path in the message.
Source
Thrown at winPEAS/winPEASexe/winPEAS/3rdParty/AlphaFS/Filesystem/Directory Class/Directory Core Methods/Directory.DeleteDirectoryNative.cs:58
// RemoveDirectory() / RemoveDirectoryTransacted()
// 2014-09-09: MSDN confirms LongPath usage.
// RemoveDirectory on a symbolic link will remove the link itself.
? NativeMethods.RemoveDirectory(pathLp)
: NativeMethods.RemoveDirectoryTransacted(pathLp, transaction.SafeHandle);
var lastError = Marshal.GetLastWin32Error();
if (!success)
{
switch ((uint) lastError)
{
case Win32Errors.ERROR_DIR_NOT_EMPTY:
// MSDN: .NET 3.5+: IOException: The directory specified by path is not an empty directory.
throw new DirectoryNotEmptyException(pathLp, true);
case Win32Errors.ERROR_DIRECTORY:
// MSDN: .NET 3.5+: DirectoryNotFoundException: Path refers to a file instead of a directory.
if (File.ExistsCore(transaction, false, pathLp, PathFormat.LongFullPath))
throw new DirectoryNotFoundException(string.Format(CultureInfo.InvariantCulture, "({0}) {1}", lastError, string.Format(CultureInfo.InvariantCulture, Resources.Target_Directory_Is_A_File, pathLp)));
break;
case Win32Errors.ERROR_PATH_NOT_FOUND:
if (continueOnNotFound)
return;
break;
case Win32Errors.ERROR_SHARING_VIOLATION:
// MSDN: .NET 3.5+: IOException: The directory is being used by another process or there is an open handle on the directory.
NativeError.ThrowException(lastError, pathLp);View on GitHub (pinned to 53fb989abc)
Solutions
- Call Directory.Delete(path, true) with recursive:true to remove contents first.
- Enumerate and delete contents explicitly, then delete the now-empty directory.
- Retry after ensuring no other process is writing into the directory (close handles/stop services).
- Catch DirectoryNotEmptyException and decide per-path whether to force-delete or skip.
Example fix
// before Directory.Delete(tempDir); // fails: not empty // after Directory.Delete(tempDir, true); // recursive delete
Defensive patterns
Strategy: try-catch
Validate before calling
if (Directory.EnumerateFileSystemEntries(path).Any())
Directory.Delete(path, true); // recursive for non-empty
else
Directory.Delete(path, false); Try / catch
try { Directory.Delete(path, false); }
catch (DirectoryNotEmptyException) { Directory.Delete(path, true); } Prevention
- Default to recursive:true unless you truly require empty-only deletes
- Check for hidden/system files that make folders look empty
- Account for concurrent writers when assuming a directory is empty
- Use the recursive overload consistently in cleanup code
When it happens
Trigger: Calling Directory.Delete(path) or Delete(path, recursive:false) on a directory containing files/subdirectories; DeleteDirectoryCore invoked from DeleteEmptySubdirectoriesCore or junction teardown on a folder that gained new entries between emptiness checks and deletion; hidden/system files present that made the folder appear empty.
Common situations: Deleting a temp/cache folder that an application is still writing to; race condition where another process created a file after the caller verified the directory was empty; passing recursive:false by default overload while assuming recursive behavior like Directory.Delete(path, true).
Related errors
- ERROR_DIR_NOT_EMPTY
- ({0}) The target directory is a file, not a directory: [{1}]
- ERROR_FILE_READ_ONLY
- ERROR_ALREADY_EXISTS
- The target directory is a file, not a directory: [{0}]
AI-assisted analysis of peass-ng/PEASS-ng@53fb989abc (2026-09-02).
Data as JSON: /api/errors/2654993be4ac66d7.
Report an issue: GitHub.