首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用MoveFileEx、CreateDirectoryEx、Get/SetNamedSecurityInfo时ACL/ ACEs是否会中断?

使用MoveFileEx、CreateDirectoryEx、Get/SetNamedSecurityInfo时ACL/ ACEs是否会中断?
EN

Stack Overflow用户
提问于 2017-11-07 17:44:06
回答 1查看 349关注 0票数 0

我正在归档文件,并希望在使用winapi将文件转移到不同卷时,在文件夹上保留相同的/网络共享。

对于文件,我使用MoveFileEx,对于目录,我使用CreateDirectoryEx和sourceDir作为模板,然后获取/SetNamedSecurityInfo,并将所有条目复制到存档版本中。

是否保留具有完全功能继承的相同权限?或者因为我在不同的卷之间移动,可能会出现中断的ACL(破碎的继承)吗?

本文https://blog.varonis.com/fix-windows-permissions-by-brian-vecci/ (很老)指出,这种情况可能会发生:

ACL的破裂可能有几个原因。已知有些自动复制程序会产生意想不到的结果。本土脚本也可以产生这些问题。当某人使用不同的权限将文件或文件夹从卷上的一个文件夹移动到同一卷上的另一个文件夹时,可能会导致另一个不一致。当一个文件或文件夹被移动到卷内时,它实际上只是在文件分配表中被重命名,并且它的权限不会改变。当文件或文件夹在卷间移动(从一个卷移到另一个卷)时,它继承新父卷的权限。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2017-11-12 09:47:04

您可以尝试使用正式/正常的方式(您已经提到了Get/SetNamedSecurityInfo)。但是,还有其他选项可以对安全描述符进行真正的1:1传输。

选项1

使用CreateFile函数和FILE_FLAG_BACKUP_SEMANTICSdwFlagsAndAttributes打开文件

https://msdn.microsoft.com/en-us/library/windows/desktop/aa363858.aspx

使用BackupReadBackupWrite调用来传输数据:

https://msdn.microsoft.com/en-us/library/windows/desktop/aa362509.aspx https://msdn.microsoft.com/en-us/library/windows/desktop/aa362511.aspx

这两个函数不仅复制正常数据,而且还复制安全描述符和NTFS备用数据流(如果存在的话)。您甚至可以使用它们复制类似于文件的目录。另见此文如下:

Windows BackupRead / BackupWrite and ACLs

不要忘记启用特权SE_BACKUP_NAME和SE_RESTORE_NAME

选项2

类似于选项1,但不使用BackupReadBackupWrite,而是以正常的方式复制文件数据。

然后:使用GetKernelObjectSecurity / SetKernelObjectSecurity读写安全描述符:

https://msdn.microsoft.com/en-us/library/aa446641.aspx

https://msdn.microsoft.com/en-us/library/aa379578.aspx

请看最后一段中的https://msdn.microsoft.com/en-us/library/aa364399.aspx,以获得解释。

重要注意事项:用于SetKernelObjectSecurity的文档包含警告,即此函数不应用于设置文件系统中的权限。

背景:

主要是因为继承..。

Microsoft仅将继承特性作为伪继承实现。每个对象(文件、目录)仍然包含所有相关的访问控制条目(ACE)。但是,如果这些标记是从父级继承的,则其中包含一个标志。在本例中,Windows资源管理器中的ACL编辑器将它们显示为灰色。

如果您使用SetNamedSecurityInfo设置一个目录的ACL,其中有一些标记为继承的ACEs,并且这个目录包含100000个子目录和文件,而且没有一个子目录阻止继承,那么这将自动导致设置所有这100000个对象的安全描述符。

系统DLL NTMARTA.DLL负责这种“递归”。如果这些子对象的所有ACL都被正确设置(从ACE顺序、继承标志.)这基本上是件好事,因为操作系统为您处理这个问题。

但是,如果某些对象的ACL有错误的条目,这可能会导致更多的损害。

现在,如果您使用SetKernelObjectSecurity,您必须处理通常由NTMARTA.DLL自己完成的所有工作。

如果正确使用,SetKernelObjectSecurity的最大优点是:

在每种情况下,它都可以用错误的条目覆盖对象。在某些情况下,SetNamedSecurityInfo无法纠正有缺陷的ACL(可能是由不知道继承的旧工具创建的)。

我编写了一个程序来管理文件系统的文件和文件夹权限,它使用SetKernelObjectSecurity。此工具允许使用业务用户不能重命名/删除的“托管文件夹”(他们只能在下面删除/重命名)。此外,它还自动处理上层文件夹所需的所有列表权限(以便能够下移)。

我们使用它来设置数百万文件的文件系统,以及成千上万的用户。这是生产超过5年,没有任何问题。

如果你有进一步的问题,不要犹豫地问。Windows权限管理是一个相当复杂的话题,如果我能够分享我作为以前的Windows (从NT4开始)和开发人员期间收集到的一些知识,我感到很高兴。

..。在我的源代码库里搜索一些我很多年前写的旧东西..。

代码语言:javascript
复制
    // omitting the CreateFile opening here and error handling too :-)
    // and also the creation of a buffer (it is a BYTE[])
    // ... just the copy loop


    LPVOID lpContextRead, lpContextWrite;

    lpContextRead = NULL;
    lpContextWrite = NULL;

    while (TRUE)
    {
        bSuccess = BackupRead(hRead, bBuffer, sizeof (bBuffer), 
                &dwBytesRead, FALSE, TRUE, &lpContextRead);

        if (!bSuccess) 
        {
            // ... error exit
        }

        if (!dwBytesRead) break;

        bSuccess = BackupWrite(hWrite, bBuffer, dwBytesRead, 
                &dwBytesWritten, FALSE, TRUE, &lpContextWrite);

        if (!bSuccess) 
        {
            // ... error exit
        }
    }

    // cleanup 
    BackupRead(hRead, bBuffer, 0, &dwBytesRead, TRUE, TRUE, &lpContextRead);
    BackupWrite(hWrite, bBuffer, 0, &dwBytesWritten, TRUE, TRUE, &lpContextWrite);

    CloseHandle(hRead);
    CloseHandle(hWrite);
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/47164268

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档