From 4818bb24e8f7f22345f90393239ce92129238ecc Mon Sep 17 00:00:00 2001 From: Sean Hall Date: Sun, 16 Dec 2018 15:54:06 -0600 Subject: Import code from old v4 repo --- src/wixext/IIsCompiler.cs | 2563 ++++++++++++++++++++++++++++++++++ src/wixext/IIsDecompiler.cs | 1547 ++++++++++++++++++++ src/wixext/IIsExtensionData.cs | 64 + src/wixext/iis.xsd | 1104 +++++++++++++++ src/wixext/messages.cs | 237 ++++ src/wixext/tables.xml | 304 ++++ src/wixlib/IIsExtension.wxs | 59 + src/wixlib/IIsExtension_Platform.wxi | 68 + src/wixlib/IIsExtension_x86.wxs | 8 + src/wixlib/en-us.wxl | 56 + src/wixlib/ja-jp.wxl | 48 + src/wixlib/pt-br.wxl | 51 + 12 files changed, 6109 insertions(+) create mode 100644 src/wixext/IIsCompiler.cs create mode 100644 src/wixext/IIsDecompiler.cs create mode 100644 src/wixext/IIsExtensionData.cs create mode 100644 src/wixext/iis.xsd create mode 100644 src/wixext/messages.cs create mode 100644 src/wixext/tables.xml create mode 100644 src/wixlib/IIsExtension.wxs create mode 100644 src/wixlib/IIsExtension_Platform.wxi create mode 100644 src/wixlib/IIsExtension_x86.wxs create mode 100644 src/wixlib/en-us.wxl create mode 100644 src/wixlib/ja-jp.wxl create mode 100644 src/wixlib/pt-br.wxl (limited to 'src') diff --git a/src/wixext/IIsCompiler.cs b/src/wixext/IIsCompiler.cs new file mode 100644 index 00000000..828d430b --- /dev/null +++ b/src/wixext/IIsCompiler.cs @@ -0,0 +1,2563 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +namespace WixToolset.Extensions +{ + using System; + using System.Collections.Generic; + using System.Globalization; + using System.Xml.Linq; + using WixToolset.Data; + using WixToolset.Extensibility; + + /// + /// The compiler for the WiX Toolset Internet Information Services Extension. + /// + public sealed class IIsCompiler : CompilerExtension + { + /// + /// Instantiate a new IIsCompiler. + /// + public IIsCompiler() + { + this.Namespace = "http://wixtoolset.org/schemas/v4/wxs/iis"; + } + + /// + /// Types of objects that custom HTTP Headers can be applied to. + /// + /// Note that this must be kept in sync with the eHttpHeaderParentType in scahttpheader.h. + private enum HttpHeaderParentType + { + /// Custom HTTP Header is to be applied to a Web Virtual Directory. + WebVirtualDir = 1, + /// Custom HTTP Header is to be applied to a Web Site. + WebSite = 2, + } + + /// + /// Types of objects that MimeMaps can be applied to. + /// + /// Note that this must be kept in sync with the eMimeMapParentType in scamimemap.h. + private enum MimeMapParentType + { + /// MimeMap is to be applied to a Web Virtual Directory. + WebVirtualDir = 1, + WebSite = 2, + } + + /// + /// Types of objects that custom WebErrors can be applied to. + /// + /// Note that this must be kept in sync with the eWebErrorParentType in scaweberror.h. + private enum WebErrorParentType + { + /// Custom WebError is to be applied to a Web Virtual Directory. + WebVirtualDir = 1, + + /// Custom WebError is to be applied to a Web Site. + WebSite = 2, + } + + /// + /// Processes an element for the Compiler. + /// + /// Source line number for the parent element. + /// Parent element of element to process. + /// Element to process. + /// Extra information about the context in which this element is being parsed. + public override void ParseElement(XElement parentElement, XElement element, IDictionary context) + { + switch (parentElement.Name.LocalName) + { + case "Component": + string componentId = context["ComponentId"]; + string directoryId = context["DirectoryId"]; + + switch (element.Name.LocalName) + { + case "Certificate": + this.ParseCertificateElement(element, componentId); + break; + case "WebAppPool": + this.ParseWebAppPoolElement(element, componentId); + break; + case "WebDir": + this.ParseWebDirElement(element, componentId, null); + break; + case "WebFilter": + this.ParseWebFilterElement(element, componentId, null); + break; + case "WebProperty": + this.ParseWebPropertyElement(element, componentId); + break; + case "WebServiceExtension": + this.ParseWebServiceExtensionElement(element, componentId); + break; + case "WebSite": + this.ParseWebSiteElement(element, componentId); + break; + case "WebVirtualDir": + this.ParseWebVirtualDirElement(element, componentId, null, null); + break; + default: + this.Core.UnexpectedElement(parentElement, element); + break; + } + break; + case "Fragment": + case "Module": + case "Product": + switch (element.Name.LocalName) + { + case "WebApplication": + this.ParseWebApplicationElement(element); + break; + case "WebAppPool": + this.ParseWebAppPoolElement(element, null); + break; + case "WebDirProperties": + this.ParseWebDirPropertiesElement(element); + break; + case "WebLog": + this.ParseWebLogElement(element); + break; + case "WebSite": + this.ParseWebSiteElement(element, null); + break; + default: + this.Core.UnexpectedElement(parentElement, element); + break; + } + break; + default: + this.Core.UnexpectedElement(parentElement, element); + break; + } + } + + /// + /// Parses a certificate element. + /// + /// Element to parse. + /// Identifier for parent component. + private void ParseCertificateElement(XElement node, string componentId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + int attributes = 0; + string binaryKey = null; + string certificatePath = null; + string name = null; + string pfxPassword = null; + int storeLocation = 0; + string storeName = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "BinaryKey": + attributes |= 2; // SCA_CERT_ATTRIBUTE_BINARYDATA + binaryKey = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "Binary", binaryKey); + break; + case "CertificatePath": + certificatePath = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Name": + name = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Overwrite": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 4; // SCA_CERT_ATTRIBUTE_OVERWRITE + } + else + { + attributes &= ~4; // SCA_CERT_ATTRIBUTE_OVERWRITE + } + break; + case "PFXPassword": + pfxPassword = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Request": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 1; // SCA_CERT_ATTRIBUTE_REQUEST + } + else + { + attributes &= ~1; // SCA_CERT_ATTRIBUTE_REQUEST + } + break; + case "StoreLocation": + string storeLocationValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < storeLocationValue.Length) + { + switch (storeLocationValue) + { + case "currentUser": + storeLocation = 1; // SCA_CERTSYSTEMSTORE_CURRENTUSER + break; + case "localMachine": + storeLocation = 2; // SCA_CERTSYSTEMSTORE_LOCALMACHINE + break; + default: + storeLocation = -1; + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, "StoreLocation", storeLocationValue, "currentUser", "localMachine")); + break; + } + } + break; + case "StoreName": + string storeNameValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < storeNameValue.Length) + { + switch (storeNameValue) + { + case "ca": + storeName = "CA"; + break; + case "my": + case "personal": + storeName = "MY"; + break; + case "request": + storeName = "REQUEST"; + break; + case "root": + storeName = "Root"; + break; + case "otherPeople": + storeName = "AddressBook"; + break; + case "trustedPeople": + storeName = "TrustedPeople"; + break; + case "trustedPublisher": + storeName = "TrustedPublisher"; + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, "StoreName", storeNameValue, "ca", "my", "request", "root", "otherPeople", "trustedPeople", "trustedPublisher")); + break; + } + } + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == name) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Name")); + } + + if (0 == storeLocation) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "StoreLocation")); + } + + if (null == storeName) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "StoreName")); + } + + if (null != binaryKey && null != certificatePath) + { + this.Core.OnMessage(WixErrors.IllegalAttributeWithOtherAttribute(sourceLineNumbers, node.Name.LocalName, "BinaryKey", "CertificatePath", certificatePath)); + } + else if (null == binaryKey && null == certificatePath) + { + this.Core.OnMessage(WixErrors.ExpectedAttributes(sourceLineNumbers, node.Name.LocalName, "BinaryKey", "CertificatePath")); + } + + this.Core.ParseForExtensionElements(node); + + // Reference InstallCertificates and UninstallCertificates since nothing will happen without them + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "InstallCertificates"); + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "UninstallCertificates"); + this.Core.EnsureTable(sourceLineNumbers, "CertificateHash"); // Certificate CustomActions require the CertificateHash table + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "Certificate"); + row[0] = id; + row[1] = componentId; + row[2] = name; + row[3] = storeLocation; + row[4] = storeName; + row[5] = attributes; + row[6] = binaryKey; + row[7] = certificatePath; + row[8] = pfxPassword; + } + } + + /// + /// Parses a CertificateRef extension element. + /// + /// Element to parse. + /// Identifier for parent web site. + private void ParseCertificateRefElement(XElement node, string webId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "Certificate", id); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "Certificate", id); + + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebSiteCertificates"); + row[0] = webId; + row[1] = id; + } + } + + /// + /// Parses a mime map element. + /// + /// Element to parse. + /// Identifier for parent symbol. + /// Type that parentId refers to. + private void ParseMimeMapElement(XElement node, string parentId, MimeMapParentType parentType) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string extension = null; + string type = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Extension": + extension = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Type": + type = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == extension) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Extension")); + } + else if (0 < extension.Length) + { + if (!extension.StartsWith(".", StringComparison.Ordinal)) + { + this.Core.OnMessage(IIsErrors.MimeMapExtensionMissingPeriod(sourceLineNumbers, node.Name.LocalName, "Extension", extension)); + } + } + + if (null == type) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Type")); + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsMimeMap"); + row[0] = id; + row[1] = (int)parentType; + row[2] = parentId; + row[3] = type; + row[4] = extension; + } + } + + /// + /// Parses a recycle time element. + /// + /// Element to parse. + /// Recycle time value. + private string ParseRecycleTimeElement(XElement node) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string value = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Value": + value = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == value) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Value")); + } + + this.Core.ParseForExtensionElements(node); + + return value; + } + + /// + /// Parses a web address element. + /// + /// Element to parse. + /// Identifier of parent web site. + /// Identifier for web address. + private string ParseWebAddressElement(XElement node, string parentWeb) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string header = null; + string ip = null; + string port = null; + bool secure = false; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Header": + header = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "IP": + ip = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Port": + port = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Secure": + secure = YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == port) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Port")); + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebAddress"); + row[0] = id; + row[1] = parentWeb; + row[2] = ip; + row[3] = port; + row[4] = header; + row[5] = secure ? 1 : 0; + } + + return id; + } + + /// + /// Parses a web application element. + /// + /// Element to parse. + /// Identifier for web application. + private string ParseWebApplicationElement(XElement node) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + YesNoDefaultType allowSessions = YesNoDefaultType.Default; + string appPool = null; + YesNoDefaultType buffer = YesNoDefaultType.Default; + YesNoDefaultType clientDebugging = YesNoDefaultType.Default; + string defaultScript = null; + int isolation = 0; + string name = null; + YesNoDefaultType parentPaths = YesNoDefaultType.Default; + int scriptTimeout = CompilerConstants.IntegerNotSet; + int sessionTimeout = CompilerConstants.IntegerNotSet; + YesNoDefaultType serverDebugging = YesNoDefaultType.Default; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "AllowSessions": + allowSessions = this.Core.GetAttributeYesNoDefaultValue(sourceLineNumbers, attrib); + break; + case "Buffer": + buffer = this.Core.GetAttributeYesNoDefaultValue(sourceLineNumbers, attrib); + break; + case "ClientDebugging": + clientDebugging = this.Core.GetAttributeYesNoDefaultValue(sourceLineNumbers, attrib); + break; + case "DefaultScript": + defaultScript = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < defaultScript.Length) + { + switch (defaultScript) + { + case "JScript": + case "VBScript": + // these are valid values + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName, defaultScript, "JScript", "VBScript")); + break; + } + } + break; + case "Isolation": + string isolationValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < isolationValue.Length) + { + switch (isolationValue) + { + case "low": + isolation = 0; + break; + case "medium": + isolation = 2; + break; + case "high": + isolation = 1; + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName, isolationValue, "low", "medium", "high")); + break; + } + } + break; + case "Name": + name = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "ParentPaths": + parentPaths = this.Core.GetAttributeYesNoDefaultValue(sourceLineNumbers, attrib); + break; + case "ScriptTimeout": + scriptTimeout = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "ServerDebugging": + serverDebugging = this.Core.GetAttributeYesNoDefaultValue(sourceLineNumbers, attrib); + break; + case "SessionTimeout": + sessionTimeout = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "WebAppPool": + appPool = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsAppPool", appPool); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == name) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Name")); + } + else if (-1 != name.IndexOf("\\", StringComparison.Ordinal)) + { + this.Core.OnMessage(IIsErrors.IllegalCharacterInAttributeValue(sourceLineNumbers, node.Name.LocalName, "Name", name, '\\')); + } + + foreach (XElement child in node.Elements()) + { + if (this.Namespace == child.Name.Namespace) + { + SourceLineNumber childSourceLineNumbers = Preprocessor.GetSourceLineNumbers(child); + switch (child.Name.LocalName) + { + case "WebApplicationExtension": + this.ParseWebApplicationExtensionElement(child, id); + break; + default: + this.Core.UnexpectedElement(node, child); + break; + } + } + else + { + this.Core.ParseExtensionElement(node, child); + } + } + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebApplication"); + row[0] = id; + row[1] = name; + row[2] = isolation; + if (YesNoDefaultType.Default != allowSessions) + { + row[3] = YesNoDefaultType.Yes == allowSessions ? 1 : 0; + } + + if (CompilerConstants.IntegerNotSet != sessionTimeout) + { + row[4] = sessionTimeout; + } + + if (YesNoDefaultType.Default != buffer) + { + row[5] = YesNoDefaultType.Yes == buffer ? 1 : 0; + } + + if (YesNoDefaultType.Default != parentPaths) + { + row[6] = YesNoDefaultType.Yes == parentPaths ? 1 : 0; + } + row[7] = defaultScript; + if (CompilerConstants.IntegerNotSet != scriptTimeout) + { + row[8] = scriptTimeout; + } + + if (YesNoDefaultType.Default != serverDebugging) + { + row[9] = YesNoDefaultType.Yes == serverDebugging ? 1 : 0; + } + + if (YesNoDefaultType.Default != clientDebugging) + { + row[10] = YesNoDefaultType.Yes == clientDebugging ? 1 : 0; + } + row[11] = appPool; + } + + return id; + } + + /// + /// Parses a web application extension element. + /// + /// Element to parse. + /// Identifier for parent web application. + private void ParseWebApplicationExtensionElement(XElement node, string application) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + int attributes = 0; + string executable = null; + string extension = null; + string verbs = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "CheckPath": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 4; + } + else + { + attributes &= ~4; + } + break; + case "Executable": + executable = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Extension": + extension = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Script": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 1; + } + else + { + attributes &= ~1; + } + break; + case "Verbs": + verbs = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebApplicationExtension"); + row[0] = application; + row[1] = extension; + row[2] = verbs; + row[3] = executable; + if (0 < attributes) + { + row[4] = attributes; + } + } + } + + /// + /// Parses web application pool element. + /// + /// Element to parse. + /// Optional identifier of parent component. + private void ParseWebAppPoolElement(XElement node, string componentId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + int attributes = 0; + int cpuAction = CompilerConstants.IntegerNotSet; + string cpuMon = null; + int idleTimeout = CompilerConstants.IntegerNotSet; + int maxCpuUsage = 0; + int maxWorkerProcs = CompilerConstants.IntegerNotSet; + string managedRuntimeVersion = null; + string managedPipelineMode = null; + string name = null; + int privateMemory = CompilerConstants.IntegerNotSet; + int queueLimit = CompilerConstants.IntegerNotSet; + int recycleMinutes = CompilerConstants.IntegerNotSet; + int recycleRequests = CompilerConstants.IntegerNotSet; + string recycleTimes = null; + int refreshCpu = CompilerConstants.IntegerNotSet; + string user = null; + int virtualMemory = CompilerConstants.IntegerNotSet; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "CpuAction": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + string cpuActionValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < cpuActionValue.Length) + { + switch (cpuActionValue) + { + case "shutdown": + cpuAction = 1; + break; + case "none": + cpuAction = 0; + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName, cpuActionValue, "shutdown", "none")); + break; + } + } + break; + case "Identity": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + string identityValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < identityValue.Length) + { + switch (identityValue) + { + case "networkService": + attributes |= 1; + break; + case "localService": + attributes |= 2; + break; + case "localSystem": + attributes |= 4; + break; + case "other": + attributes |= 8; + break; + case "applicationPoolIdentity": + attributes |= 0x10; + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName, identityValue, "networkService", "localService", "localSystem", "other", "applicationPoolIdentity")); + break; + } + } + break; + case "IdleTimeout": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + idleTimeout = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "ManagedPipelineMode": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + managedPipelineMode = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + + + if (!String.IsNullOrEmpty(managedPipelineMode)) + { + switch (managedPipelineMode) + { + // In 3.5 we allowed lower case values (per camel case enum style), we now use formatted fields, + // so the value needs to match exactly what we pass in to IIS which uses pascal case. + case "classic": + managedPipelineMode = "Classic"; + break; + case "integrated": + managedPipelineMode = "Integrated"; + break; + case "Classic": + break; + case "Integrated": + break; + default: + if (!this.Core.ContainsProperty(managedPipelineMode)) + { + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName, managedPipelineMode, "Classic", "Integrated")); + } + break; + } + } + + break; + case "ManagedRuntimeVersion": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + managedRuntimeVersion = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "MaxCpuUsage": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + maxCpuUsage = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, 100); + break; + case "MaxWorkerProcesses": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + maxWorkerProcs = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "Name": + name = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "PrivateMemory": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + privateMemory = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, 4294967); + break; + case "QueueLimit": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + queueLimit = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "RecycleMinutes": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + recycleMinutes = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "RecycleRequests": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + recycleRequests = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "RefreshCpu": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + refreshCpu = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, int.MaxValue); + break; + case "User": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + user = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "User", user); + break; + case "VirtualMemory": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + virtualMemory = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, 4294967); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == name) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Name")); + } + + if (null == user && 8 == (attributes & 0x1F)) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "User", "Identity", "other")); + } + + if (null != user && 8 != (attributes & 0x1F)) + { + this.Core.OnMessage(WixErrors.IllegalAttributeValueWithoutOtherAttribute(sourceLineNumbers, node.Name.LocalName, "User", user, "Identity", "other")); + } + + cpuMon = maxCpuUsage.ToString(CultureInfo.InvariantCulture.NumberFormat); + if (CompilerConstants.IntegerNotSet != refreshCpu) + { + cpuMon = String.Concat(cpuMon, ",", refreshCpu.ToString(CultureInfo.InvariantCulture.NumberFormat)); + if (CompilerConstants.IntegerNotSet != cpuAction) + { + cpuMon = String.Concat(cpuMon, ",", cpuAction.ToString(CultureInfo.InvariantCulture.NumberFormat)); + } + } + + foreach (XElement child in node.Elements()) + { + if (this.Namespace == child.Name.Namespace) + { + switch (child.Name.LocalName) + { + case "RecycleTime": + if (null == componentId) + { + SourceLineNumber childSourceLineNumbers = Preprocessor.GetSourceLineNumbers(child); + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, node.Name.LocalName)); + } + + if (null == recycleTimes) + { + recycleTimes = this.ParseRecycleTimeElement(child); + } + else + { + recycleTimes = String.Concat(recycleTimes, ",", this.ParseRecycleTimeElement(child)); + } + break; + default: + this.Core.UnexpectedElement(node, child); + break; + } + } + else + { + this.Core.ParseExtensionElement(node, child); + } + } + + if (null != componentId) + { + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + } + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsAppPool"); + row[0] = id; + row[1] = name; + row[2] = componentId; + row[3] = attributes; + row[4] = user; + if (CompilerConstants.IntegerNotSet != recycleMinutes) + { + row[5] = recycleMinutes; + } + + if (CompilerConstants.IntegerNotSet != recycleRequests) + { + row[6] = recycleRequests; + } + row[7] = recycleTimes; + if (CompilerConstants.IntegerNotSet != idleTimeout) + { + row[8] = idleTimeout; + } + + if (CompilerConstants.IntegerNotSet != queueLimit) + { + row[9] = queueLimit; + } + row[10] = cpuMon; + if (CompilerConstants.IntegerNotSet != maxWorkerProcs) + { + row[11] = maxWorkerProcs; + } + + if (CompilerConstants.IntegerNotSet != virtualMemory) + { + row[12] = virtualMemory; + } + + if (CompilerConstants.IntegerNotSet != privateMemory) + { + row[13] = privateMemory; + } + row[14] = managedRuntimeVersion; + row[15] = managedPipelineMode; + } + } + + /// + /// Parses a web directory element. + /// + /// Element to parse. + /// Identifier for parent component. + /// Optional identifier for parent web site. + private void ParseWebDirElement(XElement node, string componentId, string parentWeb) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string dirProperties = null; + string path = null; + string application = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "DirProperties": + dirProperties = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Path": + path = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebApplication": + application = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebSite": + if (null != parentWeb) + { + this.Core.OnMessage(IIsErrors.WebSiteAttributeUnderWebSite(sourceLineNumbers, node.Name.LocalName)); + } + + parentWeb = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebSite", parentWeb); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == path) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Path")); + } + + if (null == parentWeb) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "WebSite")); + } + + foreach (XElement child in node.Elements()) + { + if (this.Namespace == child.Name.Namespace) + { + SourceLineNumber childSourceLineNumbers = Preprocessor.GetSourceLineNumbers(child); + switch (child.Name.LocalName) + { + case "WebApplication": + if (null != application) + { + this.Core.OnMessage(IIsErrors.WebApplicationAlreadySpecified(childSourceLineNumbers, node.Name.LocalName)); + } + + application = this.ParseWebApplicationElement(child); + break; + case "WebDirProperties": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + string childWebDirProperties = this.ParseWebDirPropertiesElement(child); + if (null == dirProperties) + { + dirProperties = childWebDirProperties; + } + else + { + this.Core.OnMessage(WixErrors.IllegalAttributeWhenNested(sourceLineNumbers, child.Name.LocalName, "DirProperties", child.Name.LocalName)); + } + break; + default: + this.Core.UnexpectedElement(node, child); + break; + } + } + else + { + this.Core.ParseExtensionElement(node, child); + } + } + + if (null == dirProperties) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "DirProperties")); + } + + if (null != application) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebApplication", application); + } + + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebDirProperties", dirProperties); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebDir"); + row[0] = id; + row[1] = componentId; + row[2] = parentWeb; + row[3] = path; + row[4] = dirProperties; + row[5] = application; + } + } + + /// + /// Parses a web directory properties element. + /// + /// Element to parse. + /// The identifier for this WebDirProperties. + private string ParseWebDirPropertiesElement(XElement node) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + int access = 0; + bool accessSet = false; + int accessSSLFlags = 0; + bool accessSSLFlagsSet = false; + string anonymousUser = null; + YesNoType aspDetailedError = YesNoType.NotSet; + string authenticationProviders = null; + int authorization = 0; + bool authorizationSet = false; + string cacheControlCustom = null; + long cacheControlMaxAge = CompilerConstants.LongNotSet; + string defaultDocuments = null; + string httpExpires = null; + bool iisControlledPassword = false; + YesNoType index = YesNoType.NotSet; + YesNoType logVisits = YesNoType.NotSet; + YesNoType notCustomError = YesNoType.NotSet; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "AnonymousUser": + anonymousUser = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "User", anonymousUser); + break; + case "AspDetailedError": + aspDetailedError = this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + case "AuthenticationProviders": + authenticationProviders = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "CacheControlCustom": + cacheControlCustom = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "CacheControlMaxAge": + cacheControlMaxAge = this.Core.GetAttributeLongValue(sourceLineNumbers, attrib, 0, uint.MaxValue); // 4294967295 (uint.MaxValue) represents unlimited + break; + case "ClearCustomError": + notCustomError = this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + case "DefaultDocuments": + defaultDocuments = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "HttpExpires": + httpExpires = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "IIsControlledPassword": + iisControlledPassword = YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + case "Index": + index = this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + case "LogVisits": + logVisits = this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib); + break; + + // Access attributes + case "Execute": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + access |= 4; + } + else + { + access &= ~4; + } + accessSet = true; + break; + case "Read": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + access |= 1; + } + else + { + access &= ~1; + } + accessSet = true; + break; + case "Script": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + access |= 512; + } + else + { + access &= ~512; + } + accessSet = true; + break; + case "Write": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + access |= 2; + } + else + { + access &= ~2; + } + accessSet = true; + break; + + // AccessSSL Attributes + case "AccessSSL": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + accessSSLFlags |= 8; + } + else + { + accessSSLFlags &= ~8; + } + accessSSLFlagsSet = true; + break; + case "AccessSSL128": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + accessSSLFlags |= 256; + } + else + { + accessSSLFlags &= ~256; + } + accessSSLFlagsSet = true; + break; + case "AccessSSLMapCert": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + accessSSLFlags |= 128; + } + else + { + accessSSLFlags &= ~128; + } + accessSSLFlagsSet = true; + break; + case "AccessSSLNegotiateCert": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + accessSSLFlags |= 32; + } + else + { + accessSSLFlags &= ~32; + } + accessSSLFlagsSet = true; + break; + case "AccessSSLRequireCert": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + accessSSLFlags |= 64; + } + else + { + accessSSLFlags &= ~64; + } + accessSSLFlagsSet = true; + break; + + // Authorization attributes + case "AnonymousAccess": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + authorization |= 1; + } + else + { + authorization &= ~1; + } + authorizationSet = true; + break; + case "BasicAuthentication": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + authorization |= 2; + } + else + { + authorization &= ~2; + } + authorizationSet = true; + break; + case "DigestAuthentication": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + authorization |= 16; + } + else + { + authorization &= ~16; + } + authorizationSet = true; + break; + case "PassportAuthentication": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + authorization |= 64; + } + else + { + authorization &= ~64; + } + authorizationSet = true; + break; + case "WindowsAuthentication": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + authorization |= 4; + } + else + { + authorization &= ~4; + } + authorizationSet = true; + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebDirProperties"); + row[0] = id; + if (accessSet) + { + row[1] = access; + } + + if (authorizationSet) + { + row[2] = authorization; + } + row[3] = anonymousUser; + row[4] = iisControlledPassword ? 1 : 0; + if (YesNoType.NotSet != logVisits) + { + row[5] = YesNoType.Yes == logVisits ? 1 : 0; + } + + if (YesNoType.NotSet != index) + { + row[6] = YesNoType.Yes == index ? 1 : 0; + } + row[7] = defaultDocuments; + if (YesNoType.NotSet != aspDetailedError) + { + row[8] = YesNoType.Yes == aspDetailedError ? 1 : 0; + } + row[9] = httpExpires; + if (CompilerConstants.LongNotSet != cacheControlMaxAge) + { + row[10] = unchecked((int)cacheControlMaxAge); + } + row[11] = cacheControlCustom; + if (YesNoType.NotSet != notCustomError) + { + row[12] = YesNoType.Yes == notCustomError ? 1 : 0; + } + + if (accessSSLFlagsSet) + { + row[13] = accessSSLFlags; + } + + if (null != authenticationProviders) + { + row[14] = authenticationProviders; + } + } + + return id; + } + + /// + /// Parses a web error element. + /// + /// Element to parse. + /// Type of the parent. + /// Id of the parent. + private void ParseWebErrorElement(XElement node, WebErrorParentType parentType, string parent) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + int errorCode = CompilerConstants.IntegerNotSet; + string file = null; + string url = null; + int subCode = CompilerConstants.IntegerNotSet; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "ErrorCode": + errorCode = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 400, 599); + break; + case "File": + file = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "SubCode": + subCode = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, int.MaxValue); + break; + case "URL": + url = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (CompilerConstants.IntegerNotSet == errorCode) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "ErrorCode")); + errorCode = CompilerConstants.IllegalInteger; + } + + if (CompilerConstants.IntegerNotSet == subCode) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "SubCode")); + subCode = CompilerConstants.IllegalInteger; + } + + if (String.IsNullOrEmpty(file) && String.IsNullOrEmpty(url)) + { + this.Core.OnMessage(WixErrors.IllegalAttributeWithOtherAttribute(sourceLineNumbers, node.Name.LocalName, "File", "URL")); + } + + this.Core.ParseForExtensionElements(node); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebError"); + row[0] = errorCode; + row[1] = subCode; + row[2] = (int)parentType; + row[3] = parent; + row[4] = file; + row[5] = url; + } + } + + /// + /// Parses a web filter element. + /// + /// Element to parse. + /// Identifier of parent component. + /// Optional identifier of parent web site. + private void ParseWebFilterElement(XElement node, string componentId, string parentWeb) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string description = null; + int flags = 0; + int loadOrder = CompilerConstants.IntegerNotSet; + string name = null; + string path = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Description": + description = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Flags": + flags = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, int.MaxValue); + break; + case "LoadOrder": + string loadOrderValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < loadOrderValue.Length) + { + switch (loadOrderValue) + { + case "first": + loadOrder = 0; + break; + case "last": + loadOrder = -1; + break; + default: + loadOrder = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 1, short.MaxValue); + break; + } + } + break; + case "Name": + name = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Path": + path = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebSite": + if (null != parentWeb) + { + this.Core.OnMessage(IIsErrors.WebSiteAttributeUnderWebSite(sourceLineNumbers, node.Name.LocalName)); + } + + parentWeb = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebSite", parentWeb); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == name) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Name")); + } + + if (null == path) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Path")); + } + + this.Core.ParseForExtensionElements(node); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsFilter"); + row[0] = id; + row[1] = name; + row[2] = componentId; + row[3] = path; + row[4] = parentWeb; + row[5] = description; + row[6] = flags; + if (CompilerConstants.IntegerNotSet != loadOrder) + { + row[7] = loadOrder; + } + } + } + + /// + /// Parses web log element. + /// + /// Node to be parsed. + private void ParseWebLogElement(XElement node) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string type = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Type": + string typeValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if (0 < typeValue.Length) + { + switch (typeValue) + { + case "IIS": + type = "Microsoft IIS Log File Format"; + break; + case "NCSA": + type = "NCSA Common Log File Format"; + break; + case "none": + type = "none"; + break; + case "ODBC": + type = "ODBC Logging"; + break; + case "W3C": + type = "W3C Extended Log File Format"; + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, "Type", typeValue, "IIS", "NCSA", "none", "ODBC", "W3C")); + break; + } + } + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == type) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Type")); + } + + this.Core.ParseForExtensionElements(node); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebLog"); + row[0] = id; + row[1] = type; + } + } + + /// + /// Parses a web property element. + /// + /// Element to parse. + /// Identifier for parent component. + private void ParseWebPropertyElement(XElement node, string componentId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string value = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Value": + value = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + switch (id) + { + case "ETagChangeNumber": + case "MaxGlobalBandwidth": + // Must specify a value for these + if (null == value) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Value", "Id", id)); + } + break; + case "IIs5IsolationMode": + case "LogInUTF8": + // Can't specify a value for these + if (null != value) + { + this.Core.OnMessage(WixErrors.IllegalAttributeWithOtherAttribute(sourceLineNumbers, node.Name.LocalName, "Value", "Id", id)); + } + break; + default: + this.Core.OnMessage(WixErrors.IllegalAttributeValue(sourceLineNumbers, node.Name.LocalName, "Id", id, "ETagChangeNumber", "IIs5IsolationMode", "LogInUTF8", "MaxGlobalBandwidth")); + break; + } + + this.Core.ParseForExtensionElements(node); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsProperty"); + row[0] = id; + row[1] = componentId; + row[2] = 0; + row[3] = value; + } + } + + /// + /// Parses a web service extension element. + /// + /// Element to parse. + /// Identifier for parent component. + private void ParseWebServiceExtensionElement(XElement node, string componentId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + int attributes = 0; + string description = null; + string file = null; + string group = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Allow": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 1; + } + else + { + attributes &= ~1; + } + break; + case "Description": + description = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "File": + file = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Group": + group = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "UIDeletable": + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes |= 2; + } + else + { + attributes &= ~2; + } + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == file) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "File")); + } + + this.Core.ParseForExtensionElements(node); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebServiceExtension"); + row[0] = id; + row[1] = componentId; + row[2] = file; + row[3] = description; + row[4] = group; + row[5] = attributes; + } + } + + /// + /// Parses a web site element. + /// + /// Element to parse. + /// Optional identifier of parent component. + private void ParseWebSiteElement(XElement node, string componentId) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string application = null; + int attributes = 0; + int connectionTimeout = CompilerConstants.IntegerNotSet; + string description = null; + string directory = null; + string dirProperties = null; + string keyAddress = null; + string log = null; + string siteId = null; + int sequence = CompilerConstants.IntegerNotSet; + int state = CompilerConstants.IntegerNotSet; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "AutoStart": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + state = 2; + } + else if (state != 1) + { + state = 0; + } + break; + case "ConfigureIfExists": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + if (YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + attributes &= ~2; + } + else + { + attributes |= 2; + } + break; + case "ConnectionTimeout": + connectionTimeout = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 0, short.MaxValue); + break; + case "Description": + description = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Directory": + directory = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "Directory", directory); + break; + case "DirProperties": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + dirProperties = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "SiteId": + siteId = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + if ("*" == siteId) + { + siteId = "-1"; + } + break; + case "Sequence": + sequence = this.Core.GetAttributeIntegerValue(sourceLineNumbers, attrib, 1, short.MaxValue); + break; + case "StartOnInstall": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + // when state is set to 2 it implies 1, so don't set it to 1 + if (2 != state && YesNoType.Yes == this.Core.GetAttributeYesNoValue(sourceLineNumbers, attrib)) + { + state = 1; + } + else if (2 != state) + { + state = 0; + } + break; + case "WebApplication": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + application = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebLog": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalAttributeWithoutComponent(sourceLineNumbers, node.Name.LocalName, attrib.Name.LocalName)); + } + + log = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebLog", log); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == description) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Description")); + } + + if (null == directory && null != componentId) + { + this.Core.OnMessage(IIsErrors.RequiredAttributeUnderComponent(sourceLineNumbers, node.Name.LocalName, "Directory")); + } + + foreach (XElement child in node.Elements()) + { + if (this.Namespace == child.Name.Namespace) + { + SourceLineNumber childSourceLineNumbers = Preprocessor.GetSourceLineNumbers(child); + switch (child.Name.LocalName) + { + case "CertificateRef": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseCertificateRefElement(child, id); + break; + case "HttpHeader": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseHttpHeaderElement(child, HttpHeaderParentType.WebSite, id); + break; + case "WebAddress": + string address = this.ParseWebAddressElement(child, id); + if (null == keyAddress) + { + keyAddress = address; + } + break; + case "WebApplication": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + if (null != application) + { + this.Core.OnMessage(IIsErrors.WebApplicationAlreadySpecified(childSourceLineNumbers, node.Name.LocalName)); + } + + application = this.ParseWebApplicationElement(child); + break; + case "WebDir": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseWebDirElement(child, componentId, id); + break; + case "WebDirProperties": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + string childWebDirProperties = this.ParseWebDirPropertiesElement(child); + if (null == dirProperties) + { + dirProperties = childWebDirProperties; + } + else + { + this.Core.OnMessage(WixErrors.IllegalParentAttributeWhenNested(sourceLineNumbers, "WebSite", "DirProperties", child.Name.LocalName)); + } + break; + case "WebError": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseWebErrorElement(child, WebErrorParentType.WebSite, id); + break; + case "WebFilter": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseWebFilterElement(child, componentId, id); + break; + case "WebVirtualDir": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + this.ParseWebVirtualDirElement(child, componentId, id, null); + break; + case "MimeMap": + this.ParseMimeMapElement(child, id, MimeMapParentType.WebSite); + break; + default: + this.Core.UnexpectedElement(node, child); + break; + } + } + else + { + this.Core.ParseExtensionElement(node, child); + } + } + + + if (null == keyAddress) + { + this.Core.OnMessage(WixErrors.ExpectedElement(sourceLineNumbers, node.Name.LocalName, "WebAddress")); + } + + if (null != application) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebApplication", application); + } + + if (null != dirProperties) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebDirProperties", dirProperties); + } + + if (null != componentId) + { + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + } + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebSite"); + row[0] = id; + row[1] = componentId; + row[2] = description; + if (CompilerConstants.IntegerNotSet != connectionTimeout) + { + row[3] = connectionTimeout; + } + row[4] = directory; + if (CompilerConstants.IntegerNotSet != state) + { + row[5] = state; + } + + if (0 != attributes) + { + row[6] = attributes; + } + row[7] = keyAddress; + row[8] = dirProperties; + row[9] = application; + if (CompilerConstants.IntegerNotSet != sequence) + { + row[10] = sequence; + } + row[11] = log; + row[12] = siteId; + } + } + + /// + /// Parses a HTTP Header element. + /// + /// Element to parse. + /// Type of the parent. + /// Id of the parent. + private void ParseHttpHeaderElement(XElement node, HttpHeaderParentType parentType, string parent) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + Identifier id = null; + string headerName = null; + string headerValue = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifier(sourceLineNumbers, attrib); + break; + case "Name": + headerName = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Value": + headerValue = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == headerName) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Name")); + } + else if (null == id) + { + id = this.Core.CreateIdentifierFromFilename(headerName); + } + + this.Core.ParseForExtensionElements(node); + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsHttpHeader", id); + row[1] = (int)parentType; + row[2] = parent; + row[3] = headerName; + row[4] = headerValue; + row[5] = 0; + row[6] = null; + } + + /// + /// Parses a virtual directory element. + /// + /// Element to parse. + /// Identifier of parent component. + /// Identifier of parent web site. + /// Alias of the parent web site. + private void ParseWebVirtualDirElement(XElement node, string componentId, string parentWeb, string parentAlias) + { + SourceLineNumber sourceLineNumbers = Preprocessor.GetSourceLineNumbers(node); + string id = null; + string alias = null; + string application = null; + string directory = null; + string dirProperties = null; + + foreach (XAttribute attrib in node.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + break; + case "Alias": + alias = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "Directory": + directory = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "Directory", directory); + break; + case "DirProperties": + dirProperties = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebApplication": + application = this.Core.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "WebSite": + if (null != parentWeb) + { + this.Core.OnMessage(IIsErrors.WebSiteAttributeUnderWebSite(sourceLineNumbers, node.Name.LocalName)); + } + + parentWeb = this.Core.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebSite", parentWeb); + break; + default: + this.Core.UnexpectedAttribute(node, attrib); + break; + } + } + else + { + this.Core.ParseExtensionAttribute(node, attrib); + } + } + + if (null == id) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Id")); + } + + if (null == alias) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Alias")); + } + else if (-1 != alias.IndexOf("\\", StringComparison.Ordinal)) + { + this.Core.OnMessage(IIsErrors.IllegalCharacterInAttributeValue(sourceLineNumbers, node.Name.LocalName, "Alias", alias, '\\')); + } + + if (null == directory) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "Directory")); + } + + if (null == parentWeb) + { + this.Core.OnMessage(WixErrors.ExpectedAttribute(sourceLineNumbers, node.Name.LocalName, "WebSite")); + } + + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(sourceLineNumbers, node.Name.LocalName)); + } + + if (null != parentAlias) + { + alias = String.Concat(parentAlias, "/", alias); + } + + foreach (XElement child in node.Elements()) + { + if (this.Namespace == child.Name.Namespace) + { + SourceLineNumber childSourceLineNumbers = Preprocessor.GetSourceLineNumbers(child); + switch (child.Name.LocalName) + { + case "WebApplication": + if (null != application) + { + this.Core.OnMessage(IIsErrors.WebApplicationAlreadySpecified(childSourceLineNumbers, node.Name.LocalName)); + } + + application = this.ParseWebApplicationElement(child); + break; + case "WebDirProperties": + if (null == componentId) + { + this.Core.OnMessage(IIsErrors.IllegalElementWithoutComponent(childSourceLineNumbers, child.Name.LocalName)); + } + + string childWebDirProperties = this.ParseWebDirPropertiesElement(child); + if (null == dirProperties) + { + dirProperties = childWebDirProperties; + } + else + { + this.Core.OnMessage(WixErrors.IllegalAttributeWhenNested(sourceLineNumbers, child.Name.LocalName, "DirProperties", child.Name.LocalName)); + } + break; + + case "WebError": + this.ParseWebErrorElement(child, WebErrorParentType.WebVirtualDir, id); + break; + case "WebVirtualDir": + this.ParseWebVirtualDirElement(child, componentId, parentWeb, alias); + break; + case "HttpHeader": + this.ParseHttpHeaderElement(child, HttpHeaderParentType.WebVirtualDir, id); + break; + case "MimeMap": + this.ParseMimeMapElement(child, id, MimeMapParentType.WebVirtualDir); + break; + default: + this.Core.UnexpectedElement(node, child); + break; + } + } + else + { + this.Core.ParseExtensionElement(node, child); + } + } + + if (null != dirProperties) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebDirProperties", dirProperties); + } + + if (null != application) + { + this.Core.CreateSimpleReference(sourceLineNumbers, "IIsWebApplication", application); + } + + // Reference ConfigureIIs since nothing will happen without it + this.Core.CreateSimpleReference(sourceLineNumbers, "CustomAction", "ConfigureIIs"); + + if (!this.Core.EncounteredError) + { + Row row = this.Core.CreateRow(sourceLineNumbers, "IIsWebVirtualDir"); + row[0] = id; + row[1] = componentId; + row[2] = parentWeb; + row[3] = alias; + row[4] = directory; + row[5] = dirProperties; + row[6] = application; + } + } + } +} diff --git a/src/wixext/IIsDecompiler.cs b/src/wixext/IIsDecompiler.cs new file mode 100644 index 00000000..8b3b8248 --- /dev/null +++ b/src/wixext/IIsDecompiler.cs @@ -0,0 +1,1547 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +namespace WixToolset.Extensions +{ + using System; + using System.Collections; + using System.Globalization; + using WixToolset.Data; + using WixToolset.Extensibility; + using IIs = WixToolset.Extensions.Serialize.IIs; + using Wix = WixToolset.Data.Serialize; + + /// + /// The decompiler for the WiX Toolset Internet Information Services Extension. + /// + public sealed class IIsDecompiler : DecompilerExtension + { + /// + /// Creates a decompiler for IIs Extension. + /// + public IIsDecompiler() + { + this.TableDefinitions = IIsExtensionData.GetExtensionTableDefinitions(); + } + + /// + /// Get the extensions library to be removed. + /// + /// Table definitions for library. + /// Library to remove from decompiled output. + public override Library GetLibraryToRemove(TableDefinitionCollection tableDefinitions) + { + return IIsExtensionData.GetExtensionLibrary(tableDefinitions); + } + + /// + /// Decompiles an extension table. + /// + /// The table to decompile. + public override void DecompileTable(Table table) + { + switch (table.Name) + { + case "Certificate": + this.DecompileCertificateTable(table); + break; + case "CertificateHash": + // There is nothing to do for this table, it contains no authored data + // to be decompiled. + break; + case "IIsAppPool": + this.DecompileIIsAppPoolTable(table); + break; + case "IIsFilter": + this.DecompileIIsFilterTable(table); + break; + case "IIsProperty": + this.DecompileIIsPropertyTable(table); + break; + case "IIsHttpHeader": + this.DecompileIIsHttpHeaderTable(table); + break; + case "IIsMimeMap": + this.DecompileIIsMimeMapTable(table); + break; + case "IIsWebAddress": + this.DecompileIIsWebAddressTable(table); + break; + case "IIsWebApplication": + this.DecompileIIsWebApplicationTable(table); + break; + case "IIsWebDirProperties": + this.DecompileIIsWebDirPropertiesTable(table); + break; + case "IIsWebError": + this.DecompileIIsWebErrorTable(table); + break; + case "IIsWebLog": + this.DecompileIIsWebLogTable(table); + break; + case "IIsWebServiceExtension": + this.DecompileIIsWebServiceExtensionTable(table); + break; + case "IIsWebSite": + this.DecompileIIsWebSiteTable(table); + break; + case "IIsWebVirtualDir": + this.DecompileIIsWebVirtualDirTable(table); + break; + case "IIsWebSiteCertificates": + this.DecompileIIsWebSiteCertificatesTable(table); + break; + default: + base.DecompileTable(table); + break; + } + } + + /// + /// Finalize decompilation. + /// + /// The collection of all tables. + public override void Finish(TableIndexedCollection tables) + { + this.FinalizeIIsMimeMapTable(tables); + this.FinalizeIIsHttpHeaderTable(tables); + this.FinalizeIIsWebApplicationTable(tables); + this.FinalizeIIsWebErrorTable(tables); + this.FinalizeIIsWebVirtualDirTable(tables); + this.FinalizeIIsWebSiteCertificatesTable(tables); + this.FinalizeWebAddressTable(tables); + } + + /// + /// Decompile the Certificate table. + /// + /// The table to decompile. + private void DecompileCertificateTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.Certificate certificate = new IIs.Certificate(); + + certificate.Id = (string)row[0]; + certificate.Name = (string)row[2]; + + switch ((int)row[3]) + { + case 1: + certificate.StoreLocation = IIs.Certificate.StoreLocationType.currentUser; + break; + case 2: + certificate.StoreLocation = IIs.Certificate.StoreLocationType.localMachine; + break; + default: + // TODO: warn + break; + } + + switch ((string)row[4]) + { + case "CA": + certificate.StoreName = IIs.Certificate.StoreNameType.ca; + break; + case "MY": + certificate.StoreName = IIs.Certificate.StoreNameType.my; + break; + case "REQUEST": + certificate.StoreName = IIs.Certificate.StoreNameType.request; + break; + case "Root": + certificate.StoreName = IIs.Certificate.StoreNameType.root; + break; + case "AddressBook": + certificate.StoreName = IIs.Certificate.StoreNameType.otherPeople; + break; + case "TrustedPeople": + certificate.StoreName = IIs.Certificate.StoreNameType.trustedPeople; + break; + case "TrustedPublisher": + certificate.StoreName = IIs.Certificate.StoreNameType.trustedPublisher; + break; + default: + // TODO: warn + break; + } + + int attribute = (int)row[5]; + + if (0x1 == (attribute & 0x1)) + { + certificate.Request = IIs.YesNoType.yes; + } + + if (0x2 == (attribute & 0x2)) + { + if (null != row[6]) + { + certificate.BinaryKey = (string)row[6]; + } + else + { + // TODO: warn about expected value in row 5 + } + } + else if (null != row[7]) + { + certificate.CertificatePath = (string)row[7]; + } + + if (0x4 == (attribute & 0x4)) + { + certificate.Overwrite = IIs.YesNoType.yes; + } + + if (null != row[8]) + { + certificate.PFXPassword = (string)row[8]; + } + + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[1]); + if (null != component) + { + component.AddChild(certificate); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[1], "Component")); + } + } + } + + /// + /// Decompile the IIsAppPool table. + /// + /// The table to decompile. + private void DecompileIIsAppPoolTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebAppPool webAppPool = new IIs.WebAppPool(); + + webAppPool.Id = (string)row[0]; + + webAppPool.Name = (string)row[1]; + + switch ((int)row[3] & 0x1F) + { + case 1: + webAppPool.Identity = IIs.WebAppPool.IdentityType.networkService; + break; + case 2: + webAppPool.Identity = IIs.WebAppPool.IdentityType.localService; + break; + case 4: + webAppPool.Identity = IIs.WebAppPool.IdentityType.localSystem; + break; + case 8: + webAppPool.Identity = IIs.WebAppPool.IdentityType.other; + break; + case 0x10: + webAppPool.Identity = IIs.WebAppPool.IdentityType.applicationPoolIdentity; + break; + default: + // TODO: warn + break; + } + + if (null != row[4]) + { + webAppPool.User = (string)row[4]; + } + + if (null != row[5]) + { + webAppPool.RecycleMinutes = (int)row[5]; + } + + if (null != row[6]) + { + webAppPool.RecycleRequests = (int)row[6]; + } + + if (null != row[7]) + { + string[] recycleTimeValues = ((string)row[7]).Split(','); + + foreach (string recycleTimeValue in recycleTimeValues) + { + IIs.RecycleTime recycleTime = new IIs.RecycleTime(); + + recycleTime.Value = recycleTimeValue; + + webAppPool.AddChild(recycleTime); + } + } + + if (null != row[8]) + { + webAppPool.IdleTimeout = (int)row[8]; + } + + if (null != row[9]) + { + webAppPool.QueueLimit = (int)row[9]; + } + + if (null != row[10]) + { + string[] cpuMon = ((string)row[10]).Split(','); + + if (0 < cpuMon.Length && "0" != cpuMon[0]) + { + webAppPool.MaxCpuUsage = Convert.ToInt32(cpuMon[0], CultureInfo.InvariantCulture); + } + + if (1 < cpuMon.Length) + { + webAppPool.RefreshCpu = Convert.ToInt32(cpuMon[1], CultureInfo.InvariantCulture); + } + + if (2 < cpuMon.Length) + { + switch (Convert.ToInt32(cpuMon[2], CultureInfo.InvariantCulture)) + { + case 0: + webAppPool.CpuAction = IIs.WebAppPool.CpuActionType.none; + break; + case 1: + webAppPool.CpuAction = IIs.WebAppPool.CpuActionType.shutdown; + break; + default: + // TODO: warn + break; + } + } + + if (3 < cpuMon.Length) + { + // TODO: warn + } + } + + if (null != row[11]) + { + webAppPool.MaxWorkerProcesses = (int)row[11]; + } + + if (null != row[12]) + { + webAppPool.VirtualMemory = (int)row[12]; + } + + if (null != row[13]) + { + webAppPool.PrivateMemory = (int)row[13]; + } + + if (null != row[14]) + { + webAppPool.ManagedRuntimeVersion = (string)row[14]; + } + + if (null != row[15]) + { + webAppPool.ManagedPipelineMode = (string)row[15]; + } + + if (null != row[2]) + { + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[2]); + + if (null != component) + { + component.AddChild(webAppPool); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[2], "Component")); + } + } + else + { + this.Core.RootElement.AddChild(webAppPool); + } + } + } + + /// + /// Decompile the IIsProperty table. + /// + /// The table to decompile. + private void DecompileIIsPropertyTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebProperty webProperty = new IIs.WebProperty(); + + switch ((string)row[0]) + { + case "ETagChangeNumber": + webProperty.Id = IIs.WebProperty.IdType.ETagChangeNumber; + break; + case "IIs5IsolationMode": + webProperty.Id = IIs.WebProperty.IdType.IIs5IsolationMode; + break; + case "LogInUTF8": + webProperty.Id = IIs.WebProperty.IdType.LogInUTF8; + break; + case "MaxGlobalBandwidth": + webProperty.Id = IIs.WebProperty.IdType.MaxGlobalBandwidth; + break; + } + + if (0 != (int)row[2]) + { + // TODO: warn about value in unused column + } + + if (null != row[3]) + { + webProperty.Value = (string)row[3]; + } + + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[1]); + if (null != component) + { + component.AddChild(webProperty); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[1], "Component")); + } + } + } + + /// + /// Decompile the IIsHttpHeader table. + /// + /// The table to decompile. + private void DecompileIIsHttpHeaderTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.HttpHeader httpHeader = new IIs.HttpHeader(); + + httpHeader.Name = (string)row[3]; + + // the ParentType and Parent columns are handled in FinalizeIIsHttpHeaderTable + + httpHeader.Value = (string)row[4]; + + this.Core.IndexElement(row, httpHeader); + } + } + + /// + /// Decompile the IIsMimeMap table. + /// + /// The table to decompile. + private void DecompileIIsMimeMapTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.MimeMap mimeMap = new IIs.MimeMap(); + + mimeMap.Id = (string)row[0]; + + // the ParentType and ParentValue columns are handled in FinalizeIIsMimeMapTable + + mimeMap.Type = (string)row[3]; + + mimeMap.Extension = (string)row[4]; + + this.Core.IndexElement(row, mimeMap); + } + } + + /// + /// Decompile the IIsWebAddress table. + /// + /// The table to decompile. + private void DecompileIIsWebAddressTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebAddress webAddress = new IIs.WebAddress(); + + webAddress.Id = (string)row[0]; + + if (null != row[2]) + { + webAddress.IP = (string)row[2]; + } + + webAddress.Port = (string)row[3]; + + if (null != row[4]) + { + webAddress.Header = (string)row[4]; + } + + if (null != row[5] && 1 == (int)row[5]) + { + webAddress.Secure = IIs.YesNoType.yes; + } + + this.Core.IndexElement(row, webAddress); + } + } + + /// + /// Decompile the IIsWebApplication table. + /// + /// The table to decompile. + private void DecompileIIsWebApplicationTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebApplication webApplication = new IIs.WebApplication(); + + webApplication.Id = (string)row[0]; + + webApplication.Name = (string)row[1]; + + // these are not listed incorrectly - the order is low, high, medium + switch ((int)row[2]) + { + case 0: + webApplication.Isolation = IIs.WebApplication.IsolationType.low; + break; + case 1: + webApplication.Isolation = IIs.WebApplication.IsolationType.high; + break; + case 2: + webApplication.Isolation = IIs.WebApplication.IsolationType.medium; + break; + default: + // TODO: warn + break; + } + + if (null != row[3]) + { + switch ((int)row[3]) + { + case 0: + webApplication.AllowSessions = IIs.YesNoDefaultType.no; + break; + case 1: + webApplication.AllowSessions = IIs.YesNoDefaultType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[4]) + { + webApplication.SessionTimeout = (int)row[4]; + } + + if (null != row[5]) + { + switch ((int)row[5]) + { + case 0: + webApplication.Buffer = IIs.YesNoDefaultType.no; + break; + case 1: + webApplication.Buffer = IIs.YesNoDefaultType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[6]) + { + switch ((int)row[6]) + { + case 0: + webApplication.ParentPaths = IIs.YesNoDefaultType.no; + break; + case 1: + webApplication.ParentPaths = IIs.YesNoDefaultType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[7]) + { + switch ((string)row[7]) + { + case "JScript": + webApplication.DefaultScript = IIs.WebApplication.DefaultScriptType.JScript; + break; + case "VBScript": + webApplication.DefaultScript = IIs.WebApplication.DefaultScriptType.VBScript; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[8]) + { + webApplication.ScriptTimeout = (int)row[8]; + } + + if (null != row[9]) + { + switch ((int)row[9]) + { + case 0: + webApplication.ServerDebugging = IIs.YesNoDefaultType.no; + break; + case 1: + webApplication.ServerDebugging = IIs.YesNoDefaultType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[10]) + { + switch ((int)row[10]) + { + case 0: + webApplication.ClientDebugging = IIs.YesNoDefaultType.no; + break; + case 1: + webApplication.ClientDebugging = IIs.YesNoDefaultType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[11]) + { + webApplication.WebAppPool = (string)row[11]; + } + + this.Core.IndexElement(row, webApplication); + } + } + + /// + /// Decompile the IIsWebDirProperties table. + /// + /// The table to decompile. + private void DecompileIIsWebDirPropertiesTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebDirProperties webDirProperties = new IIs.WebDirProperties(); + + webDirProperties.Id = (string)row[0]; + + if (null != row[1]) + { + int access = (int)row[1]; + + if (0x1 == (access & 0x1)) + { + webDirProperties.Read = IIs.YesNoType.yes; + } + + if (0x2 == (access & 0x2)) + { + webDirProperties.Write = IIs.YesNoType.yes; + } + + if (0x4 == (access & 0x4)) + { + webDirProperties.Execute = IIs.YesNoType.yes; + } + + if (0x200 == (access & 0x200)) + { + webDirProperties.Script = IIs.YesNoType.yes; + } + } + + if (null != row[2]) + { + int authorization = (int)row[2]; + + if (0x1 == (authorization & 0x1)) + { + webDirProperties.AnonymousAccess = IIs.YesNoType.yes; + } + else // set one of the properties to 'no' to force the output value to be '0' if not other attributes are set + { + webDirProperties.AnonymousAccess = IIs.YesNoType.no; + } + + if (0x2 == (authorization & 0x2)) + { + webDirProperties.BasicAuthentication = IIs.YesNoType.yes; + } + + if (0x4 == (authorization & 0x4)) + { + webDirProperties.WindowsAuthentication = IIs.YesNoType.yes; + } + + if (0x10 == (authorization & 0x10)) + { + webDirProperties.DigestAuthentication = IIs.YesNoType.yes; + } + + if (0x40 == (authorization & 0x40)) + { + webDirProperties.PassportAuthentication = IIs.YesNoType.yes; + } + } + + if (null != row[3]) + { + webDirProperties.AnonymousUser = (string)row[3]; + } + + if (null != row[4] && 1 == (int)row[4]) + { + webDirProperties.IIsControlledPassword = IIs.YesNoType.yes; + } + + if (null != row[5]) + { + switch ((int)row[5]) + { + case 0: + webDirProperties.LogVisits = IIs.YesNoType.no; + break; + case 1: + webDirProperties.LogVisits = IIs.YesNoType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[6]) + { + switch ((int)row[6]) + { + case 0: + webDirProperties.Index = IIs.YesNoType.no; + break; + case 1: + webDirProperties.Index = IIs.YesNoType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[7]) + { + webDirProperties.DefaultDocuments = (string)row[7]; + } + + if (null != row[8]) + { + switch ((int)row[8]) + { + case 0: + webDirProperties.AspDetailedError = IIs.YesNoType.no; + break; + case 1: + webDirProperties.AspDetailedError = IIs.YesNoType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[9]) + { + webDirProperties.HttpExpires = (string)row[9]; + } + + if (null != row[10]) + { + // force the value to be a positive number + webDirProperties.CacheControlMaxAge = unchecked((uint)(int)row[10]); + } + + if (null != row[11]) + { + webDirProperties.CacheControlCustom = (string)row[11]; + } + + if (null != row[12]) + { + switch ((int)row[8]) + { + case 0: + webDirProperties.ClearCustomError = IIs.YesNoType.no; + break; + case 1: + webDirProperties.ClearCustomError = IIs.YesNoType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[13]) + { + int accessSSLFlags = (int)row[13]; + + if (0x8 == (accessSSLFlags & 0x8)) + { + webDirProperties.AccessSSL = IIs.YesNoType.yes; + } + + if (0x20 == (accessSSLFlags & 0x20)) + { + webDirProperties.AccessSSLNegotiateCert = IIs.YesNoType.yes; + } + + if (0x40 == (accessSSLFlags & 0x40)) + { + webDirProperties.AccessSSLRequireCert = IIs.YesNoType.yes; + } + + if (0x80 == (accessSSLFlags & 0x80)) + { + webDirProperties.AccessSSLMapCert = IIs.YesNoType.yes; + } + + if (0x100 == (accessSSLFlags & 0x100)) + { + webDirProperties.AccessSSL128 = IIs.YesNoType.yes; + } + } + + if (null != row[14]) + { + webDirProperties.AuthenticationProviders = (string)row[14]; + } + + this.Core.RootElement.AddChild(webDirProperties); + } + } + + /// + /// Decompile the IIsWebError table. + /// + /// The table to decompile. + private void DecompileIIsWebErrorTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebError webError = new IIs.WebError(); + + webError.ErrorCode = (int)row[0]; + + webError.SubCode = (int)row[1]; + + // the ParentType and ParentValue columns are handled in FinalizeIIsWebErrorTable + + if (null != row[4]) + { + webError.File = (string)row[4]; + } + + if (null != row[5]) + { + webError.URL = (string)row[5]; + } + + this.Core.IndexElement(row, webError); + } + } + + /// + /// Decompile the IIsFilter table. + /// + /// The table to decompile. + private void DecompileIIsFilterTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebFilter webFilter = new IIs.WebFilter(); + + webFilter.Id = (string)row[0]; + + webFilter.Name = (string)row[1]; + + if (null != row[3]) + { + webFilter.Path = (string)row[3]; + } + + if (null != row[5]) + { + webFilter.Description = (string)row[5]; + } + + webFilter.Flags = (int)row[6]; + + if (null != row[7]) + { + switch ((int)row[7]) + { + case (-1): + webFilter.LoadOrder = "last"; + break; + case 0: + webFilter.LoadOrder = "first"; + break; + default: + webFilter.LoadOrder = Convert.ToString((int)row[7], CultureInfo.InvariantCulture); + break; + } + } + + if (null != row[4]) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[4]); + + if (null != webSite) + { + webSite.AddChild(webFilter); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Web_", (string)row[4], "IIsWebSite")); + } + } + else // Component parent + { + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[2]); + + if (null != component) + { + component.AddChild(webFilter); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[2], "Component")); + } + } + } + } + + /// + /// Decompile the IIsWebLog table. + /// + /// The table to decompile. + private void DecompileIIsWebLogTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebLog webLog = new IIs.WebLog(); + + webLog.Id = (string)row[0]; + + switch ((string)row[1]) + { + case "Microsoft IIS Log File Format": + webLog.Type = IIs.WebLog.TypeType.IIS; + break; + case "NCSA Common Log File Format": + webLog.Type = IIs.WebLog.TypeType.NCSA; + break; + case "none": + webLog.Type = IIs.WebLog.TypeType.none; + break; + case "ODBC Logging": + webLog.Type = IIs.WebLog.TypeType.ODBC; + break; + case "W3C Extended Log File Format": + webLog.Type = IIs.WebLog.TypeType.W3C; + break; + default: + // TODO: warn + break; + } + + this.Core.RootElement.AddChild(webLog); + } + } + + /// + /// Decompile the IIsWebServiceExtension table. + /// + /// The table to decompile. + private void DecompileIIsWebServiceExtensionTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebServiceExtension webServiceExtension = new IIs.WebServiceExtension(); + + webServiceExtension.Id = (string)row[0]; + + webServiceExtension.File = (string)row[2]; + + if (null != row[3]) + { + webServiceExtension.Description = (string)row[3]; + } + + if (null != row[4]) + { + webServiceExtension.Group = (string)row[4]; + } + + int attributes = (int)row[5]; + + if (0x1 == (attributes & 0x1)) + { + webServiceExtension.Allow = IIs.YesNoType.yes; + } + else + { + webServiceExtension.Allow = IIs.YesNoType.no; + } + + if (0x2 == (attributes & 0x2)) + { + webServiceExtension.UIDeletable = IIs.YesNoType.yes; + } + + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[1]); + if (null != component) + { + component.AddChild(webServiceExtension); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[1], "Component")); + } + } + } + + /// + /// Decompile the IIsWebSite table. + /// + /// The table to decompile. + private void DecompileIIsWebSiteTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebSite webSite = new IIs.WebSite(); + + webSite.Id = (string)row[0]; + + if (null != row[2]) + { + webSite.Description = (string)row[2]; + } + + if (null != row[3]) + { + webSite.ConnectionTimeout = (int)row[3]; + } + + if (null != row[4]) + { + webSite.Directory = (string)row[4]; + } + + if (null != row[5]) + { + switch ((int)row[5]) + { + case 0: + // this is the default + break; + case 1: + webSite.StartOnInstall = IIs.YesNoType.yes; + break; + case 2: + webSite.AutoStart = IIs.YesNoType.yes; + break; + default: + // TODO: warn + break; + } + } + + if (null != row[6]) + { + int attributes = (int)row[6]; + + if (0x2 == (attributes & 0x2)) + { + webSite.ConfigureIfExists = IIs.YesNoType.no; + } + } + + // the KeyAddress_ column is handled in FinalizeWebAddressTable + + if (null != row[8]) + { + webSite.DirProperties = (string)row[8]; + } + + // the Application_ column is handled in FinalizeIIsWebApplicationTable + + if (null != row[10]) + { + if (-1 != (int)row[10]) + { + webSite.Sequence = (int)row[10]; + } + } + + if (null != row[11]) + { + webSite.WebLog = (string)row[11]; + } + + if (null != row[12]) + { + webSite.SiteId = (string)row[12]; + } + + if (null != row[1]) + { + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[1]); + + if (null != component) + { + component.AddChild(webSite); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, table.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[1], "Component")); + } + } + else + { + this.Core.RootElement.AddChild(webSite); + } + this.Core.IndexElement(row, webSite); + } + } + + /// + /// Decompile the IIsWebVirtualDir table. + /// + /// The table to decompile. + private void DecompileIIsWebVirtualDirTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.WebVirtualDir webVirtualDir = new IIs.WebVirtualDir(); + + webVirtualDir.Id = (string)row[0]; + + // the Component_ and Web_ columns are handled in FinalizeIIsWebVirtualDirTable + + webVirtualDir.Alias = (string)row[3]; + + webVirtualDir.Directory = (string)row[4]; + + if (null != row[5]) + { + webVirtualDir.DirProperties = (string)row[5]; + } + + // the Application_ column is handled in FinalizeIIsWebApplicationTable + + this.Core.IndexElement(row, webVirtualDir); + } + } + + /// + /// Decompile the IIsWebSiteCertificates table. + /// + /// The table to decompile. + private void DecompileIIsWebSiteCertificatesTable(Table table) + { + foreach (Row row in table.Rows) + { + IIs.CertificateRef certificateRef = new IIs.CertificateRef(); + + certificateRef.Id = (string)row[1]; + + this.Core.IndexElement(row, certificateRef); + } + } + + /// + /// Finalize the IIsHttpHeader table. + /// + /// The collection of all tables. + /// + /// The IIsHttpHeader table supports multiple parent types so no foreign key + /// is declared and thus nesting must be done late. + /// + private void FinalizeIIsHttpHeaderTable(TableIndexedCollection tables) + { + Table iisHttpHeaderTable = tables["IIsHttpHeader"]; + + if (null != iisHttpHeaderTable) + { + foreach (Row row in iisHttpHeaderTable.Rows) + { + IIs.HttpHeader httpHeader = (IIs.HttpHeader)this.Core.GetIndexedElement(row); + + if (1 == (int)row[1]) + { + IIs.WebVirtualDir webVirtualDir = (IIs.WebVirtualDir)this.Core.GetIndexedElement("IIsWebVirtualDir", (string)row[2]); + if (null != webVirtualDir) + { + webVirtualDir.AddChild(httpHeader); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisHttpHeaderTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "ParentValue", (string)row[2], "IIsWebVirtualDir")); + } + } + else if (2 == (int)row[1]) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[2]); + if (null != webSite) + { + webSite.AddChild(httpHeader); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisHttpHeaderTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "ParentValue", (string)row[2], "IIsWebSite")); + } + } + } + } + } + + /// + /// Finalize the IIsMimeMap table. + /// + /// The collection of all tables. + /// + /// The IIsMimeMap table supports multiple parent types so no foreign key + /// is declared and thus nesting must be done late. + /// + private void FinalizeIIsMimeMapTable(TableIndexedCollection tables) + { + Table iisMimeMapTable = tables["IIsMimeMap"]; + + if (null != iisMimeMapTable) + { + foreach (Row row in iisMimeMapTable.Rows) + { + IIs.MimeMap mimeMap = (IIs.MimeMap)this.Core.GetIndexedElement(row); + + if (2 < (int)row[1] || 0 >= (int)row[1]) + { + // TODO: warn about unknown parent type + } + + IIs.WebVirtualDir webVirtualDir = (IIs.WebVirtualDir)this.Core.GetIndexedElement("IIsWebVirtualDir", (string)row[2]); + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[2]); + if (null != webVirtualDir) + { + webVirtualDir.AddChild(mimeMap); + } + else if (null != webSite) + { + webSite.AddChild(mimeMap); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisMimeMapTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "ParentValue", (string)row[2], "IIsWebVirtualDir")); + } + } + } + } + + /// + /// Finalize the IIsWebApplication table. + /// + /// The collection of all tables. + /// + /// Since WebApplication elements may nest under a specific WebSite or + /// WebVirtualDir (or just the root element), the nesting must be done late. + /// + private void FinalizeIIsWebApplicationTable(TableIndexedCollection tables) + { + Table iisWebApplicationTable = tables["IIsWebApplication"]; + Table iisWebSiteTable = tables["IIsWebSite"]; + Table iisWebVirtualDirTable = tables["IIsWebVirtualDir"]; + + Hashtable addedWebApplications = new Hashtable(); + + if (null != iisWebSiteTable) + { + foreach (Row row in iisWebSiteTable.Rows) + { + if (null != row[9]) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement(row); + + IIs.WebApplication webApplication = (IIs.WebApplication)this.Core.GetIndexedElement("IIsWebApplication", (string)row[9]); + if (null != webApplication) + { + webSite.AddChild(webApplication); + addedWebApplications[webApplication] = null; + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebSiteTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Application_", (string)row[9], "IIsWebApplication")); + } + } + } + } + + if (null != iisWebVirtualDirTable) + { + foreach (Row row in iisWebVirtualDirTable.Rows) + { + if (null != row[6]) + { + IIs.WebVirtualDir webVirtualDir = (IIs.WebVirtualDir)this.Core.GetIndexedElement(row); + + IIs.WebApplication webApplication = (IIs.WebApplication)this.Core.GetIndexedElement("IIsWebApplication", (string)row[6]); + if (null != webApplication) + { + webVirtualDir.AddChild(webApplication); + addedWebApplications[webApplication] = null; + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebVirtualDirTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Application_", (string)row[6], "IIsWebApplication")); + } + } + } + } + + if (null != iisWebApplicationTable) + { + foreach (Row row in iisWebApplicationTable.Rows) + { + IIs.WebApplication webApplication = (IIs.WebApplication)this.Core.GetIndexedElement(row); + + if (!addedWebApplications.Contains(webApplication)) + { + this.Core.RootElement.AddChild(webApplication); + } + } + } + } + + /// + /// Finalize the IIsWebError table. + /// + /// The collection of all tables. + /// + /// Since there is no foreign key relationship declared for this table + /// (because it takes various parent types), it must be nested late. + /// + private void FinalizeIIsWebErrorTable(TableIndexedCollection tables) + { + Table iisWebErrorTable = tables["IIsWebError"]; + + if (null != iisWebErrorTable) + { + foreach (Row row in iisWebErrorTable.Rows) + { + IIs.WebError webError = (IIs.WebError)this.Core.GetIndexedElement(row); + + if (1 == (int)row[2]) // WebVirtualDir parent + { + IIs.WebVirtualDir webVirtualDir = (IIs.WebVirtualDir)this.Core.GetIndexedElement("IIsWebVirtualDir", (string)row[3]); + + if (null != webVirtualDir) + { + webVirtualDir.AddChild(webError); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebErrorTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "ParentValue", (string)row[3], "IIsWebVirtualDir")); + } + } + else if (2 == (int)row[2]) // WebSite parent + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[3]); + + if (null != webSite) + { + webSite.AddChild(webError); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebErrorTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "ParentValue", (string)row[3], "IIsWebSite")); + } + } + else + { + // TODO: warn unknown parent type + } + } + } + } + + /// + /// Finalize the IIsWebVirtualDir table. + /// + /// The collection of all tables. + /// + /// WebVirtualDir elements nest under either a WebSite or component + /// depending upon whether the component in the IIsWebVirtualDir row + /// is the same as the one in the parent IIsWebSite row. + /// + private void FinalizeIIsWebVirtualDirTable(TableIndexedCollection tables) + { + Table iisWebSiteTable = tables["IIsWebSite"]; + Table iisWebVirtualDirTable = tables["IIsWebVirtualDir"]; + + Hashtable iisWebSiteRows = new Hashtable(); + + // index the IIsWebSite rows by their primary keys + if (null != iisWebSiteTable) + { + foreach (Row row in iisWebSiteTable.Rows) + { + iisWebSiteRows.Add(row[0], row); + } + } + + if (null != iisWebVirtualDirTable) + { + foreach (Row row in iisWebVirtualDirTable.Rows) + { + IIs.WebVirtualDir webVirtualDir = (IIs.WebVirtualDir)this.Core.GetIndexedElement(row); + Row iisWebSiteRow = (Row)iisWebSiteRows[row[2]]; + + if (null != iisWebSiteRow) + { + if ((string)iisWebSiteRow[1] == (string)row[1]) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement(iisWebSiteRow); + + webSite.AddChild(webVirtualDir); + } + else + { + Wix.Component component = (Wix.Component)this.Core.GetIndexedElement("Component", (string)row[1]); + + if (null != component) + { + webVirtualDir.WebSite = (string)row[2]; + component.AddChild(webVirtualDir); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebVirtualDirTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Component_", (string)row[1], "Component")); + } + } + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebVirtualDirTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Web_", (string)row[2], "IIsWebSite")); + } + } + } + } + + /// + /// Finalize the IIsWebSiteCertificates table. + /// + /// The collection of all tables. + /// + /// This table creates CertificateRef elements which nest under WebSite + /// elements. + /// + private void FinalizeIIsWebSiteCertificatesTable(TableIndexedCollection tables) + { + Table IIsWebSiteCertificatesTable = tables["IIsWebSiteCertificates"]; + + if (null != IIsWebSiteCertificatesTable) + { + foreach (Row row in IIsWebSiteCertificatesTable.Rows) + { + IIs.CertificateRef certificateRef = (IIs.CertificateRef)this.Core.GetIndexedElement(row); + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[0]); + + if (null != webSite) + { + webSite.AddChild(certificateRef); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, IIsWebSiteCertificatesTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Web_", (string)row[0], "IIsWebSite")); + } + } + } + } + + /// + /// Finalize the WebAddress table. + /// + /// The collection of all tables. + /// + /// There is a circular dependency between the WebAddress and WebSite + /// tables, so nesting must be handled here. + /// + private void FinalizeWebAddressTable(TableIndexedCollection tables) + { + Table iisWebAddressTable = tables["IIsWebAddress"]; + Table iisWebSiteTable = tables["IIsWebSite"]; + + Hashtable addedWebAddresses = new Hashtable(); + + if (null != iisWebSiteTable) + { + foreach (Row row in iisWebSiteTable.Rows) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement(row); + + IIs.WebAddress webAddress = (IIs.WebAddress)this.Core.GetIndexedElement("IIsWebAddress", (string)row[7]); + if (null != webAddress) + { + webSite.AddChild(webAddress); + addedWebAddresses[webAddress] = null; + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebSiteTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "KeyAddress_", (string)row[7], "IIsWebAddress")); + } + } + } + + if (null != iisWebAddressTable) + { + foreach (Row row in iisWebAddressTable.Rows) + { + IIs.WebAddress webAddress = (IIs.WebAddress)this.Core.GetIndexedElement(row); + + if (!addedWebAddresses.Contains(webAddress)) + { + IIs.WebSite webSite = (IIs.WebSite)this.Core.GetIndexedElement("IIsWebSite", (string)row[1]); + + if (null != webSite) + { + webSite.AddChild(webAddress); + } + else + { + this.Core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, iisWebAddressTable.Name, row.GetPrimaryKey(DecompilerConstants.PrimaryKeyDelimiter), "Web_", (string)row[1], "IIsWebSite")); + } + } + } + } + } + } +} diff --git a/src/wixext/IIsExtensionData.cs b/src/wixext/IIsExtensionData.cs new file mode 100644 index 00000000..5b8bf564 --- /dev/null +++ b/src/wixext/IIsExtensionData.cs @@ -0,0 +1,64 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +namespace WixToolset.Extensions +{ + using System; + using System.Reflection; + using WixToolset.Data; + using WixToolset.Extensibility; + + /// + /// The WiX Toolset Internet Information Services Extension. + /// + public sealed class IIsExtensionData : ExtensionData + { + /// + /// Gets the default culture. + /// + /// The default culture. + public override string DefaultCulture + { + get { return "en-us"; } + } + + /// + /// Gets the optional table definitions for this extension. + /// + /// The optional table definitions for this extension. + public override TableDefinitionCollection TableDefinitions + { + get + { + return IIsExtensionData.GetExtensionTableDefinitions(); + } + } + + /// + /// Gets the library associated with this extension. + /// + /// The table definitions to use while loading the library. + /// The loaded library. + public override Library GetLibrary(TableDefinitionCollection tableDefinitions) + { + return IIsExtensionData.GetExtensionLibrary(tableDefinitions); + } + + /// + /// Internal mechanism to access the extension's table definitions. + /// + /// Extension's table definitions. + internal static TableDefinitionCollection GetExtensionTableDefinitions() + { + return ExtensionData.LoadTableDefinitionHelper(Assembly.GetExecutingAssembly(), "WixToolset.Extensions.Data.tables.xml"); + } + + /// + /// Internal mechanism to access the extension's library. + /// + /// Extension's library. + internal static Library GetExtensionLibrary(TableDefinitionCollection tableDefinitions) + { + return ExtensionData.LoadLibraryHelper(Assembly.GetExecutingAssembly(), "WixToolset.Extensions.Data.iis.wixlib", tableDefinitions); + } + } +} diff --git a/src/wixext/iis.xsd b/src/wixext/iis.xsd new file mode 100644 index 00000000..1c4bdafa --- /dev/null +++ b/src/wixext/iis.xsd @@ -0,0 +1,1104 @@ + + + + + + + + The source code schema for the WiX Toolset Internet Information Services Extension. + + + + + + + + + + + + + + WebDirProperties used by one or more WebSites. Lists properties common to IIS web sites and vroots. Corresponding properties can be viewed through the IIS Manager snap-in. One property entry can be reused by multiple sites or vroots using the Id field as a reference, using WebVirtualDir.DirProperties, WebSite.DirProperties, or WebDir.DirProperties. + + + + + + + + + + + Sets the Enable Anonymous Access checkbox, which maps anonymous users to a Windows user account. When setting this to 'yes' you should also provide the user account using the AnonymousUser attribute, and determine what setting to use for the IIsControlledPassword attribute. Defaults to 'no.' + + + + + Reference to the Id attribute on the User element to be used as the anonymous user for the directory. See the User element for more information. + + + + + Sets whether IIS should control the password used for the Windows account specified in the AnonymousUser attribute. Defaults to 'no.' + + + + + Sets the Windows Authentication option, which enables integrated Windows authentication to be used on the site. Defaults to 'no.' + + + + + Sets the Digest Authentication option, which allows using digest authentication with domain user accounts. Defaults to 'no.' + + + + + Sets the Basic Authentication option, which allows clients to provide credentials in plaintext over the wire. Defaults to 'no.' + + + + + Sets the Passport Authentication option, which allows clients to provide credentials via a .Net Passport account. Defaults to 'no.' + + + + + Sets whether visits to this site should be logged. Defaults to 'no.' + + + + + Sets the Index Resource option, which specifies whether this web directory should be indexed. Defaults to 'no.' + + + + + The list of default documents to set for this web directory, in comma-delimited format. + + + + + Sets the option for whether to send detailed ASP errors back to the client on script error. Default is 'no.' + + + + + Value to set the HttpExpires attribute to for a Web Dir in the metabase. + + + + + Integer value specifying the cache control maximum age value. + + + + + Custom HTTP 1.1 cache control directives. + + + + + Specifies whether IIs will return custom errors for this directory. + + + + + A value of true indicates that file access requires SSL file permission processing, with or without a client certificate. This corresponds to AccessSSL flag for AccessSSLFlags IIS metabase property. + + + + + A value of true indicates that file access requires SSL file permission processing with a minimum key size of 128 bits, with or without a client certificate. This corresponds to AccessSSL128 flag for AccessSSLFlags IIS metabase property. + + + + + This corresponds to AccessSSLMapCert flag for AccessSSLFlags IIS metabase property. + + + + + This corresponds to AccessSSLNegotiateCert flag for AccessSSLFlags IIS metabase property. + + + + + This corresponds to AccessSSLRequireCert flag for AccessSSLFlags IIS metabase property. + + + + + Comma delimited list, in order of precedence, of Windows authentication providers that IIS will attempt to use: NTLM, Kerberos, Negotiate, and others. + + + + + + + + Custom Web Errors used by WebSites and Virtual Directories. + + + You can only use error code and sub code combinations which are supported by IIS. Attempting to set a custom error for + an error code and sub code combination that is not supported by IIS (in the default list of error codes) will result in + an installation failure. + + + + + + + HTTP 1.1 error code. + + + + + Error sub code. Set to 0 to get the wild card "*". + + + + + File to be sent to the client for this error code and sub code. This can be formatted. For example: [#FileId]. + + + + + URL to be sent to the client for this error code and sub code. This can be formatted. + + + + + + + + Custom HTTP Header definition for IIS resources such as WebSite and WebVirtualDir. + + + + + Primary key for custom HTTP Header entry. This will default to the Name attribute. + + + + + Name of the custom HTTP Header. + + + + + Value for the custom HTTP Header. This attribute can contain a formatted string that is processed at install time to insert the values of properties using [PropertyName] syntax. Also supported are environment variables, file installation paths, and component installation directories; see Formatted for details. + + + + + + + + MimeMap definition for IIS resources. + + + + + Id for the MimeMap. + + + + + Mime-type covered by the MimeMap. + + + + + Extension covered by the MimeMap. Must begin with a dot. + + + + + + + + + + + IIs Filter for a Component + + + + + The unique Id for the web filter. + + + + + The name of the filter to be used in IIS. + + + + + + The path of the filter executable file. + This should usually be a value like '[!FileId]', where 'FileId' is the file identifier + of the filter executable file. + + + + + + + Specifies the parent website for this filter (if there is one). + If this is a global filter, then this attribute should not be specified. + + + + + + Description of the filter. + + + + + Sets the MD_FILTER_FLAGS metabase key for the filter. This must be an integer. See MSDN 'FilterFlags' documentation for more details. + + + + + + The legal values are "first", "last", or a number. + If a number is specified, it must be greater than 0. + + + + + + + + + Extension for WebApplication + + + + + usually a Property that resolves to short file name path + + + + + Extension being registered. Do not prefix with a '.' (e.g. you should use "html", not ".html"). To register for all extensions, use Extension="*". To register a wildcard application map (which handles all requests, even those for directories or files with no extension) omit the Extension attribute completely. + + + + + + + + + + + + + + + + + + + + IIS6 Application Pool + + + + + + + + Id of the AppPool. + + + + + Name of the AppPool to be shown in IIs. + + + + + User account to run the AppPool as. To use this, you must set the Identity attribute to 'other'. + + + + + How often, in minutes, you want the AppPool to be recycled. + + + + + How often, in requests, you want the AppPool to be recycled. + + + + + Specifies the amount of virtual memory (in KB) that a worker process can use before the worker process recycles. The maximum value supported for this attribute is 4,294,967 KB. + + + + + Specifies the amount of private memory (in KB) that a worker process can use before the worker process recycles. The maximum value supported for this attribute is 4,294,967 KB. + + + + + Shutdown worker process after being idle for (time in minutes). + + + + + Limit the kernel request queue (number of requests). + + + + + Maximum CPU usage (percent). + + + + + Refresh CPU usage numbers (in minutes). + + + + + Action taken when CPU exceeds maximum CPU use (as defined with MaxCpuUsage and RefreshCpu). + + + + + + + + + + + Maximum number of worker processes. + + + + + Identity you want the AppPool to run under (applicationPoolIdentity is only available on IIS7). Use the 'other' value in conjunction with the User attribute to specify non-standard user. + + + + + + + + + + + + + + + Specifies the request-processing mode that is used to process requests for managed content. Only available on IIS7, ignored on IIS6. + See http://www.iis.net/ConfigReference/system.applicationHost/applicationPools/applicationPoolDefaults for valid values. + This attribute may be set via a formatted Property (e.g. [MyProperty]). + + + + + + + Specifies the .NET Framework version to be used by the application pool. Only available on IIS7, ignored on IIS6. + See http://www.iis.net/ConfigReference/system.applicationHost/applicationPools/applicationPoolDefaults for valid values. + This attribute may be set via a formatted Property (e.g. [MyProperty]). + + + + + + + + + IIS6 Application Pool Recycle Times on 24 hour clock. + + + + + + + + + + + + + + + + Used to install and uninstall certificates. + + + + + + + + + + + Unique identifier for this certificate in the installation package. + + + + + + + Name of the certificate that will be installed or uninstalled in the specified store. + This attribute may be set via a formatted Property (e.g. [MyProperty]). + + + + + + + + + + Contains the certificates of certificate authorities that the user trusts to issue certificates to others. Certificates in these stores are normally supplied with the operating system or by the user's network administrator. + + + + + + + Use the "personal" value instead. + + + + + + + Contains personal certificates. These certificates will usually have an associated private key. This store is often + referred to as the "MY" certificate store. + + + + + + + + Contains the certificates of certificate authorities that the user trusts to issue certificates to others. Certificates in these stores are normally supplied with the operating system or by the user's network administrator. Certificates in this store are typically self-signed. + + + + + + + Contains the certificates of those that the user normally sends enveloped messages to or receives signed messages from. + See MSDN documentation for more information. + + + + + + + Contains the certificates of those directly trusted people and resources. + See MSDN documentation for more information. + + + + + + + Contains the certificates of those publishers who are trusted. + See MSDN documentation for more information. + + + + + + + + + + + + + + + + + + + This attribute controls whether the CertificatePath attribute is a path to a certificate file (Request='no') or the + certificate authority to request the certificate from (Request='yes'). + + + + + + + Reference to a Binary element that will store the certificate as a stream inside the package. This attribute cannot be specified with + the CertificatePath attribute. + + + + + + + + + + If the Request attribute is "no" then this attribute is the path to the certificate file outside of the package. + If the Request attribute is "yes" then this atribute is the certificate authority to request the certificate from. + This attribute may be set via a formatted Property (e.g. [MyProperty]). + + + + + + + If the Binary stream or path to the file outside of the package is a password protected PFX file, the password for that + PFX must be specified here. This attribute may be set via a formatted Property (e.g. [MyProperty]). + + + + + + + + + + Associates a certificate with the parent WebSite. The Certificate element should be + in the same Component as the parent WebSite. + + + + + + + + + + The identifier of the referenced Certificate. + + + + + + + + + + + + Here is an explanation of the acceptable values for each property and their meaning: + + + For the Ids IIs5IsolationMode and LogInUTF8, no value should be specified since + the presence of this property indicates that the setting should be set. + + + For the MaxGlobalBandwidth Id, the value should be specified in kilobytes. The + value should be a base 10 number. + + + ETagChangeNumber sets the machine-specific portion of ETag as a number. This value, + when synchronized across servers in a web farm, allows the web farm to return an + identical ETag for a given resource regardless of the server that handled the + request. The value should be a base 10 number. + + + + + IIS Properties + + + + + + + + + + + + + + + + The value to be used for the WebProperty specified in the Id attribute. See + the remarks section for information on acceptable values for each Id. + + + + + + + + + + + + + + Defines properties for a web application. These properties can be used for more than one application defined in a web site or vroot, by defining this element in a common location and referring to it by setting the WebApplication attribute of the WebSite and WebVirtualDir elements. + + + + + + + + + Sets the name of this application. + + + + + + Sets the application isolation level for this application for pre-IIS 6 applications. + + + + + + + + Means the application executes within the IIS process. + + + + + + + Executes pooled in a separate process. + + + + + + + Means execution alone in a separate process. + + + + + + + + + Sets the Enable Session State option. When enabled, you can set the session timeout using the SessionTimeout attribute. + + + + + Sets the timeout value for sessions in minutes. + + + + + Sets the option that enables response buffering in the application, which allows ASP script to set response headers anywhere in the script. + + + + + Sets the parent paths option, which allows a client to use relative paths to reach parent directories from this application. + + + + + Sets the default script language for the site. + + + + + + + + + + + Sets the timeout value in seconds for executing ASP scripts. + + + + + Enable ASP server-side script debugging. + + + + + Enable ASP client-side script debugging. + + + + + References the Id attribute of a WebAppPool element to use as the application pool for this application in IIS 6 applications. + + + + + + + + WebAddress for WebSite + + + + + + + The IP address to locate an existing WebSite or create a new WebSite. When the WebAddress is part of a WebSite element + used to locate an existing web site the following rules are used: + + When this attribute is not specified only the "All Unassigned" IP address will be located. + When this attribute is explicitly specified only the specified IP address will be located. + When this attribute has the value "*" then any IP address including the "All Unassigned" IP address will be located + + When the WebAddress is part of a WebSite element used to create a new web site the following rules are used: + + When this attribute is not specified or the value is "*" the "All Unassigned" IP address will be used. + When this attribute is explicitly specified the IP address will use that value. + + The IP attribute can contain a formatted string that is processed at install time to insert the values of properties using + [PropertyName] syntax. + + + + + + + + Determines if this address represents a secure binding. The default is 'no'. + + + + + + + + + + + Defines an IIS virtual directory. When this element is a child of WebSite element, the virtual directory is defined within that web site. Otherwise this virtual directory must reference a WebSite element via the WebSite attribute + + + + + + + + + + + + + + References the Id attribute for a WebSite in which this virtual directory belongs. Required when this element is not a child of WebSite element. + + + + + Sets the application name, which is the URL relative path used to access this virtual directory + + + + + References the Id attribute for a Directory element that points to the content for this virtual directory. + + + + + + References the Id attribute for a WebDirProperties element that specifies the security and access properties for this virtual directory. + This attribute may not be specified if a WebDirProperties element is directly nested in this element. + + + + + + References the Id attribute for a WebApplication element that specifies web application settings for this virtual directory. If a WebApplication child is not specified, the virtual directory does not host web applications. + + + + + + + + + + + Defines a subdirectory within an IIS web site. When this element is a child of WebSite, the web directory is defined within that web site. Otherwise the web directory must reference a WebSite element via the WebSite attribute. + + + + + + + + + + References the Id attribute for a WebSite element in which this directory belongs. Required when this element is not a child of a WebSite element. + + + + + Specifies the name of this web directory. + + + + + + References the Id attribute for a WebDirProperties element that specifies the security and access properties for this web directory. + This attribute may not be specified if a WebDirProperties element is directly nested in this element. + + + + + + + + + + + + + + + + Nesting WebSite under a Component element will result in a WebSite being installed to the machine as the package is installed. + + Nesting WebSite under Product, Fragment, or Module + results in a web site "locator" record being created in + the IIsWebSite table. This means that the web site + itself is neither installed nor uninstalled by the MSI + package. It does make the database available for referencing + from a WebApplication, WebVirtualDir or WebDir record. This allows an MSI to install + WebApplications, WebVirtualDirs or WebDirs to already existing web sites on the machine. + The install will fail if the web site does not exist in these cases. + + + + + IIs Web Site + + + + + + + + + + + + + + + + + + Identifier for the WebSite. Used within the MSI package only. + + + + + Specifies whether to automatically start the web site. + + + + + Specifies whether to configure the web site if it already exists. Note: This will not affect uninstall behavior. If the web site exists on uninstall, it will be removed. + + + + + Sets the timeout value for connections in seconds. + + + + + This is the name of the web site that will show up in the IIS management console. + + + + + Root directory of the web site. Resolved to a directory in the Directory table at install time by the server custom actions. + + + + + + References the Id attribute for a WebDirProperties element that specifies the security and access properties for this website root directory. + This attribute may not be specified if a WebDirProperties element is directly nested in this element. + + + + + + Sequence that the web site is to be created in. + + + + + + Optional attribute to directly specify the site id of the WebSite. Use this to ensure all web + sites in a web garden get the same site id. If a number is provided, the site id must be unique + on all target machines. If "*" is used, the Description attribute will be hashed to create a unique + value for the site id. This value must be a positive number or a "*" or a formatted value that resolves + to "-1" (for the same behavior as "*") or a positive number or blank. If this attribute is absent then + the web site will be located using the WebAddress element associated with the web site. + + + + + + Specifies whether to start the web site on install. + + + + + Reference to a WebApplication that is to be installed as part of this web site. + + + + + Reference to WebLog definition. + + + + + + + + + + + + + WebLog definition. + + + + + Identifier for the WebLog. + + + + + + + + + Microsoft IIS Log File Format + + + + + + + NCSA Common Log File Format + + + + + + + Disables logging. + + + + + + + ODBC Logging + + + + + + + W3C Extended Log File Format + + + + + + + + + + + + + + + The WebServiceExtension property is used by the Web server to determine whether a Web service extension is permitted to run. + + + + + + Usually a Property that resolves to short file name path + + + + + Description of the extension. + + + + + String used to identify groups of extensions. + + + + + Indicates if the extension is allowed or denied. + + + + + Indicates if the UI is allowed to delete the extension from the list of not. Default: Not deletable. + + + + + + + + Values of this type are any integers between 0 and 100, inclusive. + + + + + + + + + Values of this type will either be "yes" or "no". + + + + + + + + + + Values of this type will either be "default", "yes", or "no". + + + + + + + + + diff --git a/src/wixext/messages.cs b/src/wixext/messages.cs new file mode 100644 index 00000000..8b43bd9f --- /dev/null +++ b/src/wixext/messages.cs @@ -0,0 +1,237 @@ +//------------------------------------------------------------------------------ +// +// This code was generated by a tool. +// Runtime Version:4.0.30319.42000 +// +// Changes to this file may cause incorrect behavior and will be lost if +// the code is regenerated. +// +//------------------------------------------------------------------------------ + +namespace WixToolset.Extensions +{ + using System; + using System.Reflection; + using System.Resources; + using WixToolset.Data; + + + public class IIsErrorEventArgs : MessageEventArgs + { + + private static ResourceManager resourceManager = new ResourceManager("WixToolset.Extensions.Data.Messages", Assembly.GetExecutingAssembly()); + + public IIsErrorEventArgs(SourceLineNumber sourceLineNumbers, int id, string resourceName, params object[] messageArgs) : + base(sourceLineNumbers, id, resourceName, messageArgs) + { + base.ResourceManager = resourceManager; + } + } + + public sealed class IIsErrors + { + + private IIsErrors() + { + } + + public static MessageEventArgs MimeMapExtensionMissingPeriod(SourceLineNumber sourceLineNumbers, string elementName, string attributeName, string attributeValue) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5150, "IIsErrors_MimeMapExtensionMissingPeriod_1", elementName, attributeName, attributeValue); + } + + public static MessageEventArgs IllegalAttributeWithoutComponent(SourceLineNumber sourceLineNumbers, string elementName, string attributeName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5151, "IIsErrors_IllegalAttributeWithoutComponent_1", elementName, attributeName); + } + + public static MessageEventArgs IllegalElementWithoutComponent(SourceLineNumber sourceLineNumbers, string elementName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5152, "IIsErrors_IllegalElementWithoutComponent_1", elementName); + } + + public static MessageEventArgs OneOfAttributesRequiredUnderComponent(SourceLineNumber sourceLineNumbers, string elementName, string attributeName1, string attributeName2, string attributeName3, string attributeName4) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5153, "IIsErrors_OneOfAttributesRequiredUnderComponent_1", elementName, attributeName1, attributeName2, attributeName3, attributeName4); + } + + public static MessageEventArgs WebSiteAttributeUnderWebSite(SourceLineNumber sourceLineNumbers, string elementName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5154, "IIsErrors_WebSiteAttributeUnderWebSite_1", elementName); + } + + public static MessageEventArgs WebApplicationAlreadySpecified(SourceLineNumber sourceLineNumbers, string elementName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5155, "IIsErrors_WebApplicationAlreadySpecified_1", elementName); + } + + public static MessageEventArgs IllegalCharacterInAttributeValue(SourceLineNumber sourceLineNumbers, string elementName, string attributeName, string value, char illegalCharacter) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5156, "IIsErrors_IllegalCharacterInAttributeValue_1", elementName, attributeName, value, illegalCharacter); + } + + public static MessageEventArgs DeprecatedBinaryChildElement(SourceLineNumber sourceLineNumbers, string elementName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5157, "IIsErrors_DeprecatedBinaryChildElement_1", elementName); + } + + public static MessageEventArgs WebSiteNotFound(string webSiteDescription) + { + return new IIsErrorEventArgs(null, 5158, "IIsErrors_WebSiteNotFound_1", webSiteDescription); + } + + public static MessageEventArgs InsufficientPermissionHarvestWebSite() + { + return new IIsErrorEventArgs(null, 5159, "IIsErrors_InsufficientPermissionHarvestWebSite_1"); + } + + public static MessageEventArgs CannotHarvestWebSite() + { + return new IIsErrorEventArgs(null, 5160, "IIsErrors_CannotHarvestWebSite_1"); + } + + public static MessageEventArgs RequiredAttributeUnderComponent(SourceLineNumber sourceLineNumbers, string elementName, string attributeName) + { + return new IIsErrorEventArgs(sourceLineNumbers, 5161, "IIsErrors_RequiredAttributeUnderComponent_1", elementName, attributeName); + } + } + + public class IIsWarningEventArgs : MessageEventArgs + { + + private static ResourceManager resourceManager = new ResourceManager("WixToolset.Extensions.Data.Messages", Assembly.GetExecutingAssembly()); + + public IIsWarningEventArgs(SourceLineNumber sourceLineNumbers, int id, string resourceName, params object[] messageArgs) : + base(sourceLineNumbers, id, resourceName, messageArgs) + { + base.ResourceManager = resourceManager; + } + } + + public sealed class IIsWarnings + { + + private IIsWarnings() + { + } + + public static MessageEventArgs EncounteredNullDirectoryForWebSite(string directory) + { + return new IIsWarningEventArgs(null, 5400, "IIsWarnings_EncounteredNullDirectoryForWebSite_1", directory); + } + } + + public class IIsVerboseEventArgs : MessageEventArgs + { + + private static ResourceManager resourceManager = new ResourceManager("WixToolset.Extensions.Data.Messages", Assembly.GetExecutingAssembly()); + + public IIsVerboseEventArgs(SourceLineNumber sourceLineNumbers, int id, string resourceName, params object[] messageArgs) : + base(sourceLineNumbers, id, resourceName, messageArgs) + { + base.ResourceManager = resourceManager; + } + } + + public sealed class IIsVerboses + { + + private IIsVerboses() + { + } + } +} + +/* + + + + + + + + The {0}/@{1} attribute's value, '{2}', is not a valid mime map extension. It must begin with a period. + + + + + + + The {0}/@{1} attribute cannot be specified unless the element has a Component as an ancestor. A {0} that does not have a Component ancestor is not installed. + + + + + + The {0} element cannot be specified unless the element has a Component as an ancestor. A {0} that does not have a Component ancestor is not installed. + + + + + When nested under a Component, the {0} element must have one of the following attributes specified: {1}, {2}, {3} or {4}. + + + + + + + + + The {0}/@WebSite attribute cannot be specified when the {0} element is nested under a WebSite element. + + + + + The {0} element can have at most a single WebApplication specified. This can be either through the WebApplication attribute, or through a nested WebApplication element, but not both. + + + + + + The {0}/@{1} attribute's value, '{2}', is invalid. It cannot contain the character '{3}'. + + + + + + + + The {0} element contains a deprecated child Binary element. Please move the Binary element under a Fragment, Module, or Product element and set the {0}/@BinaryKey attribute to the value of the Binary/@Id attribute. + + + + + + The web site '{0}' could not be found. Please check that the web site exists, and that it is spelled correctly (please note, you must use the correct case). + + + + + + Not enough permissions to harvest website. On Windows Vista, you must run Heat elevated. + + + + + Cannot harvest website. On Windows Vista, you must install IIS 6 Management Compatibility. + + + + The {0}/@{1} attribute must be specified when the element has a Component as an ancestor. + + + + + + + + + Could not harvest website directory: {0}. Please update the output with the appropriate directory ID before using. + + + + + + + +*/ \ No newline at end of file diff --git a/src/wixext/tables.xml b/src/wixext/tables.xml new file mode 100644 index 00000000..2aef6f13 --- /dev/null +++ b/src/wixext/tables.xml @@ -0,0 +1,304 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/wixlib/IIsExtension.wxs b/src/wixlib/IIsExtension.wxs new file mode 100644 index 00000000..92d91533 --- /dev/null +++ b/src/wixlib/IIsExtension.wxs @@ -0,0 +1,59 @@ + + + + + + + + + + + + + + + + + + + + !(loc.msierrIISCannotConnect) + !(loc.msierrIISFailedReadWebSite) + !(loc.msierrIISFailedReadWebDirs) + !(loc.msierrIISFailedReadVDirs) + !(loc.msierrIISFailedReadFilters) + !(loc.msierrIISFailedReadMimeMap) + !(loc.msierrIISFailedReadAppPool) + !(loc.msierrIISFailedReadProp) + !(loc.msierrIISFailedReadWebSvcExt) + !(loc.msierrIISFailedReadWebError) + !(loc.msierrIISFailedReadHttpHeader) + + !(loc.msierrIISFailedSchedTransaction) + !(loc.msierrIISFailedSchedInstallWebs) + !(loc.msierrIISFailedSchedInstallWebDirs) + !(loc.msierrIISFailedSchedInstallVDirs) + !(loc.msierrIISFailedSchedInstallFilters) + !(loc.msierrIISFailedSchedInstallAppPool) + !(loc.msierrIISFailedSchedInstallProp) + !(loc.msierrIISFailedSchedInstallWebSvcExt) + + !(loc.msierrIISFailedSchedUninstallWebs) + !(loc.msierrIISFailedSchedUninstallWebDirs) + !(loc.msierrIISFailedSchedUninstallVDirs) + !(loc.msierrIISFailedSchedUninstallFilters) + !(loc.msierrIISFailedSchedUninstallAppPool) + !(loc.msierrIISFailedSchedUninstallProp) + !(loc.msierrIISFailedSchedUninstallWebSvcExt) + + !(loc.msierrIISFailedStartTransaction) + !(loc.msierrIISFailedOpenKey) + !(loc.msierrIISFailedCreateKey) + !(loc.msierrIISFailedWriteData) + !(loc.msierrIISFailedCreateApp) + !(loc.msierrIISFailedDeleteKey) + !(loc.msierrIISFailedDeleteValue) + !(loc.msierrIISFailedCommitInUse) + + + diff --git a/src/wixlib/IIsExtension_Platform.wxi b/src/wixlib/IIsExtension_Platform.wxi new file mode 100644 index 00000000..1991ef99 --- /dev/null +++ b/src/wixlib/IIsExtension_Platform.wxi @@ -0,0 +1,68 @@ + + + + + + + + + + + !(loc.ConfigureIIs) + !(loc.ConfigureIIsExec) + !(loc.StartMetabaseTransaction) + !(loc.RollbackMetabaseTransaction) + !(loc.CommitMetabaseTransaction) + !(loc.WriteMetabaseChanges) + + !(loc.ConfigureIIs7Exec) + !(loc.StartIIS7ConfigTransaction) + !(loc.RollbackIIS7ConfigTransaction) + !(loc.CommitIIS7ConfigTransaction) + !(loc.WriteIIS7ConfigChanges) + + + + + + + + + + + + + + + + + NOT SKIPCONFIGUREIIS AND VersionNT > 400 + + + + + + + + + + + + + + + + + + + + + + + + VersionNT > 400 + VersionNT > 400 + + + + diff --git a/src/wixlib/IIsExtension_x86.wxs b/src/wixlib/IIsExtension_x86.wxs new file mode 100644 index 00000000..93a3956f --- /dev/null +++ b/src/wixlib/IIsExtension_x86.wxs @@ -0,0 +1,8 @@ + + + + + + + + diff --git a/src/wixlib/en-us.wxl b/src/wixlib/en-us.wxl new file mode 100644 index 00000000..5b26f72f --- /dev/null +++ b/src/wixlib/en-us.wxl @@ -0,0 +1,56 @@ + + + + + + Cannot connect to Internet Information Server. ([2] [3] [4] [5]) + Failed while processing WebSites. ([2] [3] [4] [5]) + Failed while processing WebDirs. ([2] [3] [4] [5]) + Failed while processing WebVirtualDirs. ([2] [3] [4] [5]) + Failed while processing WebFilters. ([2] [3] [4] [5]) + Failed while processing MimeMaps. ([2] [3] [4] [5]) + Failed while processing WebAppPools. ([2] [3] [4] [5]) + Failed while processing WebProperties. ([2] [3] [4] [5]) + Failed while processing WebServiceExtensions. ([2] [3] [4] [5]) + Failed while processing WebErrors. ([2] [3] [4] [5]) + Failed while processing HttpHeaders. ([2] [3] [4] [5]) + + Failed to schedule transaction for changes to IIS. ([2] [3] [4] [5]) + Failed to schedule install of IIS Web Sites. ([2] [3] [4] [5]) + Failed to schedule install of IIS Web Directories. ([2] [3] [4] [5]) + Failed to schedule install of IIS Virtual Directories. ([2] [3] [4] [5]) + Failed to schedule install of IIS Filters. ([2] [3] [4] [5]) + Failed to schedule install of IIS AppPools. ([2] [3] [4] [5]) + Failed to schedule install of IIS Properties. ([2] [3] [4] [5]) + Failed to schedule install of IIS Web Service Extensions. ([2] [3] [4] [5]) + + Failed to schedule uninstall of IIS Web Sites. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS Web Directories. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS Virtual Directories. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS Filters. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS AppPools. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS Properties. ([2] [3] [4] [5]) + Failed to schedule uninstall of IIS Web Service Extensions. ([2] [3] [4] [5]) + + Failed to start IIS transaction. ([2] [3] [4] [5]) + Failed to open metabase key. ([2] [3] [4] [5]) + Failed to create metabase key. ([2] [3] [4] [5]) + Failed to write data to metabase key. ([2] [3] [4] [5]) + Failed to create web application. ([2] [3] [4] [5]) + Failed to delete metabase key. ([2] [3] [4] [5]) + Failed to delete metabase value. ([2] [3] [4] [5]) + Failed to commit IIS transaction due to a sharing violation. Some other application may be configuring IIS. + + Configuring IIS + Executing IIS Configuration + Starting IIS Metabase Transaction + Rolling back IIS Metabase Transaction + Committing IIS Metabase Transaction + Installing Metabase Keys and Values + + Configuring IIS + Starting IIS Config Transaction + Rolling back IIS Config Transaction + Committing IIS Config Transaction + Installing Config Keys and Values + diff --git a/src/wixlib/ja-jp.wxl b/src/wixlib/ja-jp.wxl new file mode 100644 index 00000000..eef25ec6 --- /dev/null +++ b/src/wixlib/ja-jp.wxl @@ -0,0 +1,48 @@ + + + + + + IISへ接続できません。 ([2] [3] [4] [5]) + ウェブ サイト処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ ディレクトリ処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ仮想ディレクトリ処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ フィルタ処理中に失敗しました。 ([2] [3] [4] [5]) + MIME マップ処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ アプリケーション プール処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ プロパティ処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ サービス拡張処理中に失敗しました。 ([2] [3] [4] [5]) + ウェブ エラー処理中に失敗しました。 ([2] [3] [4] [5]) + HTTP ヘッダ処理中に失敗しました。 ([2] [3] [4] [5]) + + IIS 変更トランザクションのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS ウェブ サイト インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS ウェブ ディレクトリ インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS 仮想ディレクトリ インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS フィルタ インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS アプリケーション プール インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS プロパティ インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS ウェブ サービス拡張インストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + + IISウェブ サイト アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS ウェブ ディレクトリ アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS 仮想ディレクトリ アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS フィルタ アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS アプリケーション プール アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS プロパティ アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + IIS ウェブ サービス拡張アンインストールのスケジューリングに失敗しました。 ([2] [3] [4] [5]) + + IIS トランザクション開始に失敗しました。 ([2] [3] [4] [5]) + メタベース キーのオープンに失敗しました。 ([2] [3] [4] [5]) + メタベース キーの作成に失敗しました。 ([2] [3] [4] [5]) + メタベース キーの書き込みに失敗しました。 ([2] [3] [4] [5]) + ウェブ アプリケーションの作成に失敗しました。 ([2] [3] [4] [5]) + メタベース キーの削除に失敗しました。 ([2] [3] [4] [5]) + メタベース値の削除に失敗しました。 ([2] [3] [4] [5]) + + IIS を構成しています + IIS メタベース トランザクションを開始しています + IIS メタベース トランザクションをロールバックしています + IIS メタベース トランザクションを確定しています + IIS メタベース キーと値をインストールしています + diff --git a/src/wixlib/pt-br.wxl b/src/wixlib/pt-br.wxl new file mode 100644 index 00000000..99c705c9 --- /dev/null +++ b/src/wixlib/pt-br.wxl @@ -0,0 +1,51 @@ + + + + + + Não foi possível conectar no Internet Information Server. ([2] [3] [4] [5]) + Erro ao processar WebSites. ([2] [3] [4] [5]) + Erro ao processar WebDirs. ([2] [3] [4] [5]) + Erro ao processar WebVirtualDirs. ([2] [3] [4] [5]) + Erro ao processar WebFilters. ([2] [3] [4] [5]) + Erro ao processar MimeMaps. ([2] [3] [4] [5]) + Erro ao processar WebAppPools. ([2] [3] [4] [5]) + Erro ao processar WebProperties. ([2] [3] [4] [5]) + Erro ao processar WebServiceExtensions. ([2] [3] [4] [5]) + Erro ao processar WebErrors. ([2] [3] [4] [5]) + Erro ao processar HttpHeaders. ([2] [3] [4] [5]) + Erro ao agendar transação para alterações no IIS. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Web Sites. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Web Directories. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Virtual Directories. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Filters. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS AppPools. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Properties. ([2] [3] [4] [5]) + Erro ao agendar instalação de IIS Web Service Extensions. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Web Sites. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Web Directories. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Virtual Directories. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Filters. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS AppPools. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Properties. ([2] [3] [4] [5]) + Erro ao agendar desinstalação de IIS Web Service Extensions. ([2] [3] [4] [5]) + Erro ao iniciar transação do IIS . ([2] [3] [4] [5]) + Erro ao abrir metabase key. ([2] [3] [4] [5]) + Erro ao criar metabase key. ([2] [3] [4] [5]) + Erro ao escrever dados na metabase key. ([2] [3] [4] [5]) + Erro ao criar aplicação Web. ([2] [3] [4] [5]) + Erro ao excluir metabase key. ([2] [3] [4] [5]) + Erro ao excluir valor da metabase. ([2] [3] [4] [5]) + Erro ao fazer commit de transação IIS por violação de compartilhamento. Alguma outra aplicação pode estar tentando configurar o ISS ao mesmo tempo. + Configurando IIS + Executando Configurações do IIS + Iniciando Transação de Metabase do IIS + Cancelando Transação de Metabase do IIS + Efetivando Transação de Metabase do IIS + Instalando Chaves e Valores de Metabase do IIS + Configurando IIS + Iniciando Transação de Configuração do IIS + Cancelando Transação de Configuração do IIS + Efetivando Transação de Configuração do IIS + Instalando Chaves e Valores de Configurações do IIS + -- cgit v1.2.3-55-g6feb