正在进行I/O删除文件:它是文件系统和/或OS功能吗? [英] Deleting a file with I/O in progress: Is it a filesystem and/or an OS feature?

查看:101
本文介绍了正在进行I/O删除文件:它是文件系统和/或OS功能吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个可以在Linux上运行但可以对已安装分区上的文件进行操作的shell脚本,

I'm writing a shell script that will run on Linux but can operate on files sitting on a mounted partition,

  1. 可能有也可能没有ext *文件系统.例如,它可以是NTFS,FAT32或任何基于inode或基于非inode的系统;

  1. that may or may not have an ext* file-system. It could eg be NTFS, FAT32, or any inode- or non-inode-based system;

可能会进一步安装在其他运行非Linux操作系统(例如Windows或Mac)的机器上.

that could get further re-mounted on other boxes running non-Linux OSes like Windows or Mac.

此外,我的脚本需要能够通过在Linux,Windows或Mac机上运行的远程进程删除此共享的,任意格式的分区上的文件(即使正在读取或写入文件时)

Further, my script needs to be able to delete a file on this shared, arbitrarily formatted partition (even while the file's being read from or written to) by a remote process running on Linux, Windows, or Mac boxes

问题:

  1. 能够删除使用中的文件的功能,

  1. Is the ability to be able to delete a file in use a feature of,

a.只有文件系统?

b.还是只有操作系统?

b. or, only the OS?

c.还是两者的结合?

c. or, a combo of both?

(Q1的扩展名)对该文件进行I/O和删除该文件的进程是本地的还是远程的,是否重要?

(Extension of Q1) Does it matter if the processe doing I/O on the file and the one deleting the file are both local or remote?

推荐答案

是否重要的​​是进程是否在文件上执行I/O和 删除文件是本地文件还是远程文件?

Does it matter if the processes doing I/O on the file and the one deleting the file are both local or remote?

有趣的是-远程系统如何在Windows 直接上访问文件(打开,读写数据,删除)?真的,这不可能.我们需要在本地系统中运行的某些代理(LANMan服务器),该代理将通过远程命令(通过

interesting - how remote system can access file (open, read-write data, delete) on windows direct ? really this impossible. we need some agent (LANMan server), running in the local system, which will be by remote commands (send say by Network Redirector) do local operations on file. so from file system view - all operations always local.

使用以下功能可以删除文件

Is the ability to be able to delete a file in use a feature of

这当然是由文件系统驱动程序实现的,但是此驱动程序是为具体的OS编写的,并基于此规则.磁盘上的文件系统数据具有通用格式(因此,驱动器在一个OS中格式化(和写入的文件),可以从另一个OS读取)-文件系统驱动程序如何处理请求,打开,读取,写入,删除文件-这是特定于操作系统.针对不同的操作系统而有所不同.根据它的规则.因此磁盘上的数据格式是常见的,并且仅取决于文件系统.但是如何读取/写入/删除此数据-已经特定于操作系统.

this is implemented of course by file system driver, but this driver written for concrete OS and based on it rules. while file system data on disk is have common format (as result drive formatted(and written files) in one OS, can be read from another OS) - how file system driver process requests, open, read, write, delete files - this is OS specific. different for different OS. based on it rules. so data format on disk is common and only depend from file system. but how this data read/write/delete - already os specific.

在Windows中,我们有删除文件的下一条规则:

in windows we have next rules for delete files:

通常,直到所有 文件的打开句柄已关闭,并且链接计数 文件为零.将文件标记为要删除时 FILE_DISPOSITION_POSIX_SEMANTICS ,该链接已从 POSIX删除句柄关闭后,即可看到可见的名称空间, 但是文件的数据流仍然可以被其他现有用户访问 直到最后一个手柄已关闭.

Normally a file marked for deletion is not actually deleted until all open handles for the file have been closed and the link count for the file is zero. When marking a file for deletion using FILE_DISPOSITION_POSIX_SEMANTICS, the link gets removed from the visible namespace as soon as the POSIX delete handle has been closed, but the file’s data streams remain accessible by other existing handles until the last handle has been closed.

因此,通常不会删除文件,直到关闭文件的最后一个句柄为止.尝试删除文件后无法访问该文件-无法再打开它(我们收到错误已请求对具有待处理删除操作的文件对象执行非关闭操作.如果尝试这样做,则在标记了文件之后删除).但是如果文件已经打开-我们仍然可以通过此句柄使用它.如果文件上存在节,也无法删除文件-错误已尝试删除无法删除的文件或目录.

so in general file will be not deleted, until the last handle to it will be closed. file became not accessible after we try delete it - can not more open it (we get error A non close operation has been requested of a file object with a delete pending. if try do this, after file marked to delete). but if file was already opened - we can still work with it by this handle. also file can not be deleted if section exist on file - will be error An attempt has been made to remove a file or directory that cannot be deleted.

从win10 redstone1版本开始存在FILE_DISPOSITION_POSIX_SEMANTICS标志,当删除句柄关闭时,该标志允许从可见的命名空间中删除文件名,但是在其他文件句柄关闭之前,文件的数据流仍然可被其他现有句柄访问

begin from win10 redstone1 build exist FILE_DISPOSITION_POSIX_SEMANTICS flag which let removed file name from the visible namespace when delete handle has been closed, but the file’s data streams remain accessible by other existing handles until the last handle has been closed

Windows代码测试演示:( ntfs支持的 FILE_DISPOSITION_POSIX_SEMANTICS仅从_WIN32_WINNT_WIN10_RS1开始.FileDispositionInfoEx信息类也仅从_WIN32_WINNT_WIN10_RS1开始.在以前的构建中,我们根本没有实现错误)

windows code test demo: (FILE_DISPOSITION_POSIX_SEMANTICS supported by ntfs begin only from _WIN32_WINNT_WIN10_RS1. FileDispositionInfoEx information class also supported begin from _WIN32_WINNT_WIN10_RS1 only. in previous build we simply got not implemented error)

void print_error(PCSTR name)
{
    PWSTR sz;
    NTSTATUS status = RtlGetLastNtStatus();
    if (FormatMessageW(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_HMODULE, 
        GetModuleHandle(L"ntdll"), status, 0, (PWSTR)&sz, 0, 0))
    {
        DbgPrint("%s=%x\n%S\n", name, status, sz);
        LocalFree(sz);
    }
}

HANDLE OpenFile(PCWSTR lpFileName, DWORD dwDesiredAccess)
{
    HANDLE hFile = CreateFileW(lpFileName, dwDesiredAccess, FILE_SHARE_VALID_FLAGS, 0, OPEN_EXISTING, 0, 0);

    if (hFile == INVALID_HANDLE_VALUE)
    {
        print_error("OpenFile");
        return 0;
    }

    return hFile;
}

void ReadTest(HANDLE hFile)
{
    if (hFile)
    {
        ULONG dwBytes;
        if (ReadFile(hFile, &dwBytes, sizeof(dwBytes), &dwBytes, 0))
        {
            DbgPrint("ReadFile=OK\n");
        }
        else
        {
            print_error("ReadFile");
        }
    }
}

void DeleteTest(PCWSTR lpFileName)
{
    HANDLE hFile1, hFile2, hFile3;

    if (hFile1 = OpenFile(lpFileName, DELETE))
    {
        hFile2 = OpenFile(lpFileName, FILE_GENERIC_READ);

        FILE_DISPOSITION_INFO_EX fdi = { FILE_DISPOSITION_DELETE | FILE_DISPOSITION_POSIX_SEMANTICS };
        if (!SetFileInformationByHandle(hFile1, FileDispositionInfoEx, &fdi, sizeof(fdi)))
        {
            print_error("SetFileInformationByHandle");
        }

        // file already not accessible here (open must fail) but visible
        if (hFile3 = OpenFile(lpFileName, FILE_GENERIC_READ))
        {
            CloseHandle(hFile3);
        }

        ReadTest(hFile2);

        // win10 rs1: file removed from the visible namespace here
        CloseHandle(hFile1);

        // are file still visible ?
        if (hFile3 = OpenFile(lpFileName, FILE_GENERIC_READ))
        {
            CloseHandle(hFile3);
        }

        // are possible create new file with this name &
        hFile3 = CreateFileW(lpFileName, DELETE, 
            FILE_SHARE_VALID_FLAGS, 0, CREATE_NEW, FILE_FLAG_DELETE_ON_CLOSE, 0);
        if (hFile3 == INVALID_HANDLE_VALUE)
        {
            print_error("CreateFile");
        }
        else
        {
            CloseHandle(hFile3);
            DbgPrint("CreateFile OK\n");
        }

        ReadTest(hFile2);

        if (hFile2)
        {
            CloseHandle(hFile2);
        }
    }
}

并输出

OpenFile=c0000056
A non close operation has been requested of a file object with a delete pending.

ReadFile=OK
OpenFile=c0000034
Object Name not found.

CreateFile OK
ReadFile=OK

这篇关于正在进行I/O删除文件:它是文件系统和/或OS功能吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆