From 46a3d3d779f187b4ad39656e0562edae353c92a6 Mon Sep 17 00:00:00 2001 From: Whisperity Date: Fri, 3 Oct 2014 20:06:50 +0200 Subject: [PATCH] Implemented whitelist override for user's request Whitelist overrides will disable the ability to alter addons. But this fixes the errors pointed out by users that the program refuses to load addons not conforming the whitelist. Also reverts the changes of previous commit 3dae81006e. Contains a HEAVY hackfix! --- SharpGMad/Main.cs | 71 +++++++---- SharpGMad/Program.cs | 6 + SharpGMad/Properties/AssemblyInfo.cs | 4 +- SharpGMad/RealtimeAddon.cs | 10 +- SharpGMad/RealtimeCommandline.cs | 169 ++++++++++++++++++++++++++- SharpGMad/Whitelist.cs | 48 ++++---- 6 files changed, 255 insertions(+), 53 deletions(-) diff --git a/SharpGMad/Main.cs b/SharpGMad/Main.cs index cac2521..618e3ef 100644 --- a/SharpGMad/Main.cs +++ b/SharpGMad/Main.cs @@ -18,6 +18,7 @@ private Main() { InitializeComponent(); UnloadAddon(); + tsbCreateAddon.Enabled = !Program.WhitelistOverridden; } public Main(string[] args) @@ -95,8 +96,30 @@ private void LoadAddon(string path) } catch (WhitelistException e) { - MessageBox.Show(e.Message, "Addon is corrupted", MessageBoxButtons.OK, MessageBoxIcon.Stop); - return; + if (!Program.WhitelistOverridden) + { + DialogResult ovrride = MessageBox.Show("This addon is against the GMA whitelist rules defined by garry!\n" + + e.Message + "\n\nFor datamining purposes, it is still possible to open this addon, HOWEVER " + + "opening this addon is an illegal operation and SharpGMad will prevent further modifications.\n\n" + + "Do you want to enable forced opening of addons by overriding the whitelist?", + "Addon is corrupted", MessageBoxButtons.YesNo, MessageBoxIcon.Question); + + if (ovrride == DialogResult.No) + { + MessageBox.Show(e.Message, "Addon is corrupted", MessageBoxButtons.OK, MessageBoxIcon.Stop); + return; + } + else if (ovrride == DialogResult.Yes) + { + Program.WhitelistOverridden = true; + tsbCreateAddon.Enabled = !Program.WhitelistOverridden; + MessageBox.Show("Restrictions disabled.\nPlease browse for the addon to open it again.", + "Addon is corrupted", MessageBoxButtons.OK, MessageBoxIcon.Information); + this.Text = "! - SharpGMad"; + UpdateStatus("Restrictions disabled by user's request."); + return; + } + } } catch (ArgumentException e) { @@ -123,8 +146,8 @@ private void LoadAddon(string path) UpdateModified(); UpdateStatus("Loaded the addon" + (AddonHandle.CanWrite ? null : " (read-only mode)")); - tsbAddFile.Enabled = AddonHandle.CanWrite; - tsbUpdateMetadata.Enabled = AddonHandle.CanWrite; + tsbAddFile.Enabled = AddonHandle.CanWrite && !Program.WhitelistOverridden; + tsbUpdateMetadata.Enabled = AddonHandle.CanWrite && !Program.WhitelistOverridden; } } @@ -144,10 +167,11 @@ private void UpdateModified() } else { - this.Text = Path.GetFileName(AddonHandle.AddonPath) + (AddonHandle.CanWrite ? null : " (read-only)") + + this.Text = Path.GetFileName(AddonHandle.AddonPath) + (Program.WhitelistOverridden ? "!" : null) + + (AddonHandle.CanWrite ? null : " (read-only)") + (AddonHandle.Modified ? "*" : null) + " - SharpGMad"; - tsbSaveAddon.Enabled = AddonHandle.CanWrite && AddonHandle.Modified; + tsbSaveAddon.Enabled = AddonHandle.CanWrite && AddonHandle.Modified && (!Program.WhitelistOverridden); } } @@ -221,7 +245,8 @@ private void UpdateFileList() foreColor = System.Drawing.SystemColors.ControlText; tsslStatus.ForeColor = foreColor; - tsslStatus.Text = "[" + DateTime.Now.ToString() + "] " + text; + tsslStatus.Text = (Program.WhitelistOverridden ? "!Cannot modify addons because the whitelist had been overridden! " : null) + + "[" + DateTime.Now.ToString() + "] " + text; } /// @@ -279,7 +304,7 @@ private void UnloadAddon() lstFiles.Items.Clear(); lstFiles.Groups.Clear(); - this.Text = "SharpGMad"; + this.Text = "SharpGMad" + (Program.WhitelistOverridden ? "!" : null); tsbSaveAddon.Enabled = false; if (AddonHandle != null) @@ -323,7 +348,7 @@ private void tsmiLegacyExtract_Click(object sender, EventArgs e) private void tsbAddFile_Click(object sender, EventArgs e) { - if (AddonHandle == null) + if (AddonHandle == null || Program.WhitelistOverridden) return; // If there is no value for file filtering, load a file list @@ -390,7 +415,7 @@ private void lstFiles_SelectedIndexChanged(object sender, EventArgs e) { // Allow remove, export and execution tsmFileRemove.Visible = true; - tsmFileRemove.Enabled = AddonHandle.CanWrite; + tsmFileRemove.Enabled = AddonHandle.CanWrite && !Program.WhitelistOverridden; tsmFileExtract.Enabled = true; tsmFileExtract.Visible = true; @@ -404,7 +429,7 @@ private void lstFiles_SelectedIndexChanged(object sender, EventArgs e) if (isExported.Count() == 0) { // Export is the file is not exported - tsmFileExportTo.Enabled = AddonHandle.CanWrite; + tsmFileExportTo.Enabled = AddonHandle.CanWrite && !Program.WhitelistOverridden; tsmFilePull.Enabled = false; tsmFileDropExport.Enabled = false; } @@ -412,7 +437,7 @@ private void lstFiles_SelectedIndexChanged(object sender, EventArgs e) { // Pull (applicable if the file is changed) and drop tsmFileExportTo.Enabled = false; - tsmFilePull.Enabled = isExported.First().Modified && AddonHandle.CanWrite; + tsmFilePull.Enabled = isExported.First().Modified && AddonHandle.CanWrite && !Program.WhitelistOverridden; tsmFileDropExport.Enabled = true; } @@ -426,7 +451,7 @@ private void lstFiles_SelectedIndexChanged(object sender, EventArgs e) else if (((System.Windows.Forms.ListView)sender).SelectedItems.Count > 1) { // Multiple files support remove, extract, but no exec and export-related stuff - tsmFileRemove.Enabled = true; + tsmFileRemove.Enabled = !Program.WhitelistOverridden; tsmFileRemove.Visible = true; tsmFileExtract.Enabled = true; @@ -501,7 +526,7 @@ private void lstFiles_KeyDown(object sender, KeyEventArgs e) private void tsmFileRemove_Click(object sender, EventArgs e) { - if (!AddonHandle.CanWrite) + if (!AddonHandle.CanWrite || Program.WhitelistOverridden) return; if (lstFiles.SelectedItems.Count == 1) @@ -599,7 +624,7 @@ private void tsmFileRemove_Click(object sender, EventArgs e) private void tsbUpdateMetadata_Click(object sender, EventArgs e) { - if (!AddonHandle.CanWrite) + if (!AddonHandle.CanWrite || Program.WhitelistOverridden) return; // Use a toggle mechanism to enable and disable the changing of metadata @@ -708,7 +733,7 @@ private void tsbDiscardMetadataChanges_Click(object sender, EventArgs e) private void tsbSaveAddon_Click(object sender, EventArgs e) { - if (!AddonHandle.CanWrite) + if (!AddonHandle.CanWrite || Program.WhitelistOverridden) return; if (!tsbUpdateMetadata.Checked) @@ -745,7 +770,7 @@ private void tsbSaveAddon_Click(object sender, EventArgs e) private void Main_FormClosing(object sender, FormClosingEventArgs e) { - if (AddonHandle is RealtimeAddon && AddonHandle.Modified) + if (AddonHandle is RealtimeAddon && AddonHandle.Modified && !Program.WhitelistOverridden) { DialogResult yesClose = MessageBox.Show("Save the addon before quitting?", Path.GetFileName(AddonHandle.AddonPath), MessageBoxButtons.YesNoCancel, MessageBoxIcon.Question); @@ -774,8 +799,14 @@ private void Main_FormClosing(object sender, FormClosingEventArgs e) private void tsbCreateAddon_Click(object sender, EventArgs e) { + if (Program.WhitelistOverridden) + { + tsbCreateAddon.Enabled = !Program.WhitelistOverridden; + return; + } + DialogResult dropChanges = new DialogResult(); - if (AddonHandle is RealtimeAddon && AddonHandle.Modified) + if (AddonHandle is RealtimeAddon && AddonHandle.Modified && !Program.WhitelistOverridden) { dropChanges = MessageBox.Show("Open an another addon without saving the current one?\nYou'll lose the changes.", "Addon already open", MessageBoxButtons.YesNo, MessageBoxIcon.Question); @@ -823,7 +854,7 @@ private void tsbCreateAddon_Click(object sender, EventArgs e) private void tsmFileExportTo_Click(object sender, EventArgs e) { - if (!AddonHandle.CanWrite) + if (!AddonHandle.CanWrite || Program.WhitelistOverridden) return; if (lstFiles.FocusedItem != null) @@ -1046,7 +1077,7 @@ private void tsbPullAll_Click(object sender, EventArgs e) /// The exported path is known automatically. private void PullFile(string filename) { - if (!AddonHandle.CanWrite) + if (!AddonHandle.CanWrite || Program.WhitelistOverridden) return; try diff --git a/SharpGMad/Program.cs b/SharpGMad/Program.cs index 565a305..bd7a7f2 100644 --- a/SharpGMad/Program.cs +++ b/SharpGMad/Program.cs @@ -11,6 +11,12 @@ namespace SharpGMad /// class Program { + // HACK: This has been just tied into the system to fix opening of illegal GMAs + /// + /// Indicates whether the whitelist was overridden by an illegal action. + /// + public static bool WhitelistOverridden = false; + #if WINDOWS /// /// External method to find a pointer for an attached console window. diff --git a/SharpGMad/Properties/AssemblyInfo.cs b/SharpGMad/Properties/AssemblyInfo.cs index 758f7e5..6eb6f95 100644 --- a/SharpGMad/Properties/AssemblyInfo.cs +++ b/SharpGMad/Properties/AssemblyInfo.cs @@ -32,5 +32,5 @@ // You can specify all the values or you can default the Build and Revision Numbers // by using the '*' as shown below: // [assembly: AssemblyVersion("1.0.*")] -[assembly: AssemblyVersion("1.1.2.1")] -[assembly: AssemblyFileVersion("1.1.2.1")] \ No newline at end of file +[assembly: AssemblyVersion("1.1.2.3")] +[assembly: AssemblyFileVersion("1.1.2.3")] \ No newline at end of file diff --git a/SharpGMad/RealtimeAddon.cs b/SharpGMad/RealtimeAddon.cs index db2060b..060ace5 100644 --- a/SharpGMad/RealtimeAddon.cs +++ b/SharpGMad/RealtimeAddon.cs @@ -135,7 +135,7 @@ public static RealtimeAddon Load(string filename, bool readOnly = false) throw new FileNotFoundException("The specified file " + filename + " does not exist."); } - FileStream fs; + FileStream fs = null; try { if (!readOnly) @@ -145,6 +145,9 @@ public static RealtimeAddon Load(string filename, bool readOnly = false) } catch (IOException) { + if (fs != null) + fs.Dispose(); + throw; } @@ -155,10 +158,12 @@ public static RealtimeAddon Load(string filename, bool readOnly = false) } catch (IOException) { + fs.Dispose(); throw; } catch (ReaderException) { + fs.Dispose(); throw; } @@ -169,14 +174,17 @@ public static RealtimeAddon Load(string filename, bool readOnly = false) } catch (ArgumentException) { + fs.Dispose(); throw; } catch (WhitelistException) { + fs.Dispose(); throw; } catch (IgnoredException) { + fs.Dispose(); throw; } diff --git a/SharpGMad/RealtimeCommandline.cs b/SharpGMad/RealtimeCommandline.cs index 776a0cd..49c191f 100644 --- a/SharpGMad/RealtimeCommandline.cs +++ b/SharpGMad/RealtimeCommandline.cs @@ -53,7 +53,8 @@ public static int Main(string[] args) } else if (AddonHandle is RealtimeAddon) { - Console.Write(Path.GetFileName(AddonHandle.AddonPath) + (AddonHandle.CanWrite ? null : " (read-only)") + + Console.Write(Path.GetFileName(AddonHandle.AddonPath) + (Program.WhitelistOverridden ? "!" : null) + + (AddonHandle.CanWrite ? null : " (read-only)") + (AddonHandle.Modified ? "*" : null) + (AddonHandle.Pullable ? "!" : null)); #if WINDOWS Console.Write("> "); @@ -590,24 +591,25 @@ public static int Main(string[] args) if (AddonHandle == null) { Console.WriteLine("load Loads addon into the memory"); - Console.WriteLine("new Create a new, empty addon named "); + if (!Program.WhitelistOverridden) + Console.WriteLine("new Create a new, empty addon named "); } if (AddonHandle is RealtimeAddon) { - if (AddonHandle.CanWrite) + if (AddonHandle.CanWrite && !Program.WhitelistOverridden) { Console.WriteLine("add Adds to the archive"); Console.WriteLine("addfolder Adds all files from to the archive"); } Console.WriteLine("list Lists the files in the memory"); - if (AddonHandle.CanWrite) + if (AddonHandle.CanWrite && !Program.WhitelistOverridden) { Console.WriteLine("remove Removes from the archive"); } Console.WriteLine("extract [path] Extract (to [path] if specified)"); Console.WriteLine("mget [f2...] Extract all specified files to "); - if (AddonHandle.CanWrite) + if (AddonHandle.CanWrite && !Program.WhitelistOverridden) { Console.WriteLine("export View the list of exported files"); Console.WriteLine("export [path] Export for editing (to [path] if specified)"); @@ -616,7 +618,7 @@ public static int Main(string[] args) Console.WriteLine("drop Drops the export for "); } Console.WriteLine("get Prints the value of metadata "); - if (AddonHandle.CanWrite) + if (AddonHandle.CanWrite && !Program.WhitelistOverridden) { Console.WriteLine("set [value] Sets metadata to the specified [value]"); Console.WriteLine("push Writes the changes to the disk"); @@ -663,6 +665,13 @@ public static int Main(string[] args) } } + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + } + break; case "exit": if (AddonHandle is RealtimeAddon) @@ -694,6 +703,14 @@ public static int Main(string[] args) /// The filename where the addon should be saved to. static void NewAddon(string filename) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle is RealtimeAddon) { Console.ForegroundColor = ConsoleColor.Red; @@ -745,6 +762,14 @@ static void NewAddon(string filename) /// Optional. The new title the addon should have. private static void SetTitle(string title = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -771,6 +796,14 @@ private static void SetTitle(string title = null) /// Optional. The new description the addon should have. private static void SetDescription(string description = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -797,6 +830,14 @@ private static void SetDescription(string description = null) /// Optional. The new author the addon should have. private static void SetAuthor(string author = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -825,6 +866,14 @@ private static void SetAuthor(string author = null) /// Optional. The new type the addon should have. private static void SetType(string type = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -873,6 +922,14 @@ private static void SetType(string type = null) /// Optional. The new tags the addon should have. private static void SetTags(string[] tagsInput = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -1003,6 +1060,50 @@ private static void LoadAddon(string filename) { AddonHandle = RealtimeAddon.Load(filename, !FileExtensions.CanWrite(filename)); } + catch (WhitelistException e) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("There was a problem opening the file."); + Console.ResetColor(); + + Console.ForegroundColor = ConsoleColor.Yellow; + Console.Write("This addon is against the GMA whitelist rules defined by garry!\n" + + e.Message + "\n\nFor datamining purposes, it is still possible to open this addon, HOWEVER " + + "opening this addon is an illegal operation and SharpGMad will prevent further modifications."); + Console.ResetColor(); + + bool decided = false; + string decision; + while (!decided) + { + Console.Write("\nDo you want to enable forced opening of addons by overriding the whitelist? (y/n) "); + decision = Console.ReadLine(); + if (decision == "n" || decision == "N") + { + Console.ForegroundColor = ConsoleColor.Green; + Console.WriteLine("The addon will not be opened."); + Console.ResetColor(); + decided = true; + return; + } + else if (decision == "y" || decision == "Y") + { + Program.WhitelistOverridden = true; + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("All security safeguards and restrictions HAD BEEN DISABLED."); + Console.ResetColor(); + Console.WriteLine("Please type the command again to load the addon."); + decided = true; + CloseAddon(); + return; + } + else + { + decided = false; + Console.WriteLine("Invalid input. Please write y for yes or n for no."); + } + } + } catch (Exception e) { Console.ForegroundColor = ConsoleColor.Red; @@ -1032,6 +1133,14 @@ private static void LoadAddon(string filename) /// The path of the file to be added. private static void AddFile(string filename) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; @@ -1099,6 +1208,14 @@ private static void AddFile(string filename) /// The folder containing the files to be added. private static void AddFolder(string folder) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (!AddonHandle.CanWrite) { Console.ForegroundColor = ConsoleColor.Red; @@ -1147,6 +1264,14 @@ private static void ListFiles() /// The path of the file to be removed. private static void RemoveFile(string filename) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; @@ -1233,6 +1358,14 @@ private static void ExtractFile(string filename, string extractPath = null) /// If omitted, the file will be exported to the current working directory. private static void ExportFile(string filename, string exportPath = null) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; @@ -1313,6 +1446,14 @@ private static void fsw_Changed(object sender, FileSystemEventArgs e) /// The exported path is known internally. private static void DropExport(string filename) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; @@ -1350,6 +1491,14 @@ private static void DropExport(string filename) /// The exported path is known automatically. private static void PullFile(string filename) { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; @@ -1394,6 +1543,14 @@ private static void PullFile(string filename) /// private static void Push() { + if (Program.WhitelistOverridden) + { + Console.ForegroundColor = ConsoleColor.Red; + Console.WriteLine("Due to opening a whitelist non compliant addon, the restrictions and addon modification capability has been disabled."); + Console.ResetColor(); + return; + } + if (AddonHandle == null) { Console.ForegroundColor = ConsoleColor.Red; diff --git a/SharpGMad/Whitelist.cs b/SharpGMad/Whitelist.cs index c8f984a..49547ab 100644 --- a/SharpGMad/Whitelist.cs +++ b/SharpGMad/Whitelist.cs @@ -29,6 +29,29 @@ static class Whitelist /// A list of string patterns of allowed files. /// private static string[] Wildcard = new string[]{ + "lua/*.lua", + "scenes/*.vcd", + "particles/*.pcf", + "resource/fonts/*.ttf", + "scripts/vehicles/*.txt", + "resource/localization/*/*.properties", + "maps/*.bsp", + "maps/*.nav", + "maps/*.ain", + "maps/thumb/*.png", + "sound/*.wav", + "sound/*.mp3", + "sound/*.ogg", + "materials/*.vmt", + "materials/*.vtf", + "materials/*.png", + "materials/*.jpg", + "materials/*.jpeg", + "models/*.mdl", + "models/*.vtx", + "models/*.phy", + "models/*.ani", + "models/*.vvd", "gamemodes/*/*.txt", "gamemodes/*/*.fgd", "gamemodes/*/logo.png", @@ -62,29 +85,6 @@ static class Whitelist "gamemodes/*/content/sound/*.wav", "gamemodes/*/content/sound/*.mp3", "gamemodes/*/content/sound/*.ogg", - "lua/*.lua", - "scenes/*.vcd", - "particles/*.pcf", - "resource/fonts/*.ttf", - "scripts/vehicles/*.txt", - "resource/localization/*/*.properties", - "maps/*.bsp", - "maps/*.nav", - "maps/*.ain", - "maps/thumb/*.png", - "sound/*.wav", - "sound/*.mp3", - "sound/*.ogg", - "materials/*.vmt", - "materials/*.vtf", - "materials/*.png", - "materials/*.jpg", - "materials/*.jpeg", - "models/*.mdl", - "models/*.vtx", - "models/*.phy", - "models/*.ani", - "models/*.vvd", null }; @@ -130,7 +130,7 @@ static Whitelist() /// True if the file is allowed, false if not. public static bool Check(string path) { - return Wildcard.Any(wildcard => Check(wildcard, path)); + return (Program.WhitelistOverridden || Wildcard.Any(wildcard => Check(wildcard, path))); } ///