需要对我的代码进行哪些修改才能使 SetSecurityDescriptorGroup 不失败?

What modification to my code is necessary to get SetSecurityDescriptorGroup to not fail?

这是该函数文档的 link: https://msdn.microsoft.com/en-us/library/windows/desktop/aa446654(v=vs.85).aspx

我编写了/应该/有效的代码,但在调用时却出现错误 ERROR_INVALID_SECURITY_DESCR。我的代码应该将一个已知的工作 GUID 从一个文件夹复制到另一个文件夹,但我将采用在修改文件或文件夹的 SecurityDescriptor 时不会在 SetSecurityDescriptorGroup 上出错的任何工作示例代码。

正如您在下面看到的,我的代码检查了所有内容的有效性,包括安全描述符,但错误“1338”仍然发生在调用 SetSecurityDescriptorGroup 时。

'1338' 是 "ERROR_INVALID_SECURITY_DESCR".

#include "stdafx.h"
#include <windows.h>
#include <AclAPI.h>
#include <sddl.h>
#include <iostream>
using std::wcout;
#include <string>
using std::string;
using std::wstring;

int main()
{
    PSECURITY_DESCRIPTOR pGoodSecurityDescriptor = NULL;

    LPCWSTR goodFilename = L"\\?\UNC\server\home\good";
    if (! (ERROR_SUCCESS == GetNamedSecurityInfo(goodFilename, SE_FILE_OBJECT,
        SACL_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION | OWNER_SECURITY_INFORMATION,
        NULL, NULL, NULL, NULL, &pGoodSecurityDescriptor)))
    {
        _tprintf(_T("GetNamedSecurityInfo Error %u\n"), GetLastError());
        return -1;
    }

    if (!IsValidSecurityDescriptor(pGoodSecurityDescriptor))
    {
        _tprintf(_T("IsValidSecurityDescriptor Error %u\n"), GetLastError());
        return -1;
    }
    PSECURITY_DESCRIPTOR pBadSecurityDescriptor = NULL;

    LPCWSTR badFilename = L"\\?\UNC\server\home\bad";
    if (!(ERROR_SUCCESS == GetNamedSecurityInfo(badFilename, SE_FILE_OBJECT,
        SACL_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION | OWNER_SECURITY_INFORMATION,
        NULL, NULL, NULL, NULL, &pBadSecurityDescriptor)))
    {
        _tprintf(_T("GetNamedSecurityInfo Error %u\n"), GetLastError());
        return -1;
    }

    if (!IsValidSecurityDescriptor(pBadSecurityDescriptor))
    {
        _tprintf(_T("IsValidSecurityDescriptor Error %u\n"), GetLastError());
        return -1;
    }

    PSID pGroup = (PSID)LocalAlloc(LPTR, sizeof(PSID));
    BOOL groupDefaulted = FALSE;

    if (!GetSecurityDescriptorGroup(pGoodSecurityDescriptor, &pGroup, &groupDefaulted))
    {
        _tprintf(_T("GetSecurityDescriptorGroup Error %u\n"), GetLastError());
        return -1;
    }

    if (!IsValidSid(pGroup))
    {
        _tprintf(_T("IsValidSid Error %u\n"), GetLastError());
        return -1;
    }

    SetLastError(0);

    if (!SetSecurityDescriptorGroup(pBadSecurityDescriptor, &pGroup, groupDefaulted))
    {
        _tprintf(_T("SetSecurityDescriptorGroup Error %u\n"), GetLastError());
        return -1;
    }    
    return 0;
}

GetNamedSecurityInfo() 函数创建自相关格式的安全描述符,但 SetSecurityDescriptorGroup() 函数需要绝对格式的安全描述符。您可以使用 MakeAbsoluteSD().

从相对格式转换为绝对格式

(另请参阅 MSDN 中的 Absolute and Self-Relative Security Descriptors。)