示例#1
0
        /// <summary>
        /// Resolves all the simple references in a section.
        /// </summary>
        /// <param name="outputType">Parent output type that will get the resolved section collection.</param>
        /// <param name="allSymbols">Collection of all symbols from loaded intermediates.</param>
        /// <param name="referencedSymbols">Collection populated during resolution of all symbols referenced during linking.</param>
        /// <param name="unresolvedReferences">Collection populated during resolution of all references that are left unresolved.</param>
        /// <param name="messageHandler">Message handler to report any duplicate symbols that may be tripped across.</param>
        /// <returns>The resolved sections.</returns>
        internal SectionCollection ResolveReferences(
            OutputType outputType,
            SymbolCollection allSymbols,
            StringCollection referencedSymbols,
            ArrayList unresolvedReferences,
            IMessageHandler messageHandler)
        {
            SectionCollection sections = new SectionCollection();

            RecursivelyResolveReferences(this, outputType, allSymbols, sections, referencedSymbols, unresolvedReferences, messageHandler);
            return(sections);
        }
示例#2
0
        /// <summary>
        /// Finds the entry section and loads the symbols from an array of intermediates.
        /// </summary>
        /// <param name="allowIdenticalRows">Flag specifying whether identical rows are allowed or not.</param>
        /// <param name="messageHandler">Message handler object to route all errors through.</param>
        /// <param name="expectedOutputType">Expected entry output type, based on output file extension provided to the linker.</param>
        /// <param name="entrySection">Located entry section.</param>
        /// <param name="allSymbols">Collection of symbols loaded.</param>
        internal void FindEntrySectionAndLoadSymbols(
            bool allowIdenticalRows,
            IMessageHandler messageHandler,
            OutputType expectedOutputType,
            out Section entrySection,
            out SymbolCollection allSymbols)
        {
            entrySection = null;
            allSymbols   = new SymbolCollection();

            string      outputExtension = Output.GetExtension(expectedOutputType);
            SectionType expectedEntrySectionType;

            try
            {
                expectedEntrySectionType = (SectionType)Enum.Parse(typeof(SectionType), expectedOutputType.ToString());
            }
            catch (ArgumentException)
            {
                expectedEntrySectionType = SectionType.Unknown;
            }

            foreach (Section section in this.collection.Keys)
            {
                if (SectionType.Product == section.Type || SectionType.Module == section.Type || SectionType.PatchCreation == section.Type || SectionType.Patch == section.Type || SectionType.Bundle == section.Type)
                {
                    if (SectionType.Unknown != expectedEntrySectionType && section.Type != expectedEntrySectionType)
                    {
                        messageHandler.OnMessage(WixWarnings.UnexpectedEntrySection(section.SourceLineNumbers, section.Type.ToString(), expectedEntrySectionType.ToString(), outputExtension));
                    }

                    if (null == entrySection)
                    {
                        entrySection = section;
                    }
                    else
                    {
                        messageHandler.OnMessage(WixErrors.MultipleEntrySections(entrySection.SourceLineNumbers, entrySection.Id, section.Id));
                        messageHandler.OnMessage(WixErrors.MultipleEntrySections2(section.SourceLineNumbers));
                    }
                }

                foreach (Symbol symbol in section.GetSymbols(messageHandler))
                {
                    try
                    {
                        Symbol existingSymbol = allSymbols[symbol.Name];
                        if (null == existingSymbol)
                        {
                            allSymbols.Add(symbol);
                        }
                        else if (allowIdenticalRows && existingSymbol.Row.IsIdentical(symbol.Row))
                        {
                            messageHandler.OnMessage(WixWarnings.IdenticalRowWarning(symbol.Row.SourceLineNumbers, existingSymbol.Name));
                            messageHandler.OnMessage(WixWarnings.IdenticalRowWarning2(existingSymbol.Row.SourceLineNumbers));
                        }
                        else
                        {
                            allSymbols.AddDuplicate(symbol);
                        }
                    }
                    catch (DuplicateSymbolsException)
                    {
                        // if there is already a duplicate symbol, just
                        // another to the list, don't bother trying to
                        // see if there are any identical symbols
                        allSymbols.AddDuplicate(symbol);
                    }
                }
            }
        }
示例#3
0
        /// <summary>
        /// Recursive helper function to resolve all references of passed in section.
        /// </summary>
        /// <param name="section">Section with references to resolve.</param>
        /// <param name="outputType">Parent output type that will get the resolved section collection.</param>
        /// <param name="allSymbols">All symbols that can be used to resolve section's references.</param>
        /// <param name="sections">Collection to add sections to during processing.</param>
        /// <param name="referencedSymbols">Collection populated during resolution of all symbols referenced during linking.</param>
        /// <param name="unresolvedReferences">Collection populated during resolution of all references that are left unresolved.</param>
        /// <param name="messageHandler">Message handler to report any duplicate symbols that may be tripped across.</param>
        /// <remarks>Note: recursive function.</remarks>
        private static void RecursivelyResolveReferences(
            Section section,
            OutputType outputType,
            SymbolCollection allSymbols,
            SectionCollection sections,
            StringCollection referencedSymbols,
            ArrayList unresolvedReferences,
            IMessageHandler messageHandler)
        {
            // if we already have this section bail
            if (sections.Contains(section))
            {
                return;
            }

            // add the passed in section to the collection of sections
            sections.Add(section);

            // process all of the references contained in this section using the collection of
            // symbols provided.  Then recursively call this method to process the
            // located symbol's section.  All in all this is a very simple depth-first
            // search of the references per-section
            Table wixSimpleReferenceTable = section.Tables["WixSimpleReference"];

            if (null != wixSimpleReferenceTable)
            {
                foreach (WixSimpleReferenceRow wixSimpleReferenceRow in wixSimpleReferenceTable.Rows)
                {
                    // If we're building a Merge Module, ignore all references to the Media table
                    // because Merge Modules don't have Media tables.
                    if (OutputType.Module == outputType && "Media" == wixSimpleReferenceRow.TableName)
                    {
                        continue;
                    }

                    if ("WixAction" == wixSimpleReferenceRow.TableName)
                    {
                        Symbol[] symbols = allSymbols.GetSymbolsForSimpleReference(wixSimpleReferenceRow);
                        if (0 == symbols.Length)
                        {
                            if (null != unresolvedReferences)
                            {
                                unresolvedReferences.Add(new SimpleReferenceSection(section, wixSimpleReferenceRow));
                            }
                        }
                        else
                        {
                            foreach (Symbol symbol in symbols)
                            {
                                if (null != symbol.Section)
                                {
                                    // components are indexed in ResolveComplexReferences
                                    if (null != referencedSymbols && null != symbol.Row.TableDefinition.Name && "Component" != symbol.Row.TableDefinition.Name && !referencedSymbols.Contains(symbol.Name))
                                    {
                                        referencedSymbols.Add(symbol.Name);
                                    }

                                    RecursivelyResolveReferences(symbol.Section, outputType, allSymbols, sections, referencedSymbols, unresolvedReferences, messageHandler);
                                }
                            }
                        }
                    }
                    else
                    {
                        Symbol symbol = allSymbols.GetSymbolForSimpleReference(wixSimpleReferenceRow, messageHandler);
                        if (null == symbol)
                        {
                            if (null != unresolvedReferences)
                            {
                                unresolvedReferences.Add(new SimpleReferenceSection(section, wixSimpleReferenceRow));
                            }
                        }
                        else
                        {
                            // components are indexed in ResolveComplexReferences
                            if (null != referencedSymbols && null != symbol.Row.TableDefinition.Name && "Component" != symbol.Row.TableDefinition.Name && !referencedSymbols.Contains(symbol.Name))
                            {
                                referencedSymbols.Add(symbol.Name);
                            }

                            RecursivelyResolveReferences(symbol.Section, outputType, allSymbols, sections, referencedSymbols, unresolvedReferences, messageHandler);
                        }
                    }
                }
            }
        }