aboutsummaryrefslogtreecommitdiff
path: root/src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs
diff options
context:
space:
mode:
Diffstat (limited to 'src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs')
-rw-r--r--src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs112
1 files changed, 112 insertions, 0 deletions
diff --git a/src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs b/src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs
new file mode 100644
index 00000000..bac8633b
--- /dev/null
+++ b/src/WixToolset.Core.Burn/Bundles/AutomaticallySlipstreamPatchesCommand.cs
@@ -0,0 +1,112 @@
1// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information.
2
3namespace WixToolset.Core.Burn.Bundles
4{
5 using System;
6 using System.Collections.Generic;
7 using System.Diagnostics;
8 using System.Linq;
9 using WixToolset.Data;
10 using WixToolset.Data.Rows;
11
12 internal class AutomaticallySlipstreamPatchesCommand
13 {
14 public IEnumerable<PackageFacade> PackageFacades { private get; set; }
15
16 public Table WixBundlePatchTargetCodeTable { private get; set; }
17
18 public Table SlipstreamMspTable { private get; set; }
19
20 public void Execute()
21 {
22 List<WixBundleMsiPackageRow> msiPackages = new List<WixBundleMsiPackageRow>();
23 Dictionary<string, List<WixBundlePatchTargetCodeRow>> targetsProductCode = new Dictionary<string, List<WixBundlePatchTargetCodeRow>>();
24 Dictionary<string, List<WixBundlePatchTargetCodeRow>> targetsUpgradeCode = new Dictionary<string, List<WixBundlePatchTargetCodeRow>>();
25
26 foreach (PackageFacade facade in this.PackageFacades)
27 {
28 if (WixBundlePackageType.Msi == facade.Package.Type)
29 {
30 // Keep track of all MSI packages.
31 msiPackages.Add(facade.MsiPackage);
32 }
33 else if (WixBundlePackageType.Msp == facade.Package.Type && facade.MspPackage.Slipstream)
34 {
35 IEnumerable<WixBundlePatchTargetCodeRow> patchTargetCodeRows = this.WixBundlePatchTargetCodeTable.RowsAs<WixBundlePatchTargetCodeRow>().Where(r => r.MspPackageId == facade.Package.WixChainItemId);
36
37 // Index target ProductCodes and UpgradeCodes for slipstreamed MSPs.
38 foreach (WixBundlePatchTargetCodeRow row in patchTargetCodeRows)
39 {
40 if (row.TargetsProductCode)
41 {
42 List<WixBundlePatchTargetCodeRow> rows;
43 if (!targetsProductCode.TryGetValue(row.TargetCode, out rows))
44 {
45 rows = new List<WixBundlePatchTargetCodeRow>();
46 targetsProductCode.Add(row.TargetCode, rows);
47 }
48
49 rows.Add(row);
50 }
51 else if (row.TargetsUpgradeCode)
52 {
53 List<WixBundlePatchTargetCodeRow> rows;
54 if (!targetsUpgradeCode.TryGetValue(row.TargetCode, out rows))
55 {
56 rows = new List<WixBundlePatchTargetCodeRow>();
57 targetsUpgradeCode.Add(row.TargetCode, rows);
58 }
59 }
60 }
61 }
62 }
63
64 RowIndexedList<Row> slipstreamMspRows = new RowIndexedList<Row>(SlipstreamMspTable);
65
66 // Loop through the MSI and slipstream patches targeting it.
67 foreach (WixBundleMsiPackageRow msi in msiPackages)
68 {
69 List<WixBundlePatchTargetCodeRow> rows;
70 if (targetsProductCode.TryGetValue(msi.ProductCode, out rows))
71 {
72 foreach (WixBundlePatchTargetCodeRow row in rows)
73 {
74 Debug.Assert(row.TargetsProductCode);
75 Debug.Assert(!row.TargetsUpgradeCode);
76
77 Row slipstreamMspRow = SlipstreamMspTable.CreateRow(row.SourceLineNumbers, false);
78 slipstreamMspRow[0] = msi.ChainPackageId;
79 slipstreamMspRow[1] = row.MspPackageId;
80
81 if (slipstreamMspRows.TryAdd(slipstreamMspRow))
82 {
83 SlipstreamMspTable.Rows.Add(slipstreamMspRow);
84 }
85 }
86
87 rows = null;
88 }
89
90 if (!String.IsNullOrEmpty(msi.UpgradeCode) && targetsUpgradeCode.TryGetValue(msi.UpgradeCode, out rows))
91 {
92 foreach (WixBundlePatchTargetCodeRow row in rows)
93 {
94 Debug.Assert(!row.TargetsProductCode);
95 Debug.Assert(row.TargetsUpgradeCode);
96
97 Row slipstreamMspRow = SlipstreamMspTable.CreateRow(row.SourceLineNumbers, false);
98 slipstreamMspRow[0] = msi.ChainPackageId;
99 slipstreamMspRow[1] = row.MspPackageId;
100
101 if (slipstreamMspRows.TryAdd(slipstreamMspRow))
102 {
103 SlipstreamMspTable.Rows.Add(slipstreamMspRow);
104 }
105 }
106
107 rows = null;
108 }
109 }
110 }
111 }
112}