他人の空似自作物置場

AppContainerUtils.zip/AuthzAnyPackageFolder/AuthzAnyPackageFolder/AuthzAnyPackageFolder.cpp


#include <iostream>
#include <vector>

#include <boost/shared_ptr.hpp>
#include <boost/type_traits/remove_pointer.hpp>
#include <boost/foreach.hpp>

#include <Windows.h>

typedef boost::shared_ptr<boost::remove_pointer<PSID>::type> SHARED_SID;
void MyFreeSid(PSID sid) {
  if (sid != NULL) {
    ::FreeSid(sid);
  }
}
SHARED_SID ToSharedSID(PSID sid) {
  return SHARED_SID(sid, &MyFreeSid);
}
void MyLocalFree(PSID sid) {
  if (sid != NULL) {
    ::LocalFree(sid);
  }
}

typedef boost::shared_ptr<boost::remove_pointer<PACL>::type> SHARED_ACL;
unsigned int GetACLSize(const std::vector<SHARED_SID> &list) {
  unsigned int size = sizeof(ACL) + (sizeof(ACCESS_ALLOWED_ACE) * list.size());
  BOOST_FOREACH(const SHARED_SID &sid, list) {
    size += ::GetLengthSid(sid.get()) - sizeof(DWORD);
  }
  // align
  size = (size + sizeof(DWORD) - 1) & 0xfffffffc;
  return size;
}
SHARED_ACL CreatePACL(const std::vector<SHARED_SID> &list) {
  const unsigned int size = GetACLSize(list);
  const SHARED_ACL acl(reinterpret_cast<PACL>(new unsigned char[size]));
  if (::InitializeAcl(acl.get(), size, ACL_REVISION) == FALSE) {
    return SHARED_ACL();
  }
  BOOST_FOREACH(const SHARED_SID &sid, list) {
    if (::AddAccessAllowedAce(acl.get(), ACL_REVISION, GENERIC_ALL, sid.get()) == FALSE) {
      return SHARED_ACL();
    }
  }
  return acl;
}

typedef boost::shared_ptr<boost::remove_pointer<HANDLE>::type> SHARED_HANDLE;
void MyCloseHandle(const HANDLE handle) {
  if (handle != NULL) {
    ::CloseHandle(handle);
  }
}

SHARED_SID GetWellKnownSid(const WELL_KNOWN_SID_TYPE type) {
  SHARED_SID sid(new unsigned char[SECURITY_MAX_SID_SIZE]);
  DWORD sidSize = SECURITY_MAX_SID_SIZE;
  if (::CreateWellKnownSid(type, NULL, sid.get(), &sidSize) == FALSE) {
    return SHARED_SID();
  }
  return sid;
}

bool CreateSecurityDescriptor(boost::shared_ptr<SECURITY_DESCRIPTOR> &desc, SHARED_ACL &acl, const std::vector<SHARED_SID> &sidList, const SHARED_SID owner) {
  acl = CreatePACL(sidList);
  if (!acl) {
    return false;
  }
  desc.reset(new SECURITY_DESCRIPTOR());
  if (::InitializeSecurityDescriptor(desc.get(), SECURITY_DESCRIPTOR_REVISION) == FALSE) {
    return false;
  }
  if (::SetSecurityDescriptorDacl(desc.get(), TRUE, acl.get(), FALSE) == FALSE) {
    return false;
  }
  return true;
}

SHARED_SID GetUserSid(const wchar_t * const name) {
  DWORD bufSize = 0;
  wchar_t domain[256];
  DWORD domainSize = _countof(domain);
  SID_NAME_USE type;
  ::LookupAccountNameW(NULL, name, NULL, &bufSize, domain, &domainSize, &type);
  SHARED_SID sid(new unsigned char[bufSize]);
  ::LookupAccountNameW(NULL, name, sid.get(), &bufSize, domain, &domainSize, &type);
  return sid;
}

SHARED_SID GetCurrentUserSid() {
  wchar_t name[256];
  DWORD size = _countof(name);
  if (::GetUserNameW(name, &size) == FALSE) {
    return SHARED_SID();
  }
  return GetUserSid(name);
}

bool AuthzAnyPackage(const char * const path) {
  const SHARED_SID owner = GetCurrentUserSid();
  boost::shared_ptr<SECURITY_DESCRIPTOR> desc;
  SHARED_ACL acl;
  std::vector<SHARED_SID> sidList;
  sidList.push_back(GetWellKnownSid(WinBuiltinAnyPackageSid));
  sidList.push_back(GetWellKnownSid(WinLocalSystemSid));
  sidList.push_back(owner);
  sidList.push_back(GetWellKnownSid(WinBuiltinAdministratorsSid));
  if (!CreateSecurityDescriptor(desc, acl, sidList, owner)) {
    return false;
  }
  if (::SetFileSecurityA(path, DACL_SECURITY_INFORMATION, desc.get()) == FALSE) {
    return false;
  }
  return true;
}

int main(const unsigned int argc, const char * const * const argv) {
  std::locale::global(std::locale("japanese"));
  if (argc != 2) {
    std::wcout << L"usage: AuthzAnyPackageFolder.exe folder_path" << std::endl;
    std::wcin.ignore();
    return 1;
  }
  if (!AuthzAnyPackage(argv[1])) {
    std::wcout << L"Error: ファイルの権限設定に失敗しました" << std::endl;
    std::wcin.ignore();
    return 1;
  }
  std::wcout << L"処理は正常に終了しました" << std::endl;
  std::wcin.ignore();
  return 0;
}