|
@@ -0,0 +1,149 @@
|
|
|
|
|
+/*============================================================================
|
|
|
|
|
+ CMake - Cross Platform Makefile Generator
|
|
|
|
|
+ Copyright 2014 Kitware, Inc.
|
|
|
|
|
+
|
|
|
|
|
+ Distributed under the OSI-approved BSD License (the "License");
|
|
|
|
|
+ see accompanying file Copyright.txt for details.
|
|
|
|
|
+
|
|
|
|
|
+ This software is distributed WITHOUT ANY WARRANTY; without even the
|
|
|
|
|
+ implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
|
|
|
+ See the License for more information.
|
|
|
|
|
+============================================================================*/
|
|
|
|
|
+
|
|
|
|
|
+#include "cmWIXAccessControlList.h"
|
|
|
|
|
+
|
|
|
|
|
+#include <CPack/cmCPackGenerator.h>
|
|
|
|
|
+
|
|
|
|
|
+#include <cmSystemTools.h>
|
|
|
|
|
+
|
|
|
|
|
+cmWIXAccessControlList::cmWIXAccessControlList(
|
|
|
|
|
+ cmCPackLog *logger,
|
|
|
|
|
+ cmInstalledFile const& installedFile,
|
|
|
|
|
+ cmWIXSourceWriter &sourceWriter):
|
|
|
|
|
+ Logger(logger),
|
|
|
|
|
+ InstalledFile(installedFile),
|
|
|
|
|
+ SourceWriter(sourceWriter)
|
|
|
|
|
+{
|
|
|
|
|
+
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+bool cmWIXAccessControlList::Apply()
|
|
|
|
|
+{
|
|
|
|
|
+ std::vector<std::string> entries;
|
|
|
|
|
+ this->InstalledFile.GetPropertyAsList("CPACK_WIX_ACL", entries);
|
|
|
|
|
+
|
|
|
|
|
+ for(size_t i = 0; i < entries.size(); ++i)
|
|
|
|
|
+ {
|
|
|
|
|
+ this->CreatePermissionElement(entries[i]);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return true;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+void cmWIXAccessControlList::CreatePermissionElement(
|
|
|
|
|
+ std::string const& entry)
|
|
|
|
|
+{
|
|
|
|
|
+ std::string::size_type pos = entry.find('=');
|
|
|
|
|
+ if(pos == std::string::npos)
|
|
|
|
|
+ {
|
|
|
|
|
+ this->ReportError(entry, "Did not find mandatory '='");
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ std::string user_and_domain = entry.substr(0, pos);
|
|
|
|
|
+ std::string permission_string = entry.substr(pos + 1);
|
|
|
|
|
+
|
|
|
|
|
+ pos = user_and_domain.find('@');
|
|
|
|
|
+ std::string user;
|
|
|
|
|
+ std::string domain;
|
|
|
|
|
+ if(pos != std::string::npos)
|
|
|
|
|
+ {
|
|
|
|
|
+ user = user_and_domain.substr(0, pos);
|
|
|
|
|
+ domain = user_and_domain.substr(pos + 1);
|
|
|
|
|
+ }
|
|
|
|
|
+ else
|
|
|
|
|
+ {
|
|
|
|
|
+ user = user_and_domain;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ std::vector<std::string> permissions =
|
|
|
|
|
+ cmSystemTools::tokenize(permission_string, ",");
|
|
|
|
|
+
|
|
|
|
|
+ this->SourceWriter.BeginElement("Permission");
|
|
|
|
|
+ this->SourceWriter.AddAttribute("User", user);
|
|
|
|
|
+ if(domain.size())
|
|
|
|
|
+ {
|
|
|
|
|
+ this->SourceWriter.AddAttribute("Domain", domain);
|
|
|
|
|
+ }
|
|
|
|
|
+ for(size_t i = 0; i < permissions.size(); ++i)
|
|
|
|
|
+ {
|
|
|
|
|
+ this->EmitBooleanAttribute(entry,
|
|
|
|
|
+ cmSystemTools::TrimWhitespace(permissions[i]));
|
|
|
|
|
+ }
|
|
|
|
|
+ this->SourceWriter.EndElement("Permission");
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+void cmWIXAccessControlList::ReportError(
|
|
|
|
|
+ std::string const& entry,
|
|
|
|
|
+ std::string const& message)
|
|
|
|
|
+{
|
|
|
|
|
+ cmCPackLogger(cmCPackLog::LOG_ERROR,
|
|
|
|
|
+ "Failed processing ACL entry '" << entry <<
|
|
|
|
|
+ "': " << message << std::endl);
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+bool cmWIXAccessControlList::IsBooleanAttribute(std::string const& name)
|
|
|
|
|
+{
|
|
|
|
|
+ static const char* validAttributes[] =
|
|
|
|
|
+ {
|
|
|
|
|
+ "Append",
|
|
|
|
|
+ "ChangePermission",
|
|
|
|
|
+ "CreateChild",
|
|
|
|
|
+ "CreateFile",
|
|
|
|
|
+ "CreateLink",
|
|
|
|
|
+ "CreateSubkeys",
|
|
|
|
|
+ "Delete",
|
|
|
|
|
+ "DeleteChild",
|
|
|
|
|
+ "EnumerateSubkeys",
|
|
|
|
|
+ "Execute",
|
|
|
|
|
+ "FileAllRights",
|
|
|
|
|
+ "GenericAll",
|
|
|
|
|
+ "GenericExecute",
|
|
|
|
|
+ "GenericRead",
|
|
|
|
|
+ "GenericWrite",
|
|
|
|
|
+ "Notify",
|
|
|
|
|
+ "Read",
|
|
|
|
|
+ "ReadAttributes",
|
|
|
|
|
+ "ReadExtendedAttributes",
|
|
|
|
|
+ "ReadPermission",
|
|
|
|
|
+ "SpecificRightsAll",
|
|
|
|
|
+ "Synchronize",
|
|
|
|
|
+ "TakeOwnership",
|
|
|
|
|
+ "Traverse",
|
|
|
|
|
+ "Write",
|
|
|
|
|
+ "WriteAttributes",
|
|
|
|
|
+ "WriteExtendedAttributes",
|
|
|
|
|
+ 0
|
|
|
|
|
+ };
|
|
|
|
|
+
|
|
|
|
|
+ size_t i = 0;
|
|
|
|
|
+ while(validAttributes[i])
|
|
|
|
|
+ {
|
|
|
|
|
+ if(name == validAttributes[i++]) return true;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ return false;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+void cmWIXAccessControlList::EmitBooleanAttribute(
|
|
|
|
|
+ std::string const& entry, std::string const& name)
|
|
|
|
|
+{
|
|
|
|
|
+ if(!this->IsBooleanAttribute(name))
|
|
|
|
|
+ {
|
|
|
|
|
+ std::stringstream message;
|
|
|
|
|
+ message << "Unknown boolean attribute '" << name << "'";
|
|
|
|
|
+ this->ReportError(entry, message.str());
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ this->SourceWriter.AddAttribute(name, "yes");
|
|
|
|
|
+}
|