1    	using System;
2    	using System.Collections.Generic;
3    	using System.Linq;
4    	using System.Text;
5    	using SysProcess = System.Diagnostics.Process;
6    	using System.Diagnostics;
7    	using System.Xml.Linq;
8    	using System.IO;
9    	using Intel.Tools.DeviceManager;
10   	
11   	namespace Intel.Deployment.ChipsetWiX
12   	{
13   	    internal class DisableTbtDeviceHelper
14   	    {
15   	        private object _processLock = new object();
16   	        private List<string> _output = new List<string>();
17   	        private SysProcess _schedulerProcess;
18   	        private ProcessStartInfo _schedulerProcStartInfo;
19   	        private string _timeout = "3";
20   	        private string _devConName = "devcon";
21   	        private string _schedulerName = "schtasks";
22   	        private string[] _TbtIds =
23   	            {
24   	                    /* Alpine Ridge DP B-step DSL6540 */
25   	                    "1578",
26   	                    "1577",
27   	                    "15B6",
28   	                    /*Alpine Ridge SP B-step DSL6340 */
29   	                    "1576",
30   	                    "1575",
31   	                    "15B5",
32   	                    /* Alpine Ridge DP C-step JHL6540 */
33   	                    "15D3",
34   	                    "15D2",
35   	                    "15D4",
36   	                    /* Alpine Ridge SP C-step JHL6340 */
37   	                    "15DA",
38   	                    "15D9",
39   	                    "15DB",
40   	                    /* Alpine Ridge LP JHL6240 */
41   	                    "15C0",
42   	                    "15BF",
43   	                    "15C1",
44   	                    /* Titan Ridge DP JHL7540 */
45   	                    "15EA",
46   	                    "15EB",
47   	                    "15EC",
48   	                    /* Titan Ridge SP JHL7340 */
49   	                    "15E7",
50   	                    "15E8",
51   	                    "15E9",
52   	                    /* Titan Ridge DD JHL7440 */
53   	                    "15EF",
54   	                    "15F0",
55   	                };
56   	
57   	        public DisableTbtDeviceHelper(string devConPath, string timeout)
58   	        {
59   	            if (!File.Exists(devConPath))
60   	            {
61   	                throw new FileNotFoundException("A valid DevCon path is required", devConPath);
62   	            }
63   	            _devConName = devConPath;
64   	            if (!string.IsNullOrEmpty(timeout))
65   	            {
66   	                _timeout = timeout;
67   	            }
68   	
69   	            _schedulerProcStartInfo = new ProcessStartInfo()
70   	            {
71   	                RedirectStandardOutput = true,
72   	                RedirectStandardError = true,
73   	                UseShellExecute = false,
74   	                CreateNoWindow = true,
75   	                FileName = _schedulerName,
76   	            };
77   	            _schedulerProcess = new SysProcess();
78   	            _schedulerProcess.StartInfo = _schedulerProcStartInfo;
79   	            _schedulerProcess.OutputDataReceived += addOutput;
80   	            _schedulerProcess.ErrorDataReceived += addOutput;
81   	        }
82   	
83   	        public void DisableTbt(DeviceList deviceList)
84   	        {
85   	            foreach (var devId in _TbtIds)
86   	            {
87   	                try
88   	                {
89   	                    var rootDevs = GetTbtRootDevice(deviceList, devId);
90   	                    if (rootDevs.Any())
91   	                    {
92   	                        var device = rootDevs.Single();
93   	                        Log.WriteLine($"Found root device {device.FriendlyName} - {device.HardwareIDs.FirstOrDefault()?.DeviceID ?? "NA"}");
94   	                        if (device.IsEnabled)
95   	                        {
96   	                            Log.WriteLine($"  Device is enabled - disabling");
97   	                            if (DisableDevice(device))
98   	                            {
99   	                                var deviceString = GetDeviceString(device);
100  	                                Log.WriteLine($"  Device is disabled - {deviceString}");
101  	                                DefferedEnableTbt(deviceString, _devConName, _timeout);
102  	                            }
103  	                        }
104  	                    }
105  	                }
106  	                catch (Exception ex)
107  	                {
108  	                    Log.WriteException(ex);
109  	                }
110  	            }
111  	        }
112  	
113  	        private string GetDeviceString(Device id)
114  	        {
115  	            return id.DeviceInstancePath;
116  	        }
117  	        
118  	        private int RunProcess(SysProcess process, string argument, List<string> output)
119  	        {
120  	            lock (_processLock)
121  	            {
122  	                _output.Clear();
123  	                process.Start();
124  	                process.BeginOutputReadLine();
125  	                process.BeginErrorReadLine();
126  	                process.WaitForExit();
127  	                process.CancelOutputRead();
128  	                process.CancelErrorRead();
129  	                output?.AddRange(_output);
130  	                return process.ExitCode;
131  	            }
132  	        }
133  	
134  	        private int RunSchedulerProcess(string argument, List<string> output)
135  	        {
136  	            _schedulerProcStartInfo.Arguments = argument;
137  	            return RunProcess(_schedulerProcess, argument, output);
138  	        }
139  	
140  	        private void addOutput(object sender, DataReceivedEventArgs e)
141  	        {
142  	            var sysProc = sender as SysProcess;
143  	            if (sysProc == null)
144  	            {
145  	                Log.WriteLine("Process Output Redirect - [sender is not SysProcess ??]: {0}", e.Data);
146  	                return;
147  	            }
148  	
149  	            if (!_string.IsNullOrWhiteSpace(e.Data))
150  	            {
151  	                _output.Add(e.Data);
152  	            }
153  	        }
154  	
155  	
156  	        private List<Device> GetTbtRootDevice(DeviceList deviceList, string devId)
157  	        {
158  	            List<Device> tbtRoot = new List<Device>();
159  	            var tbtDevicesOnSystem = deviceList.Where(x => x.HardwareIDs.Any(hwid => hwid.DeviceID.ToLower().Equals(devId.ToLower())));
160  	            foreach (var device in tbtDevicesOnSystem)
161  	            {
162  	                var parentDeviceId = device.GetParentHardwareIds(deviceList).First().DeviceID.ToLower();
163  	                if(!_TbtIds.
164  	                    Select(tbtDev => tbtDev.ToLower())
165  	                    .Any(tbtDevId => tbtDevId == parentDeviceId))
166  	                {
167  	                    tbtRoot.Add(device);
168  	                }
169  	            }
170  	            return tbtRoot;
171  	        }
172  	
173  	        private bool IsDeviceEnabled(Device device)
174  	        {
175  	            return device.IsEnabled;
176  	        }
177  	
178  	        private bool DisableDevice(Device device)
179  	        {
180  	            try
181  	            {
182  	                device.DisableDevice();
183  	                return true;
184  	            }
185  	            catch (Exception)
186  	            {
187  	                return false;
188  	            }
189  	        }
190  	
191  	        private void DefferedEnableTbt(string deviceString, string devconPath, string timeout)
192  	        {
193  	            try
194  	            {
195  	                Log.WriteLine($"Scheduling task to enable on start for {deviceString}");
196  	                string taskName = $"Intel\\Enable{deviceString.Replace("*", "").Replace('\\', '_')}";
197  	                var xmlDocument = XDocument.Parse(Resources.Intel_EnableTbt);
198  	                foreach (var node in xmlDocument.Descendants(xmlDocument.Root.Name.Namespace + "Arguments"))
199  	                {
200  	                    if (node.Value.Equals("ENABLE_TBT_ARG"))
201  	                    {
202  	                        node.Value = $"enable \"@{deviceString}\"";
203  	                    }
204  	                    else if (node.Value.Equals("DELETE_TASK_ARG"))
205  	                    {
206  	                        node.Value = $"/delete /f /tn {taskName}";
207  	                    }
208  	                    else if (node.Value.Equals("ENABLE_TBT_TIMEOUT"))
209  	                    {
210  	                        node.Value = timeout;
211  	                    }
212  	                }
213  	                foreach (var node in xmlDocument.Descendants(xmlDocument.Root.Name.Namespace + "Command"))
214  	                {
215  	                    if (node.Value.Equals("ENABLE_TBT_DEVCON"))
216  	                    {
217  	                        node.Value = devconPath;
218  	                    }
219  	                }
220  	                
(1) Event Sigma main event: The application uses the method `System.IO.Path.GetTempFileName` to create a temporary file. Using this function may lead to leak of file contents or injection of malicious data into the file through a race condition attack.
(2) Event remediation: Use the `System.IO.Path.GetRandomFileName` instead of `System.IO.Path.GetTempFileName` to create temporary files.
221  	                var tempXmlTaskFile = Path.GetTempFileName();
222  	                xmlDocument.Save(tempXmlTaskFile);
223  	                var output = new List<string>();
224  	                if (0 != RunSchedulerProcess($"/create /xml \"{tempXmlTaskFile}\" /tn \"{taskName}\" /f", output))
225  	                {
226  	                    foreach (var line in output)
227  	                    {
228  	                        Log.WriteLine(line);
229  	                    }
230  	                }
231  	                Log.WriteLine($"  Task scheduled");
232  	            }
233  	            catch (Exception ex)
234  	            {
235  	                Log.WriteException(ex);
236  	            }
237  	        }
238  	    }
239  	}
240