Beispiel #1
0
 /// <summary>
 /// Creates a new empty output object.
 /// </summary>
 /// <param name="sourceLineNumbers">The source line information for the output.</param>
 internal Output(SourceLineNumberCollection sourceLineNumbers)
 {
     this.sections = new SectionCollection();
     this.sourceLineNumbers = sourceLineNumbers;
     this.subStorages = new ArrayList();
     this.tables = new TableCollection();
 }
Beispiel #2
0
        /// <summary>
        /// Creates a new section as part of an intermediate.
        /// </summary>
        /// <param name="id">Identifier for section.</param>
        /// <param name="type">Type of section.</param>
        /// <param name="codepage">Codepage for resulting database.</param>
        public Section(string id, SectionType type, int codepage)
        {
            this.id = id;
            this.type = type;
            this.codepage = codepage;

            this.tables = new TableCollection();
        }
Beispiel #3
0
        /// <summary>
        /// Creates a new section as part of an intermediate.
        /// </summary>
        /// <param name="intermediate">Parent intermediate.</param>
        /// <param name="id">Identifier for section.</param>
        /// <param name="type">Type of section.</param>
        /// <param name="codepage">Codepage for resulting database.</param>
        public Section(Intermediate intermediate, string id, SectionType type, int codepage)
        {
            this.intermediate = intermediate;
            this.id = id;
            this.type = type;
            this.codepage = codepage;

            this.tables = new TableCollection();
            this.references = new ReferenceCollection();
            this.ignoreModularizations = new IgnoreModularizationCollection();
            this.complexReferences = new ComplexReferenceCollection();
            this.featureBacklinks = new FeatureBacklinkCollection();
        }
 /// <summary>
 /// Finalize decompilation.
 /// </summary>
 /// <param name="tables">The collection of all tables.</param>
 public virtual void FinalizeDecompile(TableCollection tables)
 {
 }
        /// <summary>
        /// Checks the InstallExecuteSequence table to determine where RemoveExistingProducts is scheduled and removes it.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        private static Wix.MajorUpgrade.ScheduleType DetermineMajorUpgradeScheduling(TableCollection tables)
        {
            int sequenceRemoveExistingProducts = 0;
            int sequenceInstallValidate = 0;
            int sequenceInstallInitialize = 0;
            int sequenceInstallFinalize = 0;
            int sequenceInstallExecute = 0;
            int sequenceInstallExecuteAgain = 0;

            Table installExecuteSequenceTable = tables["InstallExecuteSequence"];
            if (null != installExecuteSequenceTable)
            {
                int removeExistingProductsRow = -1;
                for (int i = 0; i < installExecuteSequenceTable.Rows.Count; i++)
                {
                    Row row = installExecuteSequenceTable.Rows[i];
                    string action = Convert.ToString(row[0]);
                    int sequence = Convert.ToInt32(row[2]);

                    switch (action)
                    {
                        case "RemoveExistingProducts":
                            sequenceRemoveExistingProducts = sequence;
                            removeExistingProductsRow = i;
                            break;
                        case "InstallValidate":
                            sequenceInstallValidate = sequence;
                            break;
                        case "InstallInitialize":
                            sequenceInstallInitialize = sequence;
                            break;
                        case "InstallExecute":
                            sequenceInstallExecute = sequence;
                            break;
                        case "InstallExecuteAgain":
                            sequenceInstallExecuteAgain = sequence;
                            break;
                        case "InstallFinalize":
                            sequenceInstallFinalize = sequence;
                            break;
                    }
                }

                installExecuteSequenceTable.Rows.RemoveAt(removeExistingProductsRow);
            }

            if (0 != sequenceInstallValidate && sequenceInstallValidate < sequenceRemoveExistingProducts && sequenceRemoveExistingProducts < sequenceInstallInitialize)
            {
                return Wix.MajorUpgrade.ScheduleType.afterInstallValidate;
            }
            else if (0 != sequenceInstallInitialize && sequenceInstallInitialize < sequenceRemoveExistingProducts && sequenceRemoveExistingProducts < sequenceInstallExecute)
            {
                return Wix.MajorUpgrade.ScheduleType.afterInstallInitialize;
            }
            else if (0 != sequenceInstallExecute && sequenceInstallExecute < sequenceRemoveExistingProducts && sequenceRemoveExistingProducts < sequenceInstallExecuteAgain)
            {
                return Wix.MajorUpgrade.ScheduleType.afterInstallExecute;
            }
            else if (0 != sequenceInstallExecuteAgain && sequenceInstallExecuteAgain < sequenceRemoveExistingProducts && sequenceRemoveExistingProducts < sequenceInstallFinalize)
            {
                return Wix.MajorUpgrade.ScheduleType.afterInstallExecuteAgain;
            }
            else
            {
                return Wix.MajorUpgrade.ScheduleType.afterInstallFinalize;
            }
        }
        /// <summary>
        /// Initialize decompilation.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        private void InitializeDecompile(TableCollection tables)
        {
            // reset all the state information
            this.compressed = false;
            this.patchTargetFiles.Clear();
            this.sequenceElements.Clear();
            this.shortNames = false;

            // set the codepage if its not neutral (0)
            if (0 != this.codepage)
            {
                switch (this.outputType)
                {
                    case OutputType.Module:
                        ((Wix.Module)this.core.RootElement).Codepage = this.codepage.ToString(CultureInfo.InvariantCulture);
                        break;
                    case OutputType.PatchCreation:
                        ((Wix.PatchCreation)this.core.RootElement).Codepage = this.codepage.ToString(CultureInfo.InvariantCulture);
                        break;
                    case OutputType.Product:
                        ((Wix.Product)this.core.RootElement).Codepage = this.codepage.ToString(CultureInfo.InvariantCulture);
                        break;
                }
            }

            // index the rows from the extension libraries
            Hashtable indexedExtensionTables = new Hashtable();
            foreach (WixExtension extension in this.extensions)
            {
                // determine if the extension would like its library rows to be removed
                // if there is no decompiler extension, assume rows should not be removed
                if (null == extension.DecompilerExtension || !extension.DecompilerExtension.RemoveLibraryRows)
                {
                    continue;
                }

                Library library = extension.GetLibrary(this.tableDefinitions);

                if (null != library)
                {
                    foreach (Section section in library.Sections)
                    {
                        foreach (Table table in section.Tables)
                        {
                            foreach (Row row in table.Rows)
                            {
                                string primaryKey;
                                string tableName;

                                // the Actions table needs to be handled specially
                                if ("WixAction" == table.Name)
                                {
                                    primaryKey = Convert.ToString(row[1]);

                                    if (OutputType.Module == this.outputType)
                                    {
                                        tableName = String.Concat("Module", Convert.ToString(row[0]));
                                    }
                                    else
                                    {
                                        tableName = Convert.ToString(row[0]);
                                    }
                                }
                                else
                                {
                                    primaryKey = row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter);
                                    tableName = table.Name;
                                }

                                if (null != primaryKey)
                                {
                                    if (!indexedExtensionTables.Contains(tableName))
                                    {
                                        indexedExtensionTables.Add(tableName, new Hashtable());
                                    }
                                    Hashtable indexedExtensionRows = (Hashtable)indexedExtensionTables[tableName];

                                    indexedExtensionRows[primaryKey] = null;
                                }
                            }
                        }
                    }
                }
            }

            // remove the rows from the extension libraries (to allow full round-tripping)
            foreach (string tableName in indexedExtensionTables.Keys)
            {
                Table table = tables[tableName];
                Hashtable indexedExtensionRows = (Hashtable)indexedExtensionTables[tableName];

                if (null != table)
                {
                    RowCollection originalRows = table.Rows.Clone();

                    // remove the original rows so that they can be added back if they should remain
                    table.Rows.Clear();

                    foreach (Row row in originalRows)
                    {
                        if (!indexedExtensionRows.Contains(row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter)))
                        {
                            table.Rows.Add(row);
                        }
                    }
                }
            }
        }
        /// <summary>
        /// Finalize the Upgrade table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Decompile the rows from the Upgrade and LaunchCondition tables
        /// created by the MajorUpgrade element.
        /// </remarks>
        private void FinalizeUpgradeTable(TableCollection tables)
        {
            Table launchConditionTable = tables["LaunchCondition"];
            Table upgradeTable = tables["Upgrade"];
            string downgradeErrorMessage = null;
            string disallowUpgradeErrorMessage = null;
            Wix.MajorUpgrade majorUpgrade = new Wix.MajorUpgrade();

            // find the DowngradePreventedCondition launch condition message
            if (null != launchConditionTable && 0 < launchConditionTable.Rows.Count)
            {
                foreach (Row launchRow in launchConditionTable.Rows)
                {
                    if (Compiler.DowngradePreventedCondition == Convert.ToString(launchRow[0]))
                    {
                        downgradeErrorMessage = Convert.ToString(launchRow[1]);
                    }
                    else if (Compiler.UpgradePreventedCondition == Convert.ToString(launchRow[0]))
                    {
                        disallowUpgradeErrorMessage = Convert.ToString(launchRow[1]);
                    }
                }
            }

            if (null != upgradeTable && 0 < upgradeTable.Rows.Count)
            {
                bool hasMajorUpgrade = false;

                foreach (Row row in upgradeTable.Rows)
                {
                    UpgradeRow upgradeRow = (UpgradeRow)row;

                    if (Compiler.UpgradeDetectedProperty == upgradeRow.ActionProperty)
                    {
                        hasMajorUpgrade = true;
                        int attr = upgradeRow.Attributes;
                        string removeFeatures = upgradeRow.Remove;

                        if (MsiInterop.MsidbUpgradeAttributesVersionMaxInclusive == (attr & MsiInterop.MsidbUpgradeAttributesVersionMaxInclusive))
                        {
                            majorUpgrade.AllowSameVersionUpgrades = Wix.YesNoType.yes;
                        }

                        if (MsiInterop.MsidbUpgradeAttributesMigrateFeatures != (attr & MsiInterop.MsidbUpgradeAttributesMigrateFeatures))
                        {
                            majorUpgrade.MigrateFeatures = Wix.YesNoType.no;
                        }

                        if (MsiInterop.MsidbUpgradeAttributesIgnoreRemoveFailure == (attr & MsiInterop.MsidbUpgradeAttributesIgnoreRemoveFailure))
                        {
                            majorUpgrade.IgnoreRemoveFailure = Wix.YesNoType.yes;
                        }

                        if (!String.IsNullOrEmpty(removeFeatures))
                        {
                            majorUpgrade.RemoveFeatures = removeFeatures;
                        }
                    }
                    else if (Compiler.DowngradeDetectedProperty == upgradeRow.ActionProperty)
                    {
                        hasMajorUpgrade = true;
                        majorUpgrade.DowngradeErrorMessage = downgradeErrorMessage;
                    }
                }

                if (hasMajorUpgrade)
                {
                    if (String.IsNullOrEmpty(downgradeErrorMessage))
                    {
                        majorUpgrade.AllowDowngrades = Wix.YesNoType.yes;
                    }

                    if (!String.IsNullOrEmpty(disallowUpgradeErrorMessage))
                    {
                        majorUpgrade.Disallow = Wix.YesNoType.yes;
                        majorUpgrade.DisallowUpgradeErrorMessage = disallowUpgradeErrorMessage;
                    }

                    majorUpgrade.Schedule = DetermineMajorUpgradeScheduling(tables);
                    this.core.RootElement.AddChild(majorUpgrade);
                }
            }
        }
        /// <summary>
        /// Finalize the search tables.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>Does all the complex linking required for the search tables.</remarks>
        private void FinalizeSearchTables(TableCollection tables)
        {
            Table appSearchTable = tables["AppSearch"];
            Table ccpSearchTable = tables["CCPSearch"];
            Table drLocatorTable = tables["DrLocator"];

            Hashtable appSearches = new Hashtable();
            Hashtable ccpSearches = new Hashtable();
            Hashtable drLocators = new Hashtable();
            Hashtable locators = new Hashtable();
            Hashtable usedSearchElements = new Hashtable();
            ArrayList unusedSearchElements = new ArrayList();

            Wix.ComplianceCheck complianceCheck = null;

            // index the AppSearch table by signatures
            if (null != appSearchTable)
            {
                foreach (Row row in appSearchTable.Rows)
                {
                    string property = Convert.ToString(row[0]);
                    string signature = Convert.ToString(row[1]);

                    if (!appSearches.Contains(signature))
                    {
                        appSearches.Add(signature, new StringCollection());
                    }

                    ((StringCollection)appSearches[signature]).Add(property);
                }
            }

            // index the CCPSearch table by signatures
            if (null != ccpSearchTable)
            {
                foreach (Row row in ccpSearchTable.Rows)
                {
                    string signature = Convert.ToString(row[0]);

                    if (!ccpSearches.Contains(signature))
                    {
                        ccpSearches.Add(signature, new StringCollection());
                    }

                    ((StringCollection)ccpSearches[signature]).Add(null);

                    if (null == complianceCheck && !appSearches.Contains(signature))
                    {
                        complianceCheck = new Wix.ComplianceCheck();
                        this.core.RootElement.AddChild(complianceCheck);
                    }
                }
            }

            // index the directory searches by their search elements (to get back the original row)
            if (null != drLocatorTable)
            {
                foreach (Row row in drLocatorTable.Rows)
                {
                    drLocators.Add(this.core.GetIndexedElement(row), row);
                }
            }

            // index the locator tables by their signatures
            string[] locatorTableNames = new string[] { "CompLocator", "RegLocator", "IniLocator", "DrLocator", "Signature" };
            foreach (string locatorTableName in locatorTableNames)
            {
                Table locatorTable = tables[locatorTableName];

                if (null != locatorTable)
                {
                    foreach (Row row in locatorTable.Rows)
                    {
                        string signature = Convert.ToString(row[0]);

                        if (!locators.Contains(signature))
                        {
                            locators.Add(signature, new ArrayList());
                        }

                        ((ArrayList)locators[signature]).Add(row);
                    }
                }
            }

            // move the DrLocator rows with a parent of CCP_DRIVE first to ensure they get FileSearch children (not FileSearchRef)
            foreach (ArrayList locatorRows in locators.Values)
            {
                int firstDrLocator = -1;

                for (int i = 0; i < locatorRows.Count; i++)
                {
                    Row locatorRow = (Row)locatorRows[i];

                    if ("DrLocator" == locatorRow.TableDefinition.Name)
                    {
                        if (-1 == firstDrLocator)
                        {
                            firstDrLocator = i;
                        }

                        if ("CCP_DRIVE" == Convert.ToString(locatorRow[1]))
                        {
                            locatorRows.RemoveAt(i);
                            locatorRows.Insert(firstDrLocator, locatorRow);
                            break;
                        }
                    }
                }
            }

            foreach (string signature in locators.Keys)
            {
                ArrayList locatorRows = (ArrayList)locators[signature];
                ArrayList signatureSearchElements = new ArrayList();

                foreach (Row locatorRow in locatorRows)
                {
                    bool used = true;
                    Wix.ISchemaElement searchElement = this.core.GetIndexedElement(locatorRow);

                    if ("Signature" == locatorRow.TableDefinition.Name && 0 < signatureSearchElements.Count)
                    {
                        foreach (Wix.IParentElement searchParentElement in signatureSearchElements)
                        {
                            if (!usedSearchElements.Contains(searchElement))
                            {
                                searchParentElement.AddChild(searchElement);
                                usedSearchElements[searchElement] = null;
                            }
                            else
                            {
                                Wix.FileSearchRef fileSearchRef = new Wix.FileSearchRef();

                                fileSearchRef.Id = signature;

                                searchParentElement.AddChild(fileSearchRef);
                            }
                        }
                    }
                    else if ("DrLocator" == locatorRow.TableDefinition.Name && null != locatorRow[1])
                    {
                        string parentSignature = Convert.ToString(locatorRow[1]);

                        if ("CCP_DRIVE" == parentSignature)
                        {
                            if (appSearches.Contains(signature))
                            {
                                StringCollection appSearchPropertyIds = (StringCollection)appSearches[signature];

                                foreach (string propertyId in appSearchPropertyIds)
                                {
                                    Wix.Property property = this.EnsureProperty(propertyId);
                                    Wix.ComplianceDrive complianceDrive = null;

                                    if (ccpSearches.Contains(signature))
                                    {
                                        property.ComplianceCheck = Wix.YesNoType.yes;
                                    }

                                    foreach (Wix.ISchemaElement element in property.Children)
                                    {
                                        complianceDrive = element as Wix.ComplianceDrive;
                                        if (null != complianceDrive)
                                        {
                                            break;
                                        }
                                    }

                                    if (null == complianceDrive)
                                    {
                                        complianceDrive = new Wix.ComplianceDrive();
                                        property.AddChild(complianceDrive);
                                    }

                                    if (!usedSearchElements.Contains(searchElement))
                                    {
                                        complianceDrive.AddChild(searchElement);
                                        usedSearchElements[searchElement] = null;
                                    }
                                    else
                                    {
                                        Wix.DirectorySearchRef directorySearchRef = new Wix.DirectorySearchRef();

                                        directorySearchRef.Id = signature;

                                        if (null != locatorRow[1])
                                        {
                                            directorySearchRef.Parent = Convert.ToString(locatorRow[1]);
                                        }

                                        if (null != locatorRow[2])
                                        {
                                            directorySearchRef.Path = Convert.ToString(locatorRow[2]);
                                        }

                                        complianceDrive.AddChild(directorySearchRef);
                                        signatureSearchElements.Add(directorySearchRef);
                                    }
                                }
                            }
                            else if (ccpSearches.Contains(signature))
                            {
                                Wix.ComplianceDrive complianceDrive = null;

                                foreach (Wix.ISchemaElement element in complianceCheck.Children)
                                {
                                    complianceDrive = element as Wix.ComplianceDrive;
                                    if (null != complianceDrive)
                                    {
                                        break;
                                    }
                                }

                                if (null == complianceDrive)
                                {
                                    complianceDrive = new Wix.ComplianceDrive();
                                    complianceCheck.AddChild(complianceDrive);
                                }

                                if (!usedSearchElements.Contains(searchElement))
                                {
                                    complianceDrive.AddChild(searchElement);
                                    usedSearchElements[searchElement] = null;
                                }
                                else
                                {
                                    Wix.DirectorySearchRef directorySearchRef = new Wix.DirectorySearchRef();

                                    directorySearchRef.Id = signature;

                                    if (null != locatorRow[1])
                                    {
                                        directorySearchRef.Parent = Convert.ToString(locatorRow[1]);
                                    }

                                    if (null != locatorRow[2])
                                    {
                                        directorySearchRef.Path = Convert.ToString(locatorRow[2]);
                                    }

                                    complianceDrive.AddChild(directorySearchRef);
                                    signatureSearchElements.Add(directorySearchRef);
                                }
                            }
                        }
                        else
                        {
                            bool usedDrLocator = false;
                            ArrayList parentLocatorRows = (ArrayList)locators[parentSignature];

                            if (null != parentLocatorRows)
                            {
                                foreach (Row parentLocatorRow in parentLocatorRows)
                                {
                                    if ("DrLocator" == parentLocatorRow.TableDefinition.Name)
                                    {
                                        Wix.IParentElement parentSearchElement = (Wix.IParentElement)this.core.GetIndexedElement(parentLocatorRow);

                                        if (parentSearchElement.Children.GetEnumerator().MoveNext())
                                        {
                                            Row parentDrLocatorRow = (Row)drLocators[parentSearchElement];
                                            Wix.DirectorySearchRef directorySeachRef = new Wix.DirectorySearchRef();

                                            directorySeachRef.Id = parentSignature;

                                            if (null != parentDrLocatorRow[1])
                                            {
                                                directorySeachRef.Parent = Convert.ToString(parentDrLocatorRow[1]);
                                            }

                                            if (null != parentDrLocatorRow[2])
                                            {
                                                directorySeachRef.Path = Convert.ToString(parentDrLocatorRow[2]);
                                            }

                                            parentSearchElement = directorySeachRef;
                                            unusedSearchElements.Add(directorySeachRef);
                                        }

                                        if (!usedSearchElements.Contains(searchElement))
                                        {
                                            parentSearchElement.AddChild(searchElement);
                                            usedSearchElements[searchElement] = null;
                                            usedDrLocator = true;
                                        }
                                        else
                                        {
                                            Wix.DirectorySearchRef directorySearchRef = new Wix.DirectorySearchRef();

                                            directorySearchRef.Id = signature;

                                            directorySearchRef.Parent = parentSignature;

                                            if (null != locatorRow[2])
                                            {
                                                directorySearchRef.Path = Convert.ToString(locatorRow[2]);
                                            }

                                            parentSearchElement.AddChild(searchElement);
                                            usedDrLocator = true;
                                        }
                                    }
                                }

                                // keep track of unused DrLocator rows
                                if (!usedDrLocator)
                                {
                                    unusedSearchElements.Add(searchElement);
                                }
                            }
                            else
                            {
                                // TODO: warn
                            }
                        }
                    }
                    else if (appSearches.Contains(signature))
                    {
                        StringCollection appSearchPropertyIds = (StringCollection)appSearches[signature];

                        foreach (string propertyId in appSearchPropertyIds)
                        {
                            Wix.Property property = this.EnsureProperty(propertyId);

                            if (ccpSearches.Contains(signature))
                            {
                                property.ComplianceCheck = Wix.YesNoType.yes;
                            }

                            if (!usedSearchElements.Contains(searchElement))
                            {
                                property.AddChild(searchElement);
                                usedSearchElements[searchElement] = null;
                            }
                            else if ("RegLocator" == locatorRow.TableDefinition.Name)
                            {
                                Wix.RegistrySearchRef registrySearchRef = new Wix.RegistrySearchRef();

                                registrySearchRef.Id = signature;

                                property.AddChild(registrySearchRef);
                                signatureSearchElements.Add(registrySearchRef);
                            }
                            else
                            {
                                // TODO: warn about unavailable Ref element
                            }
                        }
                    }
                    else if (ccpSearches.Contains(signature))
                    {
                        if (!usedSearchElements.Contains(searchElement))
                        {
                            complianceCheck.AddChild(searchElement);
                            usedSearchElements[searchElement] = null;
                        }
                        else if ("RegLocator" == locatorRow.TableDefinition.Name)
                        {
                            Wix.RegistrySearchRef registrySearchRef = new Wix.RegistrySearchRef();

                            registrySearchRef.Id = signature;

                            complianceCheck.AddChild(registrySearchRef);
                            signatureSearchElements.Add(registrySearchRef);
                        }
                        else
                        {
                            // TODO: warn about unavailable Ref element
                        }
                    }
                    else
                    {
                        if ("DrLocator" == locatorRow.TableDefinition.Name)
                        {
                            unusedSearchElements.Add(searchElement);
                        }
                        else
                        {
                            // TODO: warn
                            used = false;
                        }
                    }

                    // keep track of the search elements for this signature so that nested searches go in the proper parents
                    if (used)
                    {
                        signatureSearchElements.Add(searchElement);
                    }
                }
            }

            foreach (Wix.IParentElement unusedSearchElement in unusedSearchElements)
            {
                bool used = false;

                foreach (Wix.ISchemaElement schemaElement in unusedSearchElement.Children)
                {
                    Wix.DirectorySearch directorySearch = schemaElement as Wix.DirectorySearch;
                    if (null != directorySearch)
                    {
                        StringCollection appSearchProperties = (StringCollection)appSearches[directorySearch.Id];

                        Wix.ISchemaElement unusedSearchSchemaElement = unusedSearchElement as Wix.ISchemaElement;
                        if (null != appSearchProperties)
                        {
                            Wix.Property property = this.EnsureProperty(appSearchProperties[0]);

                            property.AddChild(unusedSearchSchemaElement);
                            used = true;
                            break;
                        }
                        else if (ccpSearches.Contains(directorySearch.Id))
                        {
                            complianceCheck.AddChild(unusedSearchSchemaElement);
                            used = true;
                            break;
                        }
                        else
                        {
                            // TODO: warn
                        }
                    }
                }

                if (!used)
                {
                    // TODO: warn
                }
            }
        }
        /// <summary>
        /// Finalize the RemoveFile table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Sets the directory/property for each RemoveFile row.
        /// </remarks>
        private void FinalizeRemoveFileTable(TableCollection tables)
        {
            Table removeFileTable = tables["RemoveFile"];

            if (null != removeFileTable)
            {
                foreach (Row row in removeFileTable.Rows)
                {
                    bool isDirectory = false;
                    string property = Convert.ToString(row[3]);

                    // determine if the property is actually authored as a directory
                    if (null != this.core.GetIndexedElement("Directory", property))
                    {
                        isDirectory = true;
                    }

                    Wix.ISchemaElement element = this.core.GetIndexedElement(row);

                    Wix.RemoveFile removeFile = element as Wix.RemoveFile;
                    if (null != removeFile)
                    {
                        if (isDirectory)
                        {
                            removeFile.Directory = property;
                        }
                        else
                        {
                            removeFile.Property = property;
                        }
                    }
                    else
                    {
                        Wix.RemoveFolder removeFolder = (Wix.RemoveFolder)element;

                        if (isDirectory)
                        {
                            removeFolder.Directory = property;
                        }
                        else
                        {
                            removeFolder.Property = property;
                        }
                    }
                }
            }
        }
Beispiel #10
0
        /// <summary>
        /// Finalize the ProgId table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Enumerates through all the Class rows, looking for child ProgIds (these are the
        /// default ProgIds for a given Class).  Then go through the ProgId table and add any
        /// remaining ProgIds for each Class.  This happens during finalize because there is
        /// a circular dependency between the Class and ProgId tables.
        /// </remarks>
        private void FinalizeProgIdTable(TableCollection tables)
        {
            Table classTable = tables["Class"];
            Table progIdTable = tables["ProgId"];
            Table extensionTable = tables["Extension"];
            Table componentTable = tables["Component"];

            Hashtable addedProgIds = new Hashtable();
            Hashtable classes = new Hashtable();
            Hashtable components = new Hashtable();

            // add the default ProgIds for each class (and index the class table)
            if (null != classTable)
            {
                foreach (Row row in classTable.Rows)
                {
                    Wix.Class wixClass = (Wix.Class)this.core.GetIndexedElement(row);

                    if (null != row[3])
                    {
                        Wix.ProgId progId = (Wix.ProgId)this.core.GetIndexedElement("ProgId", Convert.ToString(row[3]));

                        if (null != progId)
                        {
                            if (addedProgIds.Contains(progId))
                            {
                                this.core.OnMessage(WixWarnings.TooManyProgIds(row.SourceLineNumbers, Convert.ToString(row[0]), Convert.ToString(row[3]), Convert.ToString(addedProgIds[progId])));
                            }
                            else
                            {
                                wixClass.AddChild(progId);
                                addedProgIds.Add(progId, wixClass.Id);
                            }
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Class", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "ProgId_Default", Convert.ToString(row[3]), "ProgId"));
                        }
                    }

                    // index the Class elements for nesting of ProgId elements (which don't use the full Class primary key)
                    if (!classes.Contains(wixClass.Id))
                    {
                        classes.Add(wixClass.Id, new ArrayList());
                    }
                    ((ArrayList)classes[wixClass.Id]).Add(wixClass);
                }
            }
            
            // add the remaining non-default ProgId entries for each class
            if (null != progIdTable)
            {
                foreach (Row row in progIdTable.Rows)
                {
                    Wix.ProgId progId = (Wix.ProgId)this.core.GetIndexedElement(row);

                    if (!addedProgIds.Contains(progId) && null != row[2] && null == progId.ParentElement)
                    {
                        ArrayList classElements = (ArrayList)classes[row[2]];

                        if (null != classElements)
                        {
                            foreach (Wix.Class wixClass in classElements)
                            {
                                wixClass.AddChild(progId);
                                addedProgIds.Add(progId, wixClass.Id);
                            }
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "ProgId", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Class_", Convert.ToString(row[2]), "Class"));
                        }
                    }
                }
            }

            if (null != componentTable)
            {
                foreach (Row row in componentTable.Rows)
                {
                    Wix.Component wixComponent = (Wix.Component)this.core.GetIndexedElement(row);

                    // index the Class elements for nesting of ProgId elements (which don't use the full Class primary key)
                    if (!components.Contains(wixComponent.Id))
                    {
                        components.Add(wixComponent.Id, new ArrayList());
                    }
                    ((ArrayList)components[wixComponent.Id]).Add(wixComponent);
                }
            }

            // Check for any progIds that are not hooked up to a class and hook them up to the component specified by the extension
            if (null != extensionTable)
            {
                foreach (Row row in extensionTable.Rows)
                {
                    // ignore the extension if it isn't associated with a progId
                    if (null == row[2])
                    {
                        continue;
                    }

                    Wix.ProgId progId = (Wix.ProgId)this.core.GetIndexedElement("ProgId", Convert.ToString(row[2]));

                    // Haven't added the progId yet and it doesn't have a parent progId
                    if (!addedProgIds.Contains(progId) && null == progId.ParentElement)
                    {
                        ArrayList componentElements = (ArrayList)components[row[1]];

                        if (null != componentElements)
                        {
                            foreach (Wix.Component wixComponent in componentElements)
                            {
                                wixComponent.AddChild(progId);
                            }
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Extension", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Component_", Convert.ToString(row[1]), "Component"));
                        }
                    }
                }
            }
        }
Beispiel #11
0
 /// <summary>
 /// Finalize decompilation.
 /// </summary>
 /// <param name="tables">The collection of all tables.</param>
 public virtual void FinalizeDecompile(TableCollection tables)
 {
 }
Beispiel #12
0
        /// <summary>
        /// Resolve source fields in the tables included in the output
        /// </summary>
        /// <param name="tables">The tables to resolve.</param>
        /// <param name="cabinets">Cabinets containing files that need to be patched.</param>
        /// <param name="delayedFields">The collection of delayed fields. Null if resolution of delayed fields is not allowed</param>
        private void ResolveFields(TableCollection tables, Hashtable cabinets, ArrayList delayedFields)
        {
            foreach (Table table in tables)
            {
                foreach (Row row in table.Rows)
                {
                    foreach (Field field in row.Fields)
                    {
                        bool isDefault = true;
                        bool delayedResolve = false;

                        // Check to make sure we're in a scenario where we can handle variable resolution.
                        if (null != delayedFields)
                        {
                            // resolve localization and wix variables
                            if (field.Data is string)
                            {
                                field.Data = this.WixVariableResolver.ResolveVariables(row.SourceLineNumbers, (string)field.Data, false, ref isDefault, ref delayedResolve);
                                if (delayedResolve)
                                {
                                    delayedFields.Add(new DelayedField(row, field));
                                }
                            }
                        }

                        // resolve file paths
                        if (!this.WixVariableResolver.EncounteredError && ColumnType.Object == field.Column.Type)
                        {
                            ObjectField objectField = (ObjectField)field;

                            // skip file resolution if the file is to be deleted
                            if (RowOperation.Delete == row.Operation)
                            {
                                continue;
                            }

                            // file is compressed in a cabinet (and not modified above)
                            if (null != objectField.CabinetFileId && isDefault)
                            {
                                // index cabinets that have not been previously encountered
                                if (!cabinets.ContainsKey(objectField.BaseUri))
                                {
                                    Uri baseUri = new Uri(objectField.BaseUri);
                                    string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                    string extractedDirectoryName = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                    // index the cabinet file's base URI (source location) and extracted directory
                                    cabinets.Add(objectField.BaseUri, Path.Combine(this.TempFilesLocation, extractedDirectoryName));
                                }

                                // set the path to the file once its extracted from the cabinet
                                objectField.Data = Path.Combine((string)cabinets[objectField.BaseUri], objectField.CabinetFileId);
                            }
                            else if (null != objectField.Data) // non-compressed file (or localized value)
                            {
                                // when SuppressFileHasAndInfo is true do not resolve file paths
                                if (this.suppressFileHashAndInfo && table.Name == "WixFile")
                                {
                                    continue;
                                }

                                try
                                {
                                    if (OutputType.Patch != this.FileManager.Output.Type) // Normal binding for non-Patch scenario such as link (light.exe)
                                    {
                                        // keep a copy of the un-resolved data for future replay. This will be saved into wixpdb file
                                        if (null == objectField.UnresolvedData)
                                        {
                                            objectField.UnresolvedData = (string)objectField.Data;
                                        }

                                        // resolve the path to the file
                                        objectField.Data = this.FileManager.ResolveFile((string)objectField.Data, table.Name, row.SourceLineNumbers, BindStage.Normal);
                                    }
                                    else if (!(this.FileManager.ReBaseTarget || this.FileManager.ReBaseUpdated)) // Normal binding for Patch Scenario (normal patch, no re-basing logic)
                                    {
                                        // resolve the path to the file
                                        objectField.Data = this.FileManager.ResolveFile((string)objectField.Data, table.Name, row.SourceLineNumbers, BindStage.Normal);
                                    }
                                    else // Re-base binding path scenario caused by pyro.exe -bt -bu
                                    {
                                        // by default, use the resolved Data for file lookup
                                        string filePathToResolve = (string)objectField.Data;

                                        // if -bu is used in pyro command, this condition holds true and the tool
                                        // will use pre-resolved source for new wixpdb file
                                        if (this.FileManager.ReBaseUpdated)
                                        {
                                            // try to use the unResolved Source if it exists.
                                            // New version of wixpdb file keeps a copy of pre-resolved Source. i.e. !(bindpath.test)\foo.dll
                                            // Old version of winpdb file does not contain this attribute and the value is null.
                                            if (null != objectField.UnresolvedData)
                                            {
                                                filePathToResolve = objectField.UnresolvedData;
                                            }
                                        }

                                        objectField.Data = this.FileManager.ResolveFile(filePathToResolve, table.Name, row.SourceLineNumbers, BindStage.Updated);
                                    }
                                }
                                catch (WixFileNotFoundException)
                                {
                                    // display the error with source line information
                                    this.core.OnMessage(WixErrors.FileNotFound(row.SourceLineNumbers, (string)objectField.Data));
                                }
                            }

                            isDefault = true;
                            if (null != objectField.PreviousData)
                            {
                                objectField.PreviousData = this.WixVariableResolver.ResolveVariables(row.SourceLineNumbers, objectField.PreviousData, false, ref isDefault);
                                if (!this.WixVariableResolver.EncounteredError)
                                {
                                    // file is compressed in a cabinet (and not modified above)
                                    if (null != objectField.PreviousCabinetFileId && isDefault)
                                    {
                                        // when loading transforms from disk, PreviousBaseUri may not have been set
                                        if (null == objectField.PreviousBaseUri)
                                        {
                                            objectField.PreviousBaseUri = objectField.BaseUri;
                                        }

                                        // index cabinets that have not been previously encountered
                                        if (!cabinets.ContainsKey(objectField.PreviousBaseUri))
                                        {
                                            Uri baseUri = new Uri(objectField.PreviousBaseUri);
                                            string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                            string extractedDirectoryName = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                            // index the cabinet file's base URI (source location) and extracted directory
                                            cabinets.Add(objectField.PreviousBaseUri, Path.Combine(this.TempFilesLocation, extractedDirectoryName));
                                        }

                                        // set the path to the file once its extracted from the cabinet
                                        objectField.PreviousData = Path.Combine((string)cabinets[objectField.PreviousBaseUri], objectField.PreviousCabinetFileId);
                                    }
                                    else if (null != objectField.PreviousData) // non-compressed file (or localized value)
                                    {
                                        // when SuppressFileHasAndInfo is true do not resolve file paths
                                        if (this.suppressFileHashAndInfo && table.Name == "WixFile")
                                        {
                                            continue;
                                        }

                                        try
                                        {
                                            if (!this.FileManager.ReBaseTarget && !this.FileManager.ReBaseUpdated)
                                            {
                                                // resolve the path to the file
                                                objectField.PreviousData = this.FileManager.ResolveFile((string)objectField.PreviousData, table.Name, row.SourceLineNumbers, BindStage.Normal);
                                            }
                                            else
                                            {
                                                if (this.FileManager.ReBaseTarget)
                                                {
                                                    // if -bt is used, it come here
                                                    // Try to use the original unresolved source from either target build or update build
                                                    // If both target and updated are of old wixpdb, it behaves the same as today, no re-base logic here
                                                    // If target is old version and updated is new version, it uses unresolved path from updated build
                                                    // If both target and updated are of new versions, it uses unresolved path from target build
                                                    if (null != objectField.UnresolvedPreviousData || null != objectField.UnresolvedData)
                                                    {
                                                        objectField.PreviousData = objectField.UnresolvedPreviousData ?? objectField.UnresolvedData;
                                                    }
                                                }

                                                // resolve the path to the file
                                                objectField.PreviousData = this.FileManager.ResolveFile((string)objectField.PreviousData, table.Name, row.SourceLineNumbers, BindStage.Target);

                                            }
                                        }
                                        catch (WixFileNotFoundException)
                                        {
                                            // display the error with source line information
                                            this.core.OnMessage(WixErrors.FileNotFound(row.SourceLineNumbers, (string)objectField.PreviousData));
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }

            // remember if the variable resolver found an error
            if (this.WixVariableResolver.EncounteredError)
            {
                this.core.EncounteredError = true;
            }
        }
Beispiel #13
0
        /// <summary>
        /// Merge data from the unreal tables into the real tables.
        /// </summary>
        /// <param name="tables">Collection of all tables.</param>
        private void MergeUnrealTables(TableCollection tables)
        {
            // merge data from the WixBBControl rows into the BBControl rows
            Table wixBBControlTable = tables["WixBBControl"];
            Table bbControlTable = tables["BBControl"];
            if (null != wixBBControlTable && null != bbControlTable)
            {
                // index all the BBControl rows by their identifier
                Hashtable indexedBBControlRows = new Hashtable(bbControlTable.Rows.Count);
                foreach (BBControlRow bbControlRow in bbControlTable.Rows)
                {
                    indexedBBControlRows.Add(bbControlRow.GetPrimaryKey('/'), bbControlRow);
                }

                foreach (Row row in wixBBControlTable.Rows)
                {
                    BBControlRow bbControlRow = (BBControlRow)indexedBBControlRows[row.GetPrimaryKey('/')];

                    bbControlRow.SourceFile = (string)row[2];
                }
            }

            // merge data from the WixControl rows into the Control rows
            Table wixControlTable = tables["WixControl"];
            Table controlTable = tables["Control"];
            if (null != wixControlTable && null != controlTable)
            {
                // index all the Control rows by their identifier
                Hashtable indexedControlRows = new Hashtable(controlTable.Rows.Count);
                foreach (ControlRow controlRow in controlTable.Rows)
                {
                    indexedControlRows.Add(controlRow.GetPrimaryKey('/'), controlRow);
                }

                foreach (Row row in wixControlTable.Rows)
                {
                    ControlRow controlRow = (ControlRow)indexedControlRows[row.GetPrimaryKey('/')];

                    controlRow.SourceFile = (string)row[2];
                }
            }

            // merge data from the WixFile rows into the File rows
            Table wixFileTable = tables["WixFile"];
            Table fileTable = tables["File"];
            if (null != wixFileTable && null != fileTable)
            {
                // index all the File rows by their identifier
                Hashtable indexedFileRows = new Hashtable(fileTable.Rows.Count, StringComparer.OrdinalIgnoreCase);

                foreach (FileRow fileRow in fileTable.Rows)
                {
                    try
                    {
                        indexedFileRows.Add(fileRow.File, fileRow);
                    }
                    catch (ArgumentException)
                    {
                        this.core.OnMessage(WixErrors.DuplicateFileId(fileRow.File));
                    }
                }

                if (this.core.EncounteredError)
                {
                    return;
                }

                foreach (WixFileRow row in wixFileTable.Rows)
                {
                    FileRow fileRow = (FileRow)indexedFileRows[row.File];

                    if (null != row[1])
                    {
                        fileRow.AssemblyType = (FileAssemblyType)Enum.ToObject(typeof(FileAssemblyType), row.AssemblyAttributes);
                    }
                    else
                    {
                        fileRow.AssemblyType = FileAssemblyType.NotAnAssembly;
                    }
                    fileRow.AssemblyApplication = row.AssemblyApplication;
                    fileRow.AssemblyManifest = row.AssemblyManifest;
                    fileRow.Directory = row.Directory;
                    fileRow.DiskId = row.DiskId;
                    fileRow.Source = row.Source;
                    fileRow.PreviousSource = row.PreviousSource;
                    fileRow.ProcessorArchitecture = row.ProcessorArchitecture;
                    fileRow.PatchGroup = row.PatchGroup;
                    fileRow.PatchAttributes = row.PatchAttributes;
                    fileRow.RetainLengths = row.RetainLengths;
                    fileRow.IgnoreOffsets = row.IgnoreOffsets;
                    fileRow.IgnoreLengths = row.IgnoreLengths;
                    fileRow.RetainOffsets = row.RetainOffsets;
                    fileRow.PreviousRetainLengths = row.PreviousRetainLengths;
                    fileRow.PreviousIgnoreOffsets = row.PreviousIgnoreOffsets;
                    fileRow.PreviousIgnoreLengths = row.PreviousIgnoreLengths;
                    fileRow.PreviousRetainOffsets = row.PreviousRetainOffsets;
                }
            }

            // merge data from the WixPatchSymbolPaths rows into the File rows
            Table wixPatchSymbolPathsTable = tables["WixPatchSymbolPaths"];
            Table mediaTable = tables["Media"];
            Table directoryTable = tables["Directory"];
            Table componentTable = tables["Component"];
            if (null != wixPatchSymbolPathsTable)
            {
                int fileRowNum = (null != fileTable) ? fileTable.Rows.Count : 0;
                int componentRowNum = (null != fileTable) ? componentTable.Rows.Count : 0;
                int directoryRowNum = (null != directoryTable) ? directoryTable.Rows.Count : 0;
                int mediaRowNum = (null != mediaTable) ? mediaTable.Rows.Count : 0;

                Hashtable fileRowsByFile = new Hashtable(fileRowNum);
                Hashtable fileRowsByComponent = new Hashtable(componentRowNum);
                Hashtable fileRowsByDirectory = new Hashtable(directoryRowNum);
                Hashtable fileRowsByDiskId = new Hashtable(mediaRowNum);

                // index all the File rows by their identifier
                if (null != fileTable)
                {
                    foreach (FileRow fileRow in fileTable.Rows)
                    {
                        fileRowsByFile.Add(fileRow.File, fileRow);

                        ArrayList fileRows = (ArrayList)fileRowsByComponent[fileRow.Component];
                        if (null == fileRows)
                        {
                            fileRows = new ArrayList();
                            fileRowsByComponent.Add(fileRow.Component, fileRows);
                        }
                        fileRows.Add(fileRow);

                        fileRows = (ArrayList)fileRowsByDirectory[fileRow.Directory];
                        if (null == fileRows)
                        {
                            fileRows = new ArrayList();
                            fileRowsByDirectory.Add(fileRow.Directory, fileRows);
                        }
                        fileRows.Add(fileRow);

                        fileRows = (ArrayList)fileRowsByDiskId[fileRow.DiskId];
                        if (null == fileRows)
                        {
                            fileRows = new ArrayList();
                            fileRowsByDiskId.Add(fileRow.DiskId, fileRows);
                        }
                        fileRows.Add(fileRow);
                    }
                }

                wixPatchSymbolPathsTable.Rows.Sort(new WixPatchSymbolPathsComparer());

                foreach (Row row in wixPatchSymbolPathsTable.Rows)
                {
                    switch ((string)row[0])
                    {
                        case "File":
                            MergeSymbolPaths(row, (FileRow)fileRowsByFile[row[1]]);
                            break;

                        case "Product":
                            foreach (FileRow fileRow in fileRowsByFile)
                            {
                                MergeSymbolPaths(row, fileRow);
                            }
                            break;

                        case "Component":
                            ArrayList fileRowsByThisComponent = (ArrayList)(fileRowsByComponent[row[1]]);
                            if (null != fileRowsByThisComponent)
                            {
                                foreach (FileRow fileRow in fileRowsByThisComponent)
                                {
                                    MergeSymbolPaths(row, fileRow);
                                }
                            }

                            break;

                        case "Directory":
                            ArrayList fileRowsByThisDirectory = (ArrayList)(fileRowsByDirectory[row[1]]);
                            if (null != fileRowsByThisDirectory)
                            {
                                foreach (FileRow fileRow in fileRowsByThisDirectory)
                                {
                                    MergeSymbolPaths(row, fileRow);
                                }
                            }
                            break;

                        case "Media":
                            ArrayList fileRowsByThisDiskId = (ArrayList)(fileRowsByDiskId[row[1]]);
                            if (null != fileRowsByThisDiskId)
                            {
                                foreach (FileRow fileRow in fileRowsByThisDiskId)
                                {
                                    MergeSymbolPaths(row, fileRow);
                                }
                            }
                            break;

                        default:
                            // error
                            break;
                    }
                }
            }

            // copy data from the WixMedia rows into the Media rows
            Table wixMediaTable = tables["WixMedia"];
            if (null != wixMediaTable && null != mediaTable)
            {
                // index all the Media rows by their identifier
                Hashtable indexedMediaRows = new Hashtable(mediaTable.Rows.Count);
                foreach (MediaRow mediaRow in mediaTable.Rows)
                {
                    indexedMediaRows.Add(mediaRow.DiskId, mediaRow);
                }

                foreach (Row row in wixMediaTable.Rows)
                {
                    MediaRow mediaRow = (MediaRow)indexedMediaRows[row[0]];

                    // compression level
                    if (null != row[1])
                    {
                        mediaRow.CompressionLevel = WixCreateCab.CompressionLevelFromString((string)row[1]);
                    }

                    // layout
                    if (null != row[2])
                    {
                        mediaRow.Layout = (string)row[2];
                    }
                }
            }
        }
Beispiel #14
0
        /// <summary>
        /// Localize dialogs and controls.
        /// </summary>
        /// <param name="tables">The tables to localize.</param>
        private void LocalizeUI(TableCollection tables)
        {
            Table dialogTable = tables["Dialog"];
            if (null != dialogTable)
            {
                foreach (Row row in dialogTable.Rows)
                {
                    string dialog = (string)row[0];
                    LocalizedControl localizedControl = this.Localizer.GetLocalizedControl(dialog, null);
                    if (null != localizedControl)
                    {
                        if (CompilerCore.IntegerNotSet != localizedControl.X)
                        {
                            row[1] = localizedControl.X;
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Y)
                        {
                            row[2] = localizedControl.Y;
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Width)
                        {
                            row[3] = localizedControl.Width;
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Height)
                        {
                            row[4] = localizedControl.Height;
                        }

                        row[5] = (int)row[5] | localizedControl.Attributes;

                        if (!String.IsNullOrEmpty(localizedControl.Text))
                        {
                            row[6] = localizedControl.Text;
                        }
                    }
                }
            }

            Table controlTable = tables["Control"];
            if (null != controlTable)
            {
                foreach (Row row in controlTable.Rows)
                {
                    string dialog = (string)row[0];
                    string control = (string)row[1];
                    LocalizedControl localizedControl = this.Localizer.GetLocalizedControl(dialog, control);
                    if (null != localizedControl)
                    {
                        if (CompilerCore.IntegerNotSet != localizedControl.X)
                        {
                            row[3] = localizedControl.X.ToString();
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Y)
                        {
                            row[4] = localizedControl.Y.ToString();
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Width)
                        {
                            row[5] = localizedControl.Width.ToString();
                        }

                        if (CompilerCore.IntegerNotSet != localizedControl.Height)
                        {
                            row[6] = localizedControl.Height.ToString();
                        }

                        row[7] = (int)row[7] | localizedControl.Attributes;

                        if (!String.IsNullOrEmpty(localizedControl.Text))
                        {
                            row[9] = localizedControl.Text;
                        }
                    }
                }
            }
        }
Beispiel #15
0
        /// <summary>
        /// Finalize the File table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Sets the source, diskId, and assembly information for each file.
        /// </remarks>
        private void FinalizeFileTable(TableCollection tables)
        {
            Table fileTable = tables["File"];
            Table mediaTable = tables["Media"];
            Table msiAssemblyTable = tables["MsiAssembly"];
            Table typeLibTable = tables["TypeLib"];

            MediaRowCollection mediaRows;

            // index the media table by media id
            if (null != mediaTable)
            {
                mediaRows = new MediaRowCollection();
                mediaRows.AddRange(mediaTable.Rows);
            }

            // set the disk identifiers and sources for files
            if (null != fileTable)
            {
                foreach (FileRow fileRow in fileTable.Rows)
                {
                    Wix.File file = (Wix.File)this.core.GetIndexedElement("File", fileRow.File);

                    // Don't bother processing files that are orphaned (and won't show up in the output anyway)
                    if (null != file.ParentElement)
                    {
                        // set the diskid
                        if (null != mediaTable)
                        {
                            foreach (MediaRow mediaRow in mediaTable.Rows)
                            {
                                if (fileRow.Sequence <= mediaRow.LastSequence)
                                {
                                    file.DiskId = Convert.ToString(mediaRow.DiskId);
                                    break;
                                }
                            }
                        }                     

                        // set the source (done here because it requires information from the Directory table)
                        if (OutputType.Module == this.outputType)
                        {
                            file.Source = String.Concat(this.exportFilePath, Path.DirectorySeparatorChar, "File", Path.DirectorySeparatorChar, file.Id, '.', this.modularizationGuid.Substring(1, 36).Replace('-', '_'));
                        }
                        else if (Wix.YesNoDefaultType.yes == file.Compressed || (Wix.YesNoDefaultType.no != file.Compressed && this.compressed))
                        {
                            file.Source = String.Concat(this.exportFilePath, Path.DirectorySeparatorChar, "File", Path.DirectorySeparatorChar, file.Id);
                        }
                        else // uncompressed
                        {
                            string fileName = (null != file.ShortName ? file.ShortName : file.Name);

                            if (!this.shortNames && null != file.Name)
                            {
                                fileName = file.Name;
                            }

                            if (this.compressed) // uncompressed at the root of the source image
                            {
                                file.Source = String.Concat("SourceDir", Path.DirectorySeparatorChar, fileName);
                            }
                            else
                            {
                                string sourcePath = this.GetSourcePath(file);

                                file.Source = Path.Combine(sourcePath, fileName);
                            }
                        }
                    }
                }
            }

            // set the file assemblies and manifests
            if (null != msiAssemblyTable)
            {
                foreach (Row row in msiAssemblyTable.Rows)
                {
                    Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", Convert.ToString(row[0]));

                    if (null == component)
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "MsiAssembly", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Component_", Convert.ToString(row[0]), "Component"));
                    }
                    else
                    {
                        foreach (Wix.ISchemaElement element in component.Children)
                        {
                            Wix.File file = element as Wix.File;

                            if (null != file && Wix.YesNoType.yes == file.KeyPath)
                            {
                                if (null != row[2])
                                {
                                    file.AssemblyManifest = Convert.ToString(row[2]);
                                }

                                if (null != row[3])
                                {
                                    file.AssemblyApplication = Convert.ToString(row[3]);
                                }

                                if (null == row[4] || 0 == Convert.ToInt32(row[4]))
                                {
                                    file.Assembly = Wix.File.AssemblyType.net;
                                }
                                else
                                {
                                    file.Assembly = Wix.File.AssemblyType.win32;
                                }
                            }
                        }
                    }
                }
            }

            // nest the TypeLib elements
            if (null != typeLibTable)
            {
                foreach (Row row in typeLibTable.Rows)
                {
                    Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", Convert.ToString(row[2]));
                    Wix.TypeLib typeLib = (Wix.TypeLib)this.core.GetIndexedElement(row);

                    foreach (Wix.ISchemaElement element in component.Children)
                    {
                        Wix.File file = element as Wix.File;

                        if (null != file && Wix.YesNoType.yes == file.KeyPath)
                        {
                            file.AddChild(typeLib);
                        }
                    }
                }
            }
        }
Beispiel #16
0
        /// <summary>
        /// Finalize the MIME table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// There is a foreign key shared between the MIME and Extension
        /// tables so either one would be valid to be decompiled first, so
        /// the only safe way to nest the MIME elements is to do it during finalize.
        /// </remarks>
        private void FinalizeMIMETable(TableCollection tables)
        {
            Table extensionTable = tables["Extension"];
            Table mimeTable = tables["MIME"];

            Hashtable comExtensions = new Hashtable();

            if (null != extensionTable)
            {
                foreach (Row row in extensionTable.Rows)
                {
                    Wix.Extension extension = (Wix.Extension)this.core.GetIndexedElement(row);

                    // index the extension
                    if (!comExtensions.Contains(row[0]))
                    {
                        comExtensions.Add(row[0], new ArrayList());
                    }
                    ((ArrayList)comExtensions[row[0]]).Add(extension);

                    // set the default MIME element for this extension
                    if (null != row[3])
                    {
                        Wix.MIME mime = (Wix.MIME)this.core.GetIndexedElement("MIME", Convert.ToString(row[3]));

                        if (null != mime)
                        {
                            mime.Default = Wix.YesNoType.yes;
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Extension", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "MIME_", Convert.ToString(row[3]), "MIME"));
                        }
                    }
                }
            }

            if (null != mimeTable)
            {
                foreach (Row row in mimeTable.Rows)
                {
                    Wix.MIME mime = (Wix.MIME)this.core.GetIndexedElement(row);

                    if (comExtensions.Contains(row[1]))
                    {
                        ArrayList extensionElements = (ArrayList)comExtensions[row[1]];

                        foreach (Wix.Extension extension in extensionElements)
                        {
                            extension.AddChild(mime);
                        }
                    }
                    else
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "MIME", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Extension_", Convert.ToString(row[1]), "Extension"));
                    }
                }
            }
        }
Beispiel #17
0
        /// <summary>
        /// Resolves paths to files.
        /// </summary>
        /// <param name="sectionTables">TableCollection of tables to process</param>
        /// <param name="binderFileManager">If provided, the binder file manager is used to bind files into the output.</param>
        /// <param name="wixVariableResolver">The Wix variable resolver.</param>
        /// <param name="tempFilesLocation">Location for temporary files.</param>
        /// <param name="cabinets">Hash of source cabinets.</param>
        /// <param name="fileIds">Collection of CabinetFileIds.</param>
        /// <param name="files">Collection of file paths from compressed files.</param>
        /// <param name="index">CabinetFileId generator.</param>
        public static void ResolveSectionFiles(TableCollection sectionTables, BinderFileManager binderFileManager, WixVariableResolver wixVariableResolver, string tempFilesLocation, Hashtable cabinets, StringCollection fileIds, StringCollection files, ref int index)
        {
            foreach (Table table in sectionTables)
            {
                foreach (Row row in table.Rows)
                {
                    foreach (Field field in row.Fields)
                    {
                        ObjectField objectField = field as ObjectField;

                        if (null != objectField && null != objectField.Data)
                        {
                            string file              = null;
                            string previousFile      = null;
                            bool   isDefault         = true;
                            bool   isPreviousDefault = true;

                            // resolve localization and wix variables if there is a file manager that would use the value
                            // if it was different, otherwise we just don't care so skip the whole variable resolution thing.
                            if (null != wixVariableResolver && null != binderFileManager)
                            {
                                objectField.Data = wixVariableResolver.ResolveVariables(row.SourceLineNumbers, (string)objectField.Data, false, ref isDefault);

                                if (null != objectField.PreviousData)
                                {
                                    objectField.PreviousData = wixVariableResolver.ResolveVariables(row.SourceLineNumbers, objectField.PreviousData, false, ref isPreviousDefault);
                                }

                                // do not save the output if errors were found while resolving object paths
                                if (wixVariableResolver.EncounteredError)
                                {
                                    return;
                                }
                            }

                            // file is compressed in a cabinet (and not modified above)
                            if (null != objectField.CabinetFileId && isDefault)
                            {
                                // index cabinets that have not been previously encountered
                                if (!cabinets.ContainsKey(objectField.BaseUri))
                                {
                                    Uri    baseUri = new Uri(objectField.BaseUri);
                                    string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                    string extractedDirectoryName        = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                    // index the cabinet file's base URI (source location) and extracted directory
                                    cabinets.Add(objectField.BaseUri, Path.Combine(tempFilesLocation, extractedDirectoryName));
                                }

                                // set the path to the file once its extracted from the cabinet
                                file = Path.Combine((string)cabinets[objectField.BaseUri], objectField.CabinetFileId);
                            }
                            else if (null != binderFileManager)
                            {
                                file = binderFileManager.ResolveFile((string)objectField.Data, table.Name, row.SourceLineNumbers, BindStage.Normal);
                            }

                            // add the file to the list of files to go in the cabinet
                            if (null != file)
                            {
                                string cabinetFileId = (index++).ToString(CultureInfo.InvariantCulture);

                                objectField.CabinetFileId = cabinetFileId;
                                fileIds.Add(cabinetFileId);

                                files.Add(file);
                            }

                            // previous file is compressed in a cabinet (and not modified above)
                            if (null != objectField.PreviousCabinetFileId && isPreviousDefault)
                            {
                                // index cabinets that have not been previously encountered
                                if (!cabinets.ContainsKey(objectField.PreviousBaseUri))
                                {
                                    Uri    baseUri = new Uri(objectField.PreviousBaseUri);
                                    string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                    string extractedDirectoryName        = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                    // index the cabinet file's base URI (source location) and extracted directory
                                    cabinets.Add(objectField.PreviousBaseUri, Path.Combine(tempFilesLocation, extractedDirectoryName));
                                }

                                // set the path to the file once its extracted from the cabinet
                                previousFile = Path.Combine((string)cabinets[objectField.PreviousBaseUri], objectField.PreviousCabinetFileId);
                            }
                            else if (null != objectField.PreviousData && null != binderFileManager)
                            {
                                previousFile = binderFileManager.ResolveFile((string)objectField.PreviousData, table.Name, row.SourceLineNumbers, BindStage.Normal);
                            }

                            // add the file to the list of files to go in the cabinet
                            if (null != previousFile)
                            {
                                string cabinetFileId = (index++).ToString(CultureInfo.InvariantCulture);

                                objectField.PreviousCabinetFileId = cabinetFileId;
                                fileIds.Add(cabinetFileId);

                                files.Add(previousFile);
                            }
                        }
                    }
                }
            }
        }
Beispiel #18
0
        /// <summary>
        /// Finalize the Property table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Removes properties that are generated from other entries.
        /// </remarks>
        private void FinalizePropertyTable(TableCollection tables)
        {
            Table propertyTable = tables["Property"];
            Table customActionTable = tables["CustomAction"];

            if (null != propertyTable && null != customActionTable)
            {
                foreach (Row row in customActionTable.Rows)
                {
                    int bits = Convert.ToInt32(row[1]);
                    if (MsiInterop.MsidbCustomActionTypeHideTarget == (bits & MsiInterop.MsidbCustomActionTypeHideTarget) &&
                        MsiInterop.MsidbCustomActionTypeInScript == (bits & MsiInterop.MsidbCustomActionTypeInScript))
                    {
                        Wix.Property property = (Wix.Property)this.core.GetIndexedElement("Property", Convert.ToString(row[0]));

                        // If no other fields on the property are set we must have created it during link
                        if (null == property.Value && Wix.YesNoType.yes != property.Secure && Wix.YesNoType.yes != property.SuppressModularization)
                        {
                            this.core.RootElement.RemoveChild(property);
                        }
                    }
                }
            }
        }
Beispiel #19
0
        /// <summary>
        /// Resolves paths to files.
        /// </summary>
        /// <param name="sectionTables">TableCollection of tables to process</param>
        /// <param name="binderFileManager">If provided, the binder file manager is used to bind files into the output.</param>
        /// <param name="wixVariableResolver">The Wix variable resolver.</param>
        /// <param name="tempFilesLocation">Location for temporary files.</param>
        /// <param name="cabinets">Hash of source cabinets.</param>
        /// <param name="fileIds">Collection of CabinetFileIds.</param>
        /// <param name="files">Collection of file paths from compressed files.</param>
        /// <param name="index">CabinetFileId generator.</param>
        public static void ResolveSectionFiles(TableCollection sectionTables, BinderFileManager binderFileManager, WixVariableResolver wixVariableResolver, string tempFilesLocation, Hashtable cabinets, StringCollection fileIds, StringCollection files, ref int index)
        {
            foreach (Table table in sectionTables)
            {
                foreach (Row row in table.Rows)
                {
                    foreach (Field field in row.Fields)
                    {
                        ObjectField objectField = field as ObjectField;

                        if (null != objectField && null != objectField.Data)
                        {
                            string file = null;
                            string previousFile = null;
                            bool isDefault = true;
                            bool isPreviousDefault = true;

                            // resolve localization and wix variables if there is a file manager that would use the value
                            // if it was different, otherwise we just don't care so skip the whole variable resolution thing.
                            if (null != wixVariableResolver && null != binderFileManager)
                            {
                                objectField.Data = wixVariableResolver.ResolveVariables(row.SourceLineNumbers, (string)objectField.Data, false, ref isDefault);

                                if (null != objectField.PreviousData)
                                {
                                    objectField.PreviousData = wixVariableResolver.ResolveVariables(row.SourceLineNumbers, objectField.PreviousData, false, ref isPreviousDefault);
                                }

                                // do not save the output if errors were found while resolving object paths
                                if (wixVariableResolver.EncounteredError)
                                {
                                    return;
                                }
                            }

                            // file is compressed in a cabinet (and not modified above)
                            if (null != objectField.CabinetFileId && isDefault)
                            {
                                // index cabinets that have not been previously encountered
                                if (!cabinets.ContainsKey(objectField.BaseUri))
                                {
                                    Uri baseUri = new Uri(objectField.BaseUri);
                                    string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                    string extractedDirectoryName = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                    // index the cabinet file's base URI (source location) and extracted directory
                                    cabinets.Add(objectField.BaseUri, Path.Combine(tempFilesLocation, extractedDirectoryName));
                                }

                                // set the path to the file once its extracted from the cabinet
                                file = Path.Combine((string)cabinets[objectField.BaseUri], objectField.CabinetFileId);
                            }
                            else if (null != binderFileManager)
                            {
                                file = binderFileManager.ResolveFile((string)objectField.Data, table.Name, row.SourceLineNumbers, BindStage.Normal);
                            }

                            // add the file to the list of files to go in the cabinet
                            if (null != file)
                            {
                                string cabinetFileId = (index++).ToString(CultureInfo.InvariantCulture);

                                objectField.CabinetFileId = cabinetFileId;
                                fileIds.Add(cabinetFileId);

                                files.Add(file);
                            }

                            // previous file is compressed in a cabinet (and not modified above)
                            if (null != objectField.PreviousCabinetFileId && isPreviousDefault)
                            {
                                // index cabinets that have not been previously encountered
                                if (!cabinets.ContainsKey(objectField.PreviousBaseUri))
                                {
                                    Uri baseUri = new Uri(objectField.PreviousBaseUri);
                                    string localFileNameWithoutExtension = Path.GetFileNameWithoutExtension(baseUri.LocalPath);
                                    string extractedDirectoryName = String.Format(CultureInfo.InvariantCulture, "cab_{0}_{1}", cabinets.Count, localFileNameWithoutExtension);

                                    // index the cabinet file's base URI (source location) and extracted directory
                                    cabinets.Add(objectField.PreviousBaseUri, Path.Combine(tempFilesLocation, extractedDirectoryName));
                                }

                                // set the path to the file once its extracted from the cabinet
                                previousFile = Path.Combine((string)cabinets[objectField.PreviousBaseUri], objectField.PreviousCabinetFileId);
                            }
                            else if (null != objectField.PreviousData && null != binderFileManager)
                            {
                                previousFile = binderFileManager.ResolveFile((string)objectField.PreviousData, table.Name, row.SourceLineNumbers, BindStage.Normal);
                            }

                            // add the file to the list of files to go in the cabinet
                            if (null != previousFile)
                            {
                                string cabinetFileId = (index++).ToString(CultureInfo.InvariantCulture);

                                objectField.PreviousCabinetFileId = cabinetFileId;
                                fileIds.Add(cabinetFileId);

                                files.Add(previousFile);
                            }
                        }
                    }
                }
            }
        }
Beispiel #20
0
        /// <summary>
        /// Finalize the MsiLockPermissionsEx table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Nests the PermissionEx elements below their parent elements.  There are no declared foreign
        /// keys for the parents of the MsiLockPermissionsEx table.
        /// </remarks>
        private void FinalizeMsiLockPermissionsExTable(TableCollection tables)
        {
            Table createFolderTable = tables["CreateFolder"];
            Table msiLockPermissionsExTable = tables["MsiLockPermissionsEx"];

            Hashtable createFolders = new Hashtable();

            // index the CreateFolder table because the foreign key to this table from the
            // MsiLockPermissionsEx table is only part of the primary key of this table
            if (null != createFolderTable)
            {
                foreach (Row row in createFolderTable.Rows)
                {
                    Wix.CreateFolder createFolder = (Wix.CreateFolder)this.core.GetIndexedElement(row);
                    string directoryId = Convert.ToString(row[0]);

                    if (!createFolders.Contains(directoryId))
                    {
                        createFolders.Add(directoryId, new ArrayList());
                    }
                    ((ArrayList)createFolders[directoryId]).Add(createFolder);
                }
            }

            if (null != msiLockPermissionsExTable)
            {
                foreach (Row row in msiLockPermissionsExTable.Rows)
                {
                    string id = Convert.ToString(row[1]);
                    string table = Convert.ToString(row[2]);

                    Wix.PermissionEx permissionEx = (Wix.PermissionEx)this.core.GetIndexedElement(row);

                    if ("CreateFolder" == table)
                    {
                        ArrayList createFolderElements = (ArrayList)createFolders[id];

                        if (null != createFolderElements)
                        {
                            foreach (Wix.CreateFolder createFolder in createFolderElements)
                            {
                                createFolder.AddChild(permissionEx);
                            }
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "MsiLockPermissionsEx", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "LockObject", id, table));
                        }
                    }
                    else
                    {
                        Wix.IParentElement parentElement = (Wix.IParentElement)this.core.GetIndexedElement(table, id);

                        if (null != parentElement)
                        {
                            parentElement.AddChild(permissionEx);
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "MsiLockPermissionsEx", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "LockObject", id, table));
                        }
                    }
                }
            }
        }
Beispiel #21
0
        /// <summary>
        /// Finalize the Component table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Set the keypaths for each component.
        /// </remarks>
        private void FinalizeComponentTable(TableCollection tables)
        {
            Table componentTable = tables["Component"];
            Table fileTable = tables["File"];
            Table odbcDataSourceTable = tables["ODBCDataSource"];
            Table registryTable = tables["Registry"];

            // set the component keypaths
            if (null != componentTable)
            {
                foreach (Row row in componentTable.Rows)
                {
                    int attributes = Convert.ToInt32(row[3]);

                    if (null == row[5])
                    {
                        Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", Convert.ToString(row[0]));

                        component.KeyPath = Wix.YesNoType.yes;
                    }
                    else if (MsiInterop.MsidbComponentAttributesRegistryKeyPath == (attributes & MsiInterop.MsidbComponentAttributesRegistryKeyPath))
                    {
                        object registryObject = this.core.GetIndexedElement("Registry", Convert.ToString(row[5]));

                        if (null != registryObject)
                        {
                            Wix.RegistryValue registryValue = registryObject as Wix.RegistryValue;

                            if (null != registryValue)
                            {
                                registryValue.KeyPath = Wix.YesNoType.yes;
                            }
                            else
                            {
                                this.core.OnMessage(WixWarnings.IllegalRegistryKeyPath(row.SourceLineNumbers, "Component", Convert.ToString(row[5])));
                            }
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Component", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "KeyPath", Convert.ToString(row[5]), "Registry"));
                        }
                    }
                    else if (MsiInterop.MsidbComponentAttributesODBCDataSource == (attributes & MsiInterop.MsidbComponentAttributesODBCDataSource))
                    {
                        Wix.ODBCDataSource odbcDataSource = (Wix.ODBCDataSource)this.core.GetIndexedElement("ODBCDataSource", Convert.ToString(row[5]));

                        if (null != odbcDataSource)
                        {
                            odbcDataSource.KeyPath = Wix.YesNoType.yes;
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Component", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "KeyPath", Convert.ToString(row[5]), "ODBCDataSource"));
                        }
                    }
                    else
                    {
                        Wix.File file = (Wix.File)this.core.GetIndexedElement("File", Convert.ToString(row[5]));

                        if (null != file)
                        {
                            file.KeyPath = Wix.YesNoType.yes;
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Component", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "KeyPath", Convert.ToString(row[5]), "File"));
                        }
                    }
                }
            }

            // add the File children elements
            if (null != fileTable)
            {
                foreach (FileRow fileRow in fileTable.Rows)
                {
                    Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", fileRow.Component);
                    Wix.File file = (Wix.File)this.core.GetIndexedElement(fileRow);

                    if (null != component)
                    {
                        component.AddChild(file);
                    }
                    else
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(fileRow.SourceLineNumbers, "File", fileRow.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Component_", fileRow.Component, "Component"));
                    }
                }
            }

            // add the ODBCDataSource children elements
            if (null != odbcDataSourceTable)
            {
                foreach (Row row in odbcDataSourceTable.Rows)
                {
                    Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", Convert.ToString(row[1]));
                    Wix.ODBCDataSource odbcDataSource = (Wix.ODBCDataSource)this.core.GetIndexedElement(row);

                    if (null != component)
                    {
                        component.AddChild(odbcDataSource);
                    }
                    else
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "ODBCDataSource", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Component_", Convert.ToString(row[1]), "Component"));
                    }
                }
            }

            // add the Registry children elements
            if (null != registryTable)
            {
                foreach (Row row in registryTable.Rows)
                {
                    Wix.Component component = (Wix.Component)this.core.GetIndexedElement("Component", Convert.ToString(row[5]));
                    Wix.ISchemaElement registryElement = (Wix.ISchemaElement)this.core.GetIndexedElement(row);

                    if (null != component)
                    {
                        component.AddChild(registryElement);
                    }
                    else
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Registry", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Component_", Convert.ToString(row[5]), "Component"));
                    }
                }
            }
        }
Beispiel #22
0
        /// <summary>
        /// Finalize the sequence tables.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Creates the sequence elements.  Occurs during finalization because its
        /// not known if sequences refer to custom actions or dialogs during decompilation.
        /// </remarks>
        private void FinalizeSequenceTables(TableCollection tables)
        {
            // finalize the normal sequence tables
            if (OutputType.Product == this.outputType && !this.treatProductAsModule)
            {
                foreach (SequenceTable sequenceTable in Enum.GetValues(typeof(SequenceTable)))
                {
                    // if suppressing UI elements, skip UI-related sequence tables
                    if (this.suppressUI && ("AdminUISequence" == sequenceTable.ToString() || "InstallUISequence" == sequenceTable.ToString()))
                    {
                        continue;
                    }

                    Table actionsTable = new Table(null, this.tableDefinitions["WixAction"]);
                    Table table = tables[sequenceTable.ToString()];

                    if (null != table)
                    {
                        ArrayList actionRows = new ArrayList();
                        bool needAbsoluteScheduling = this.suppressRelativeActionSequencing;
                        WixActionRowCollection nonSequencedActionRows = new WixActionRowCollection();
                        WixActionRowCollection suppressedRelativeActionRows = new WixActionRowCollection();

                        // create a sorted array of actions in this table
                        foreach (Row row in table.Rows)
                        {
                            WixActionRow actionRow = (WixActionRow)actionsTable.CreateRow(null);

                            actionRow.Action = Convert.ToString(row[0]);

                            if (null != row[1])
                            {
                                actionRow.Condition = Convert.ToString(row[1]);
                            }

                            actionRow.Sequence = Convert.ToInt32(row[2]);

                            actionRow.SequenceTable = sequenceTable;

                            actionRows.Add(actionRow);
                        }
                        actionRows.Sort();

                        for (int i = 0; i < actionRows.Count && !needAbsoluteScheduling; i++)
                        {
                            WixActionRow actionRow = (WixActionRow)actionRows[i];
                            WixActionRow standardActionRow = this.standardActions[actionRow.SequenceTable, actionRow.Action];

                            // create actions for custom actions, dialogs, AppSearch when its moved, and standard actions with non-standard conditions
                            if ("AppSearch" == actionRow.Action || null == standardActionRow || actionRow.Condition != standardActionRow.Condition)
                            {
                                WixActionRow previousActionRow = null;
                                WixActionRow nextActionRow = null;

                                // find the previous action row if there is one
                                if (0 <= i - 1)
                                {
                                    previousActionRow = (WixActionRow)actionRows[i - 1];
                                }

                                // find the next action row if there is one
                                if (actionRows.Count > i + 1)
                                {
                                    nextActionRow = (WixActionRow)actionRows[i + 1];
                                }

                                // the logic for setting the before or after attribute for an action:
                                // 1. If more than one action shares the same sequence number, everything must be absolutely sequenced.
                                // 2. If the next action is a standard action and is 1 sequence number higher, this action occurs before it.
                                // 3. If the previous action is a standard action and is 1 sequence number lower, this action occurs after it.
                                // 4. If this action is not standard and the previous action is 1 sequence number lower and does not occur before this action, this action occurs after it.
                                // 5. If this action is not standard and the previous action does not have the same sequence number and the next action is 1 sequence number higher, this action occurs before it.
                                // 6. If this action is AppSearch and has all standard information, ignore it.
                                // 7. If this action is standard and has a non-standard condition, create the action without any scheduling information.
                                // 8. Everything must be absolutely sequenced.
                                if ((null != previousActionRow && actionRow.Sequence == previousActionRow.Sequence) || (null != nextActionRow && actionRow.Sequence == nextActionRow.Sequence))
                                {
                                    needAbsoluteScheduling = true;
                                }
                                else if (null != nextActionRow && null != this.standardActions[sequenceTable, nextActionRow.Action] && actionRow.Sequence + 1 == nextActionRow.Sequence)
                                {
                                    actionRow.Before = nextActionRow.Action;
                                }
                                else if (null != previousActionRow && null != this.standardActions[sequenceTable, previousActionRow.Action] && actionRow.Sequence - 1 == previousActionRow.Sequence)
                                {
                                    actionRow.After = previousActionRow.Action;
                                }
                                else if (null == standardActionRow && null != previousActionRow && actionRow.Sequence - 1 == previousActionRow.Sequence && previousActionRow.Before != actionRow.Action)
                                {
                                    actionRow.After = previousActionRow.Action;
                                }
                                else if (null == standardActionRow && null != previousActionRow && actionRow.Sequence != previousActionRow.Sequence && null != nextActionRow && actionRow.Sequence + 1 == nextActionRow.Sequence)
                                {
                                    actionRow.Before = nextActionRow.Action;
                                }
                                else if ("AppSearch" == actionRow.Action && null != standardActionRow && actionRow.Sequence == standardActionRow.Sequence && actionRow.Condition == standardActionRow.Condition)
                                {
                                    // ignore an AppSearch row which has the WiX standard sequence and a standard condition
                                }
                                else if (null != standardActionRow && actionRow.Condition != standardActionRow.Condition) // standard actions get their standard sequence numbers
                                {
                                    nonSequencedActionRows.Add(actionRow);
                                }
                                else if (0 < actionRow.Sequence)
                                {
                                    needAbsoluteScheduling = true;
                                }
                            }
                            else
                            {
                                suppressedRelativeActionRows.Add(actionRow);
                            }
                        }

                        // create the actions now that we know if they must be absolutely or relatively scheduled
                        foreach (WixActionRow actionRow in actionRows)
                        {
                            if (needAbsoluteScheduling)
                            {
                                // remove any before/after information to ensure this is absolutely sequenced
                                actionRow.Before = null;
                                actionRow.After = null;
                            }
                            else if (nonSequencedActionRows.Contains(actionRow.SequenceTable, actionRow.Action))
                            {
                                // clear the sequence attribute to ensure this action is scheduled without a sequence number (or before/after)
                                actionRow.Sequence = 0;
                            }
                            else if (suppressedRelativeActionRows.Contains(actionRow.SequenceTable, actionRow.Action))
                            {
                                // skip the suppressed relatively scheduled action rows
                                continue;
                            }

                            // create the action element
                            this.CreateActionElement(actionRow);
                        }
                    }
                }
            }
            else if (OutputType.Module == this.outputType || this.treatProductAsModule) // finalize the Module sequence tables
            {
                foreach (SequenceTable sequenceTable in Enum.GetValues(typeof(SequenceTable)))
                {
                    // if suppressing UI elements, skip UI-related sequence tables
                    if (this.suppressUI && ("AdminUISequence" == sequenceTable.ToString() || "InstallUISequence" == sequenceTable.ToString()))
                    {
                        continue;
                    }

                    Table actionsTable = new Table(null, this.tableDefinitions["WixAction"]);
                    Table table = tables[String.Concat("Module", sequenceTable.ToString())];

                    if (null != table)
                    {
                        foreach (Row row in table.Rows)
                        {
                            WixActionRow actionRow = (WixActionRow)actionsTable.CreateRow(null);

                            actionRow.Action = Convert.ToString(row[0]);

                            if (null != row[1])
                            {
                                actionRow.Sequence = Convert.ToInt32(row[1]);
                            }

                            if (null != row[2] && null != row[3])
                            {
                                switch (Convert.ToInt32(row[3]))
                                {
                                    case 0:
                                        actionRow.Before = Convert.ToString(row[2]);
                                        break;
                                    case 1:
                                        actionRow.After = Convert.ToString(row[2]);
                                        break;
                                    default:
                                        this.core.OnMessage(WixWarnings.IllegalColumnValue(row.SourceLineNumbers, table.Name, row.Fields[3].Column.Name, row[3]));
                                        break;
                                }
                            }

                            if (null != row[4])
                            {
                                actionRow.Condition = Convert.ToString(row[4]);
                            }

                            actionRow.SequenceTable = sequenceTable;

                            // create action elements for non-standard actions
                            if (null == this.standardActions[actionRow.SequenceTable, actionRow.Action] || null != actionRow.After || null != actionRow.Before)
                            {
                                this.CreateActionElement(actionRow);
                            }
                        }
                    }
                }
            }
        }
Beispiel #23
0
        /// <summary>
        /// Finalize the Dialog table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Sets the first, default, and cancel control for each dialog and adds all child control
        /// elements to the dialog.
        /// </remarks>
        private void FinalizeDialogTable(TableCollection tables)
        {
            // if the user has requested to suppress the UI elements, we have nothing to do
            if (this.suppressUI)
            {
                return;
            }

            Table controlTable = tables["Control"];
            Table dialogTable = tables["Dialog"];

            Hashtable addedControls = new Hashtable();
            Hashtable controlRows = new Hashtable();

            // index the rows in the control rows (because we need the Control_Next value)
            if (null != controlTable)
            {
                foreach (Row row in controlTable.Rows)
                {
                    controlRows.Add(row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), row);
                }
            }

            if (null != dialogTable)
            {
                foreach (Row row in dialogTable.Rows)
                {
                    Wix.Dialog dialog = (Wix.Dialog)this.core.GetIndexedElement(row);
                    string dialogId = Convert.ToString(row[0]);

                    Wix.Control control = (Wix.Control)this.core.GetIndexedElement("Control", dialogId, Convert.ToString(row[7]));
                    if (null == control)
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Dialog", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Dialog", dialogId, "Control_First", Convert.ToString(row[7]), "Control"));
                    }

                    // add tabbable controls
                    while (null != control)
                    {
                        Row controlRow = (Row)controlRows[String.Concat(dialogId, DecompilerCore.PrimaryKeyDelimiter, control.Id)];

                        control.TabSkip = Wix.YesNoType.no;
                        dialog.AddChild(control);
                        addedControls.Add(control, null);

                        if (null != controlRow[10])
                        {
                            control = (Wix.Control)this.core.GetIndexedElement("Control", dialogId, Convert.ToString(controlRow[10]));
                            if (null != control)
                            {
                                // looped back to the first control in the dialog
                                if (addedControls.Contains(control))
                                {
                                    control = null;
                                }
                            }
                            else
                            {
                                this.core.OnMessage(WixWarnings.ExpectedForeignRow(controlRow.SourceLineNumbers, "Control", controlRow.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Dialog_", dialogId, "Control_Next", Convert.ToString(controlRow[10]), "Control"));
                            }
                        }
                        else
                        {
                            control = null;
                        }
                    }

                    // set default control
                    if (null != row[8])
                    {
                        Wix.Control defaultControl = (Wix.Control)this.core.GetIndexedElement("Control", dialogId, Convert.ToString(row[8]));

                        if (null != defaultControl)
                        {
                            defaultControl.Default = Wix.YesNoType.yes;
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Dialog", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Dialog", dialogId, "Control_Default", Convert.ToString(row[8]), "Control"));
                        }
                    }

                    // set cancel control
                    if (null != row[9])
                    {
                        Wix.Control cancelControl = (Wix.Control)this.core.GetIndexedElement("Control", dialogId, Convert.ToString(row[9]));

                        if (null != cancelControl)
                        {
                            cancelControl.Cancel = Wix.YesNoType.yes;
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Dialog", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Dialog", dialogId, "Control_Cancel", Convert.ToString(row[9]), "Control"));
                        }
                    }
                }
            }

            // add the non-tabbable controls to the dialog
            if (null != controlTable)
            {
                foreach (Row row in controlTable.Rows)
                {
                    Wix.Control control = (Wix.Control)this.core.GetIndexedElement(row);
                    Wix.Dialog dialog = (Wix.Dialog)this.core.GetIndexedElement("Dialog", Convert.ToString(row[0]));

                    if (null == dialog)
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Control", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Dialog_", Convert.ToString(row[0]), "Dialog"));
                        continue;
                    }

                    if (!addedControls.Contains(control))
                    {
                        control.TabSkip = Wix.YesNoType.yes;
                        dialog.AddChild(control);
                    }
                }
            }
        }
Beispiel #24
0
        /// <summary>
        /// Finalize the Verb table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// The Extension table is a foreign table for the Verb table, but the
        /// foreign key is only part of the primary key of the Extension table,
        /// so it needs special logic to be nested properly.
        /// </remarks>
        private void FinalizeVerbTable(TableCollection tables)
        {
            Table extensionTable = tables["Extension"];
            Table verbTable = tables["Verb"];

            Hashtable extensionElements = new Hashtable();

            if (null != extensionTable)
            {
                foreach (Row row in extensionTable.Rows)
                {
                    Wix.Extension extension = (Wix.Extension)this.core.GetIndexedElement(row);

                    if (!extensionElements.Contains(row[0]))
                    {
                        extensionElements.Add(row[0], new ArrayList());
                    }

                    ((ArrayList)extensionElements[row[0]]).Add(extension);
                }
            }

            if (null != verbTable)
            {
                foreach (Row row in verbTable.Rows)
                {
                    Wix.Verb verb = (Wix.Verb)this.core.GetIndexedElement(row);

                    ArrayList extensionsArray = (ArrayList)extensionElements[row[0]];
                    if (null != extensionsArray)
                    {
                        foreach (Wix.Extension extension in extensionsArray)
                        {
                            extension.AddChild(verb);
                        }
                    }
                    else
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, verbTable.Name, row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Extension_", Convert.ToString(row[0]), "Extension"));
                    }
                }
            }
        }
Beispiel #25
0
        /// <summary>
        /// Finalize the DuplicateFile and MoveFile tables.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Sets the source/destination property/directory for each DuplicateFile or
        /// MoveFile row.
        /// </remarks>
        private void FinalizeDuplicateMoveFileTables(TableCollection tables)
        {
            Table duplicateFileTable = tables["DuplicateFile"];
            Table moveFileTable = tables["MoveFile"];

            if (null != duplicateFileTable)
            {
                foreach (Row row in duplicateFileTable.Rows)
                {
                    Wix.CopyFile copyFile = (Wix.CopyFile)this.core.GetIndexedElement(row);

                    if (null != row[4])
                    {
                        if (null != this.core.GetIndexedElement("Directory", Convert.ToString(row[4])))
                        {
                            copyFile.DestinationDirectory = Convert.ToString(row[4]);
                        }
                        else
                        {
                            copyFile.DestinationProperty = Convert.ToString(row[4]);
                        }
                    }
                }
            }

            if (null != moveFileTable)
            {
                foreach (Row row in moveFileTable.Rows)
                {
                    Wix.CopyFile copyFile = (Wix.CopyFile)this.core.GetIndexedElement(row);

                    if (null != row[4])
                    {
                        if (null != this.core.GetIndexedElement("Directory", Convert.ToString(row[4])))
                        {
                            copyFile.SourceDirectory = Convert.ToString(row[4]);
                        }
                        else
                        {
                            copyFile.SourceProperty = Convert.ToString(row[4]);
                        }
                    }

                    if (null != this.core.GetIndexedElement("Directory", Convert.ToString(row[5])))
                    {
                        copyFile.DestinationDirectory = Convert.ToString(row[5]);
                    }
                    else
                    {
                        copyFile.DestinationProperty = Convert.ToString(row[5]);
                    }
                }
            }
        }
Beispiel #26
0
 /// <summary>
 /// Finalize decompilation.
 /// </summary>
 /// <param name="tables">The collection of all tables.</param>
 private void FinalizeDecompile(TableCollection tables)
 {
     if (OutputType.PatchCreation == this.outputType)
     {
         this.FinalizeFamilyFileRangesTable(tables);
     }
     else
     {
         this.FinalizeCheckBoxTable(tables);
         this.FinalizeComponentTable(tables);
         this.FinalizeDialogTable(tables);
         this.FinalizeDuplicateMoveFileTables(tables);
         this.FinalizeFeatureComponentsTable(tables);
         this.FinalizeFileTable(tables);
         this.FinalizeMIMETable(tables);
         this.FinalizeMsiLockPermissionsExTable(tables);
         this.FinalizeLockPermissionsTable(tables);
         this.FinalizeProgIdTable(tables);
         this.FinalizePropertyTable(tables);
         this.FinalizeRemoveFileTable(tables);
         this.FinalizeSearchTables(tables);
         this.FinalizeUpgradeTable(tables);
         this.FinalizeSequenceTables(tables);
         this.FinalizeVerbTable(tables);
     }
 }
Beispiel #27
0
        /// <summary>
        /// Finalize the FamilyFileRanges table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        private void FinalizeFamilyFileRangesTable(TableCollection tables)
        {
            Table externalFilesTable = tables["ExternalFiles"];
            Table familyFileRangesTable = tables["FamilyFileRanges"];
            Table targetFiles_OptionalDataTable = tables["TargetFiles_OptionalData"];

            Hashtable usedProtectRanges = new Hashtable();

            if (null != familyFileRangesTable)
            {
                foreach (Row row in familyFileRangesTable.Rows)
                {
                    Wix.ProtectRange protectRange = new Wix.ProtectRange();

                    if (null != row[2] && null != row[3])
                    {
                        string[] retainOffsets = (Convert.ToString(row[2])).Split(',');
                        string[] retainLengths = (Convert.ToString(row[3])).Split(',');

                        if (retainOffsets.Length == retainLengths.Length)
                        {
                            for (int i = 0; i < retainOffsets.Length; i++)
                            {
                                if (retainOffsets[i].StartsWith("0x", StringComparison.Ordinal))
                                {
                                    protectRange.Offset = Convert.ToInt32(retainOffsets[i].Substring(2), 16);
                                }
                                else
                                {
                                    protectRange.Offset = Convert.ToInt32(retainOffsets[i], CultureInfo.InvariantCulture);
                                }

                                if (retainLengths[i].StartsWith("0x", StringComparison.Ordinal))
                                {
                                    protectRange.Length = Convert.ToInt32(retainLengths[i].Substring(2), 16);
                                }
                                else
                                {
                                    protectRange.Length = Convert.ToInt32(retainLengths[i], CultureInfo.InvariantCulture);
                                }
                            }
                        }
                        else
                        {
                            // TODO: warn
                        }
                    }
                    else if (null != row[2] || null != row[3])
                    {
                        // TODO: warn about mismatch between columns
                    }

                    this.core.IndexElement(row, protectRange);
                }
            }

            if (null != externalFilesTable)
            {
                foreach (Row row in externalFilesTable.Rows)
                {
                    Wix.ExternalFile externalFile = (Wix.ExternalFile)this.core.GetIndexedElement(row);

                    Wix.ProtectRange protectRange = (Wix.ProtectRange)this.core.GetIndexedElement("FamilyFileRanges", Convert.ToString(row[0]), Convert.ToString(row[1]));
                    if (null != protectRange)
                    {
                        externalFile.AddChild(protectRange);
                        usedProtectRanges[protectRange] = null;
                    }
                }
            }

            if (null != targetFiles_OptionalDataTable)
            {
                Table targetImagesTable = tables["TargetImages"];
                Table upgradedImagesTable = tables["UpgradedImages"];

                Hashtable targetImageRows = new Hashtable();
                Hashtable upgradedImagesRows = new Hashtable();

                // index the TargetImages table
                if (null != targetImagesTable)
                {
                    foreach (Row row in targetImagesTable.Rows)
                    {
                        targetImageRows.Add(row[0], row);
                    }
                }

                // index the UpgradedImages table
                if (null != upgradedImagesTable)
                {
                    foreach (Row row in upgradedImagesTable.Rows)
                    {
                        upgradedImagesRows.Add(row[0], row);
                    }
                }

                foreach (Row row in targetFiles_OptionalDataTable.Rows)
                {
                    Wix.TargetFile targetFile = (Wix.TargetFile)this.patchTargetFiles[row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter)];

                    Row targetImageRow = (Row)targetImageRows[row[0]];
                    if (null == targetImageRow)
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, targetFiles_OptionalDataTable.Name, row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Target", Convert.ToString(row[0]), "TargetImages"));
                        continue;
                    }

                    Row upgradedImagesRow = (Row)upgradedImagesRows[targetImageRow[3]];
                    if (null == upgradedImagesRow)
                    {
                        this.core.OnMessage(WixWarnings.ExpectedForeignRow(targetImageRow.SourceLineNumbers, targetImageRow.Table.Name, targetImageRow.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Upgraded", Convert.ToString(row[3]), "UpgradedImages"));
                        continue;
                    }

                    Wix.ProtectRange protectRange = (Wix.ProtectRange)this.core.GetIndexedElement("FamilyFileRanges", Convert.ToString(upgradedImagesRow[4]), Convert.ToString(row[1]));
                    if (null != protectRange)
                    {
                        targetFile.AddChild(protectRange);
                        usedProtectRanges[protectRange] = null;
                    }
                }
            }

            if (null != familyFileRangesTable)
            {
                foreach (Row row in familyFileRangesTable.Rows)
                {
                    Wix.ProtectRange protectRange = (Wix.ProtectRange)this.core.GetIndexedElement(row);

                    if (!usedProtectRanges.Contains(protectRange))
                    {
                        Wix.ProtectFile protectFile = new Wix.ProtectFile();

                        protectFile.File = Convert.ToString(row[1]);

                        protectFile.AddChild(protectRange);

                        Wix.Family family = (Wix.Family)this.core.GetIndexedElement("ImageFamilies", Convert.ToString(row[0]));
                        if (null != family)
                        {
                            family.AddChild(protectFile);
                        }
                        else
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, familyFileRangesTable.Name, row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Family", Convert.ToString(row[0]), "ImageFamilies"));
                        }
                    }
                }
            }
        }
Beispiel #28
0
        /// <summary>
        /// Finalize the CheckBox table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Enumerates through all the Control rows, looking for controls of type "CheckBox" with
        /// a value in the Property column.  This is then possibly matched up with a CheckBox row
        /// to retrieve a CheckBoxValue.  There is no foreign key from the Control to CheckBox table.
        /// </remarks>
        private void FinalizeCheckBoxTable(TableCollection tables)
        {
            // if the user has requested to suppress the UI elements, we have nothing to do
            if (this.suppressUI)
            {
                return;
            }

            Table checkBoxTable = tables["CheckBox"];
            Table controlTable = tables["Control"];

            Hashtable checkBoxes = new Hashtable();
            Hashtable checkBoxProperties = new Hashtable();

            // index the CheckBox table
            if (null != checkBoxTable)
            {
                foreach (Row row in checkBoxTable.Rows)
                {
                    checkBoxes.Add(row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), row);
                    checkBoxProperties.Add(row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), false);
                }
            }

            // enumerate through the Control table, adding CheckBox values where appropriate
            if (null != controlTable)
            {
                foreach (Row row in controlTable.Rows)
                {
                    Wix.Control control = (Wix.Control)this.core.GetIndexedElement(row);

                    if ("CheckBox" == Convert.ToString(row[2]) && null != row[8])
                    {
                        Row checkBoxRow = (Row)checkBoxes[row[8]];

                        if (null == checkBoxRow)
                        {
                            this.core.OnMessage(WixWarnings.ExpectedForeignRow(row.SourceLineNumbers, "Control", row.GetPrimaryKey(DecompilerCore.PrimaryKeyDelimiter), "Property", Convert.ToString(row[8]), "CheckBox"));
                        }
                        else 
                        {
                            // if we've seen this property already, create a reference to it
                            if (Convert.ToBoolean(checkBoxProperties[row[8]]))
                            {
                                control.CheckBoxPropertyRef = Convert.ToString(row[8]);
                            }
                            else
                            {
                                control.Property = Convert.ToString(row[8]);
                                checkBoxProperties[row[8]] = true;
                            }
                            
                            if (null != checkBoxRow[1])
                            {
                                control.CheckBoxValue = Convert.ToString(checkBoxRow[1]);
                            }
                        }
                    }
                }
            }
        }
Beispiel #29
0
        /// <summary>
        /// Finalize the FeatureComponents table.
        /// </summary>
        /// <param name="tables">The collection of all tables.</param>
        /// <remarks>
        /// Since tables specifying references to the FeatureComponents table have references to
        /// the Feature and Component table separately, but not the FeatureComponents table specifically,
        /// the FeatureComponents table and primary features must be decompiled during finalization.
        /// </remarks>
        private void FinalizeFeatureComponentsTable(TableCollection tables)
        {
            Table classTable = tables["Class"];
            Table extensionTable = tables["Extension"];
            Table msiAssemblyTable = tables["MsiAssembly"];
            Table publishComponentTable = tables["PublishComponent"];
            Table shortcutTable = tables["Shortcut"];
            Table typeLibTable = tables["TypeLib"];

            if (null != classTable)
            {
                foreach (Row row in classTable.Rows)
                {
                    this.SetPrimaryFeature(row, 11, 2);
                }
            }

            if (null != extensionTable)
            {
                foreach (Row row in extensionTable.Rows)
                {
                    this.SetPrimaryFeature(row, 4, 1);
                }
            }

            if (null != msiAssemblyTable)
            {
                foreach (Row row in msiAssemblyTable.Rows)
                {
                    this.SetPrimaryFeature(row, 1, 0);
                }
            }

            if (null != publishComponentTable)
            {
                foreach (Row row in publishComponentTable.Rows)
                {
                    this.SetPrimaryFeature(row, 4, 2);
                }
            }

            if (null != shortcutTable)
            {
                foreach (Row row in shortcutTable.Rows)
                {
                    string target = Convert.ToString(row[4]);

                    if (!target.StartsWith("[", StringComparison.Ordinal) && !target.EndsWith("]", StringComparison.Ordinal))
                    {
                        this.SetPrimaryFeature(row, 4, 3);
                    }
                }
            }

            if (null != typeLibTable)
            {
                foreach (Row row in typeLibTable.Rows)
                {
                    this.SetPrimaryFeature(row, 6, 2);
                }
            }
        }