使用线程模拟检查客户端的安全描述符

时间:2018-04-19 17:48:28

标签: windows acl impersonation

我正在尝试检查客户端文件的访问权限,以便用线程模拟它。 我在Microsoft开发中心检查了这个例子,但似乎有很多问题https://msdn.microsoft.com/en-us/library/windows/desktop/aa379648(v=vs.85).aspx

我也有一段代码,但它总是返回false

      PACL file_dacl = NULL;
      AutoLocalFreeSDescriptor psd;
      DWORD dstatus = GetNamedSecurityInfoA(fname2.buf, SE_FILE_OBJECT, DACL_SECURITY_INFORMATION,
            NULL, NULL, &file_dacl, NULL, &psd.psd);
      if (ERROR_SUCCESS != dstatus) {
         return false;
      }
      AutoCloseHandle security_token;
      // Not sure if OpenAsSelf (3rd arg) should be true or false
      BOOL bstatus = OpenThreadToken(GetCurrentThread(), TOKEN_ALL_ACCESS, true, &security_token.stoken);
      if ((! bstatus) && (GetLastError() == ERROR_NO_TOKEN)) {
         bstatus = OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &security_token.stoken);
      }
      if (! bstatus) {
         return false;
      }
      GENERIC_MAPPING f_perms_map = {
         FILE_GENERIC_READ,
         FILE_GENERIC_WRITE,
         FILE_GENERIC_EXECUTE,
         FILE_ALL_ACCESS
      };
      DWORD file_exec_access;
      if (perm == 'r') {
         file_exec_access = FILE_GENERIC_READ;
      }
      else if (perm == 'w') {
         file_exec_access = FILE_GENERIC_WRITE;
      }
      else { // perm is 'x'
         file_exec_access = FILE_GENERIC_EXECUTE;
      }
      MapGenericMask(&file_exec_access, &f_perms_map);
      PRIVILEGE_SET priv_set;
      DWORD priv_set_size = sizeof(priv_set);
      DWORD granted_access = 0;
      BOOL have_access = false;
      bstatus = AccessCheck(psd.psd, security_token.stoken, file_exec_access, &f_perms_map,
            &priv_set, &priv_set_size, &granted_access, &have_access);

      DWORD d = GetLastError();
      LPSTR messageBuffer = nullptr;
      size_t size = FormatMessageA(FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
          NULL, d, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPSTR)&messageBuffer, 0, NULL);

      std::string message(messageBuffer, size);

      //Free the buffer.
      LocalFree(messageBuffer);
      if (bstatus) {
         return (have_access != 0);
      }
      else {
         return false;
      }

问题是与客户端本身有关还是问题与代码有关?

0 个答案:

没有答案