From b205794d6ad7b50e140f615f367366e607571341 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 28 Jan 2025 22:00:17 +0800 Subject: [PATCH 1/9] Add fuzz test cases --- .../RegistryPreview.FuzzTests/FuzzTests.cs | 26 ++++++++++ .../MSTestSettings.cs | 5 ++ .../OneFuzzConfig.json | 50 +++++++++++++++++++ .../RegistryPreview.FuzzTests.csproj | 28 +++++++++++ 4 files changed, 109 insertions(+) create mode 100644 src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs create mode 100644 src/modules/registrypreview/RegistryPreview.FuzzTests/MSTestSettings.cs create mode 100644 src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json create mode 100644 src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs new file mode 100644 index 000000000000..f81bb1cc33e0 --- /dev/null +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs @@ -0,0 +1,26 @@ +// Copyright (c) Microsoft Corporation +// The Microsoft Corporation licenses this file to you under the MIT license. +// See the LICENSE file in the project root for more information. +namespace RegistryPreview.FuzzTests +{ + public class FuzzTests + { + public static void FuzzTargetMethod(ReadOnlySpan input) + { + try + { + // … use input parameter in code under test … + // + // TargetMethod(…); + } + catch (Exception ex) when (ex is ArgumentException) + { + // This is an example. It's important to filter out any *expected* exceptions from our code here. + // However, catching all exceptions is considered an anti-pattern because it may suppress legitimate + // issues, such as a NullReferenceException thrown by our code. In this case, we still re-throw + // the exception, as the ToJsonFromXmlOrCsvAsync method is not expected to throw any exceptions. + throw; + } + } + } +} diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/MSTestSettings.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/MSTestSettings.cs new file mode 100644 index 000000000000..5b05c0b86e3f --- /dev/null +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/MSTestSettings.cs @@ -0,0 +1,5 @@ +// Copyright (c) Microsoft Corporation +// The Microsoft Corporation licenses this file to you under the MIT license. +// See the LICENSE file in the project root for more information. + +[assembly: Parallelize(Scope = ExecutionScope.MethodLevel)] diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json b/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json new file mode 100644 index 000000000000..d86b7bf773c6 --- /dev/null +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json @@ -0,0 +1,50 @@ +// Copyright (c) Microsoft Corporation +// The Microsoft Corporation licenses this file to you under the MIT license. +// See the LICENSE file in the project root for more information. +{ + "configVersion": 3, + "entries": [ + { + "fuzzer": { + "$type": "libfuzzerDotNet", + "dll": "RegistryPreview.FuzzTests.dll", + "class": "RegistryPreview.FuzzTests.FuzzTests", + "method": "FuzzTargetMethod", + "FuzzingTargetBinaries": [ + "PowerToys.RegistryPreview.dll" + ] + }, + "adoTemplate": { + // supply the values appropriate to your + // project, where bugs will be filed + "org": "microsoft", + "project": "OS", + "AssignedTo": "mengyuanchen@microsoft.com", + "AreaPath": "OS\\Windows Client and Services\\WinPD\\DEEP-Developer Experience, Ecosystem and Partnerships\\SHINE\\PowerToys", + "IterationPath": "OS\\Future" + }, + "jobNotificationEmail": "mengyuanchen@microsoft.com", + "skip": false, + "rebootAfterSetup": false, + "oneFuzzJobs": [ + // at least one job is required + { + "projectName": "RegistryPreview", + "targetName": "RegistryPreview-dotnet-fuzzer" + } + ], + "jobDependencies": [ + // this should contain, at minimum, + // the DLL and PDB files + // you will need to add any other files required + // (globs are supported) + "RegistryPreview.FuzzTests.dll", + "RegistryPreview.FuzzTests.pdb", + "Microsoft.Windows.SDK.NET.dll", + "Newtonsoft.Json.dll", + "WinRT.Runtime.dll" + ], + "SdlWorkItemId": 49911822 + } + ] +} \ No newline at end of file diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj new file mode 100644 index 000000000000..a196ccb1b120 --- /dev/null +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj @@ -0,0 +1,28 @@ + + + + net8.0 + latest + enable + enable + + + + ..\..\..\..\$(Platform)\$(Configuration)\tests\RegistryPreview.FuzzTests\ + + + + + PreserveNewest + + + + + + + + + + + + From 88f5e65ee8332b2b3e3265883e979c76bad8d059 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 11 Feb 2025 10:53:24 +0800 Subject: [PATCH 2/9] add fuzz tests framework in registrypreview --- PowerToys.sln | 15 +++++++++++++++ .../RegistryPreview.FuzzTests/FuzzTests.cs | 10 ++++++---- 2 files changed, 21 insertions(+), 4 deletions(-) diff --git a/PowerToys.sln b/PowerToys.sln index 870999f12c3b..cdd4357681f4 100644 --- a/PowerToys.sln +++ b/PowerToys.sln @@ -636,6 +636,8 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ZoomItModuleInterface", "sr EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ZoomItSettingsInterop", "src\modules\ZoomIt\ZoomItSettingsInterop\ZoomItSettingsInterop.vcxproj", "{CA7D8106-30B9-4AEC-9D05-B69B31B8C461}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "RegistryPreview.FuzzTests", "src\modules\registrypreview\RegistryPreview.FuzzTests\RegistryPreview.FuzzTests.csproj", "{50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|ARM64 = Debug|ARM64 @@ -2834,6 +2836,18 @@ Global {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x64.Build.0 = Release|x64 {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x86.ActiveCfg = Release|x64 {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x86.Build.0 = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|ARM64.ActiveCfg = Debug|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|ARM64.Build.0 = Debug|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x64.ActiveCfg = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x64.Build.0 = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x86.ActiveCfg = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x86.Build.0 = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|ARM64.ActiveCfg = Release|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|ARM64.Build.0 = Release|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x64.ActiveCfg = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x64.Build.0 = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x86.ActiveCfg = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x86.Build.0 = Release|x64 EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -3069,6 +3083,7 @@ Global {0A84F764-3A88-44CD-AA96-41BDBD48627B} = {DD6E12FE-5509-4ABC-ACC2-3D6DC98A238C} {E4585179-2AC1-4D5F-A3FF-CFC5392F694C} = {DD6E12FE-5509-4ABC-ACC2-3D6DC98A238C} {CA7D8106-30B9-4AEC-9D05-B69B31B8C461} = {DD6E12FE-5509-4ABC-ACC2-3D6DC98A238C} + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734} = {929C1324-22E8-4412-A9A8-80E85F3985A5} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {C3A2F9D1-7930-4EF4-A6FC-7EE0A99821D0} diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs index f81bb1cc33e0..8e50b667f6bb 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs @@ -1,17 +1,19 @@ // Copyright (c) Microsoft Corporation // The Microsoft Corporation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. +using System; +using Microsoft.VisualStudio.TestTools.UnitTesting; + namespace RegistryPreview.FuzzTests { public class FuzzTests { - public static void FuzzTargetMethod(ReadOnlySpan input) + public static void FuzzParseRegistryFile(ReadOnlySpan input) { try { - // … use input parameter in code under test … - // - // TargetMethod(…); + var text = System.Text.Encoding.UTF8.GetString(input); + } catch (Exception ex) when (ex is ArgumentException) { From 330e2920374d19247cd2715a3a4805489348a923 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Mon, 24 Feb 2025 20:35:30 +0800 Subject: [PATCH 3/9] add registrypreview fuzzing code --- .pipelines/v2/templates/job-fuzz.yml | 2 +- .../RegistryPreview.FuzzTests/FuzzTests.cs | 159 ++++++++++++++++-- .../OneFuzzConfig.json | 46 ++++- .../RegistryPreview.FuzzTests.csproj | 6 +- .../RegistryPreviewUILib/ParseHelper.cs | 112 ++++++++++++ .../RegistryPreviewMainPage.Utilities.cs | 28 +-- 6 files changed, 325 insertions(+), 28 deletions(-) create mode 100644 src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs diff --git a/.pipelines/v2/templates/job-fuzz.yml b/.pipelines/v2/templates/job-fuzz.yml index b4e380194e65..c144fa91fd21 100644 --- a/.pipelines/v2/templates/job-fuzz.yml +++ b/.pipelines/v2/templates/job-fuzz.yml @@ -26,7 +26,7 @@ jobs: displayName: Download artifacts artifact: $(ArtifactName) patterns: |- - **/tests/*.FuzzTests/** + **/tests/RegistryPreview.FuzzTests/** - task: onefuzz-task@0 inputs: diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs index 8e50b667f6bb..2dffff832c24 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs @@ -2,26 +2,165 @@ // The Microsoft Corporation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. using System; +using System.Diagnostics; +using System.Globalization; +using System.Resources; using Microsoft.VisualStudio.TestTools.UnitTesting; +using Microsoft.Win32; +using RegistryPreviewUILib; namespace RegistryPreview.FuzzTests { public class FuzzTests { - public static void FuzzParseRegistryFile(ReadOnlySpan input) + private const string REGISTRYHEADER4 = "regedit4"; + private const string REGISTRYHEADER5 = "windows registry editor version 5.00"; + private const string KEYIMAGE = "ms-appx:///Assets/RegistryPreview/folder32.png"; + private const string DELETEDKEYIMAGE = "ms-appx:///Assets/RegistryPreview/deleted-folder32.png"; + + public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) { - try + string registryLine; + + var filenameText = GenerateRegistryHeader(input); + + string[] registryLines = filenameText.Split("\r"); + + if (registryLines.Length <= 1) + { + return; + } + + // REG files have to start with one of two headers and it's case-insensitive + registryLine = registryLines[0]; + + if (!IsValidRegistryHeader(registryLine)) + { + return; + } + + int index = 1; + registryLine = registryLines[index]; + + ParseHelper.ProcessRegistryLine(registryLine); + if (registryLine.StartsWith("[-", StringComparison.InvariantCulture)) + { + // remove the - as we won't need it but it will get special treatment in the UI + registryLine = registryLine.Remove(1, 1); + + string imageName = DELETEDKEYIMAGE; + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); + } + else if (registryLine.StartsWith('[')) + { + string imageName = KEYIMAGE; + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); + } + else + { + return; + } + } + + public static void FuzzStripFirstAndLast(ReadOnlySpan input) + { + string registryLine; + + var filenameText = GenerateRegistryHeader(input); + Console.WriteLine($"\n input1 is {filenameText}"); + + filenameText = filenameText.Replace("\r\n", "\r"); + string[] registryLines = filenameText.Split("\r"); + + if (registryLines.Length <= 1) + { + return; + } + + // REG files have to start with one of two headers and it's case-insensitive + registryLine = registryLines[0]; + + if (!IsValidRegistryHeader(registryLine)) { - var text = System.Text.Encoding.UTF8.GetString(input); - + return; } - catch (Exception ex) when (ex is ArgumentException) + + int index = 1; + registryLine = registryLines[index]; + Console.WriteLine($"\n registryLine1 is {registryLine}"); + + ParseHelper.ProcessRegistryLine(registryLine); + + if (registryLine.StartsWith("[-", StringComparison.InvariantCulture)) + { + // remove the - as we won't need it but it will get special treatment in the UI + registryLine = registryLine.Remove(1, 1); + + string imageName = DELETEDKEYIMAGE; + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); + Console.WriteLine($"\n CheckKeyLineForBrackets is {registryLine}"); + + registryLine = ParseHelper.StripFirstAndLast(registryLine); + } + else if (registryLine.StartsWith('[')) + { + string imageName = KEYIMAGE; + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); + Console.WriteLine($"\n CheckKeyLineForBrackets2 is {registryLine}"); + + registryLine = ParseHelper.StripFirstAndLast(registryLine); + } + else if (registryLine.StartsWith('"') && registryLine.EndsWith("=-", StringComparison.InvariantCulture)) + { + registryLine = registryLine.Replace("=-", string.Empty); + + // remove the "'s without removing all of them + registryLine = ParseHelper.StripFirstAndLast(registryLine); + } + else if (registryLine.StartsWith('"')) + { + int equal = registryLine.IndexOf('='); + if ((equal < 0) || (equal > registryLine.Length - 1)) + { + // something is very wrong + return; + } + + // set the name and the value + string name = registryLine.Substring(0, equal); + + // trim the whitespace and quotes from the name + name = name.Trim(); + name = ParseHelper.StripFirstAndLast(name); + } + else + { + return; + } + } + + public static string GenerateRegistryHeader(ReadOnlySpan input) + { + string header = new Random().Next(2) == 0 ? REGISTRYHEADER4 : REGISTRYHEADER5; + + string inputText = System.Text.Encoding.UTF8.GetString(input); + string filenameText = header + "\r\n" + inputText; + + return filenameText.Replace("\r\n", "\r"); + } + + private static bool IsValidRegistryHeader(string line) + { + // Convert the line to lowercase once for comparison + var lineLower = line.ToLowerInvariant(); + + switch (line) { - // This is an example. It's important to filter out any *expected* exceptions from our code here. - // However, catching all exceptions is considered an anti-pattern because it may suppress legitimate - // issues, such as a NullReferenceException thrown by our code. In this case, we still re-throw - // the exception, as the ToJsonFromXmlOrCsvAsync method is not expected to throw any exceptions. - throw; + case REGISTRYHEADER4: + case REGISTRYHEADER5: + return true; + default: + return false; } } } diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json b/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json index d86b7bf773c6..a074f41123f0 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/OneFuzzConfig.json @@ -9,7 +9,7 @@ "$type": "libfuzzerDotNet", "dll": "RegistryPreview.FuzzTests.dll", "class": "RegistryPreview.FuzzTests.FuzzTests", - "method": "FuzzTargetMethod", + "method": "FuzzCheckKeyLineForBrackets", "FuzzingTargetBinaries": [ "PowerToys.RegistryPreview.dll" ] @@ -30,7 +30,48 @@ // at least one job is required { "projectName": "RegistryPreview", - "targetName": "RegistryPreview-dotnet-fuzzer" + "targetName": "RegistryPreview-dotnet-CheckKeyLineForBrackets-fuzzer" + } + ], + "jobDependencies": [ + // this should contain, at minimum, + // the DLL and PDB files + // you will need to add any other files required + // (globs are supported) + "RegistryPreview.FuzzTests.dll", + "RegistryPreview.FuzzTests.pdb", + "Microsoft.Windows.SDK.NET.dll", + "WinRT.Runtime.dll" + ], + "SdlWorkItemId": 49911822 + }, + { + "fuzzer": { + "$type": "libfuzzerDotNet", + "dll": "RegistryPreview.FuzzTests.dll", + "class": "RegistryPreview.FuzzTests.FuzzTests", + "method": "FuzzStripFirstAndLast", + "FuzzingTargetBinaries": [ + "PowerToys.RegistryPreview.dll" + ] + }, + "adoTemplate": { + // supply the values appropriate to your + // project, where bugs will be filed + "org": "microsoft", + "project": "OS", + "AssignedTo": "mengyuanchen@microsoft.com", + "AreaPath": "OS\\Windows Client and Services\\WinPD\\DEEP-Developer Experience, Ecosystem and Partnerships\\SHINE\\PowerToys", + "IterationPath": "OS\\Future" + }, + "jobNotificationEmail": "mengyuanchen@microsoft.com", + "skip": false, + "rebootAfterSetup": false, + "oneFuzzJobs": [ + // at least one job is required + { + "projectName": "RegistryPreview", + "targetName": "RegistryPreview-dotnet-StripFirstAndLasts-fuzzer" } ], "jobDependencies": [ @@ -41,7 +82,6 @@ "RegistryPreview.FuzzTests.dll", "RegistryPreview.FuzzTests.pdb", "Microsoft.Windows.SDK.NET.dll", - "Newtonsoft.Json.dll", "WinRT.Runtime.dll" ], "SdlWorkItemId": 49911822 diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj index a196ccb1b120..eef76c93bc08 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj @@ -1,7 +1,7 @@ - net8.0 + net7.0 latest enable enable @@ -11,6 +11,10 @@ ..\..\..\..\$(Platform)\$(Configuration)\tests\RegistryPreview.FuzzTests\ + + + + PreserveNewest diff --git a/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs b/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs new file mode 100644 index 000000000000..617f0b4c4ab6 --- /dev/null +++ b/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs @@ -0,0 +1,112 @@ +// Copyright (c) Microsoft Corporation +// The Microsoft Corporation licenses this file to you under the MIT license. +// See the LICENSE file in the project root for more information. + +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace RegistryPreviewUILib +{ + public class ParseHelper + { + private const string ERRORIMAGE = "ms-appx:///Assets/RegistryPreview/error32.png"; + + /// + /// Checks a Key line for the closing bracket and treat it as an error if it cannot be found + /// + public static void CheckKeyLineForBrackets(ref string registryLine, ref string imageName) + { + // following the current behavior of the registry editor, find the last ] and treat everything else as ignorable + int lastBracket = registryLine.LastIndexOf(']'); + if (lastBracket == -1) + { + // since we don't have a last bracket yet, add an extra space and continue processing + registryLine += " "; + imageName = ERRORIMAGE; + } + else + { + // having found the last ] and there is text after it, drop the rest of the string on the floor + if (lastBracket < registryLine.Length - 1) + { + registryLine = registryLine.Substring(0, lastBracket + 1); + } + + if (CheckForKnownGoodBranches(registryLine) == false) + { + imageName = ERRORIMAGE; + } + } + } + + /// + /// Make sure the root of a full path start with one of the five "hard coded" roots. Throw an error for the branch if it doesn't. + /// + private static bool CheckForKnownGoodBranches(string key) + { + if ((key.StartsWith("[HKEY_CLASSES_ROOT]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKEY_CURRENT_USER]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKEY_USERS]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKEY_LOCAL_MACHINE]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKEY_CURRENT_CONFIG]", StringComparison.InvariantCultureIgnoreCase) == false) + && + (key.StartsWith(@"[HKEY_CLASSES_ROOT\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKEY_CURRENT_USER\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKEY_USERS\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKEY_LOCAL_MACHINE\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKEY_CURRENT_CONFIG\", StringComparison.InvariantCultureIgnoreCase) == false) + && + (key.StartsWith("[HKCR]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKCU]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKU]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKLM]", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith("[HKCC]", StringComparison.InvariantCultureIgnoreCase) == false) + && + (key.StartsWith(@"[HKCR\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKCU\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKU\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKLM\", StringComparison.InvariantCultureIgnoreCase) == false && + key.StartsWith(@"[HKCC\", StringComparison.InvariantCultureIgnoreCase) == false)) + { + return false; + } + + return true; + } + + /// + /// Rip the first and last character off a string, + /// checking that the string is at least 2 characters long to avoid errors + /// + public static string StripFirstAndLast(string line) + { + if (line.Length > 1) + { + line = line.Remove(line.Length - 1, 1); + line = line.Remove(0, 1); + } + + return line; + } + + public static string ProcessRegistryLine(string registryLine) + { + if (registryLine.StartsWith("@=-", StringComparison.InvariantCulture)) + { + // REG file has a callout to delete the @ Value which won't work *but* the Registry Editor will + // clear the value of the @ Value instead, so it's still a valid line. + registryLine = registryLine.Replace("@=-", "\"(Default)\"=\"\""); + } + else if (registryLine.StartsWith("@=", StringComparison.InvariantCulture)) + { + // This is the Value called "(Default)" so we tweak the line for the UX + registryLine = registryLine.Replace("@=", "\"(Default)\"="); + } + + return registryLine; + } + } +} diff --git a/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs b/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs index b8fc6e4e1d9a..6a29a387f607 100644 --- a/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs +++ b/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs @@ -225,7 +225,9 @@ private bool ParseRegistryFile(string filenameText) { // special case for when the registryLine begins with a @ - make some tweaks and // let the regular processing handle the rest. - if (registryLine.StartsWith("@=-", StringComparison.InvariantCulture)) + registryLine = ParseHelper.ProcessRegistryLine(registryLine); + + /* if (registryLine.StartsWith("@=-", StringComparison.InvariantCulture)) { // REG file has a callout to delete the @ Value which won't work *but* the Registry Editor will // clear the value of the @ Value instead, so it's still a valid line. @@ -235,7 +237,7 @@ private bool ParseRegistryFile(string filenameText) { // This is the Value called "(Default)" so we tweak the line for the UX registryLine = registryLine.Replace("@=", "\"(Default)\"="); - } + }*/ // continue until we have nothing left to read // switch logic, based off what the current line we're reading is @@ -245,10 +247,10 @@ private bool ParseRegistryFile(string filenameText) registryLine = registryLine.Remove(1, 1); string imageName = DELETEDKEYIMAGE; - CheckKeyLineForBrackets(ref registryLine, ref imageName); + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); // this is a key, so remove the first [ and last ] - registryLine = StripFirstAndLast(registryLine); + registryLine = ParseHelper.StripFirstAndLast(registryLine); // do not track the result of this node, since it should have no children AddTextToTree(registryLine, imageName); @@ -256,10 +258,10 @@ private bool ParseRegistryFile(string filenameText) else if (registryLine.StartsWith('[')) { string imageName = KEYIMAGE; - CheckKeyLineForBrackets(ref registryLine, ref imageName); + ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); // this is a key, so remove the first [ and last ] - registryLine = StripFirstAndLast(registryLine); + registryLine = ParseHelper.StripFirstAndLast(registryLine); treeViewNode = AddTextToTree(registryLine, imageName); lastKeyPath = registryLine; @@ -270,7 +272,7 @@ private bool ParseRegistryFile(string filenameText) registryLine = registryLine.Replace("=-", string.Empty); // remove the "'s without removing all of them - registryLine = StripFirstAndLast(registryLine); + registryLine = ParseHelper.StripFirstAndLast(registryLine); // Create a new listview item that will be used to display the delete value and store it registryValue = new RegistryValue(registryLine, string.Empty, string.Empty, lastKeyPath); @@ -300,7 +302,7 @@ private bool ParseRegistryFile(string filenameText) // trim the whitespace and quotes from the name name = name.Trim(); - name = StripFirstAndLast(name); + name = ParseHelper.StripFirstAndLast(name); // Clean out any escaped characters in the value, only for the preview name = StripEscapedCharacters(name); @@ -326,7 +328,7 @@ private bool ParseRegistryFile(string filenameText) if (value.StartsWith('"') && value.EndsWith('"')) { - value = StripFirstAndLast(value); + value = ParseHelper.StripFirstAndLast(value); } else { @@ -1038,7 +1040,7 @@ private void SetValueToolTip(RegistryValue registryValue) /// /// Checks a Key line for the closing bracket and treat it as an error if it cannot be found /// - private void CheckKeyLineForBrackets(ref string registryLine, ref string imageName) + /* private void CheckKeyLineForBrackets(ref string registryLine, ref string imageName) { // following the current behavior of the registry editor, find the last ] and treat everything else as ignorable int lastBracket = registryLine.LastIndexOf(']'); @@ -1061,7 +1063,7 @@ private void CheckKeyLineForBrackets(ref string registryLine, ref string imageNa imageName = ERRORIMAGE; } } - } + } */ /// /// Takes a binary registry value, sees if it has a ; and dumps the rest of the line - this does not work for REG_SZ values @@ -1082,7 +1084,7 @@ private string ScanAndRemoveComments(string value) /// /// Make sure the root of a full path start with one of the five "hard coded" roots. Throw an error for the branch if it doesn't. /// - private bool CheckForKnownGoodBranches(string key) + /* private bool CheckForKnownGoodBranches(string key) { if ((key.StartsWith("[HKEY_CLASSES_ROOT]", StringComparison.InvariantCultureIgnoreCase) == false && key.StartsWith("[HKEY_CURRENT_USER]", StringComparison.InvariantCultureIgnoreCase) == false && @@ -1112,7 +1114,7 @@ private bool CheckForKnownGoodBranches(string key) } return true; - } + } */ /// /// Turns the Open Key button in the command bar on/off, depending on if a key is selected From d1b4fee0b6e0a8a6d9a331c29b89cfdbbd262925 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Mon, 24 Feb 2025 20:59:02 +0800 Subject: [PATCH 4/9] add annotations and change net7.0--net8.0 --- .../RegistryPreview.FuzzTests/FuzzTests.cs | 20 ++++++++++++++----- .../RegistryPreview.FuzzTests.csproj | 5 +++-- 2 files changed, 18 insertions(+), 7 deletions(-) diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs index 2dffff832c24..58f6e871ae26 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs @@ -18,10 +18,12 @@ public class FuzzTests private const string KEYIMAGE = "ms-appx:///Assets/RegistryPreview/folder32.png"; private const string DELETEDKEYIMAGE = "ms-appx:///Assets/RegistryPreview/deleted-folder32.png"; + // Case 1: Fuzz test for CheckKeyLineForBrackets public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) { string registryLine; + // Simulate registry file content as filenameText var filenameText = GenerateRegistryHeader(input); string[] registryLines = filenameText.Split("\r"); @@ -32,15 +34,17 @@ public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) } // REG files have to start with one of two headers and it's case-insensitive + // The header in the registry file is either REGISTRYHEADER4 or REGISTRYHEADER5 registryLine = registryLines[0]; + // Check if the registry header is valid if (!IsValidRegistryHeader(registryLine)) { return; } int index = 1; - registryLine = registryLines[index]; + registryLine = registryLines[index]; // Extract content after the header ParseHelper.ProcessRegistryLine(registryLine); if (registryLine.StartsWith("[-", StringComparison.InvariantCulture)) @@ -49,11 +53,15 @@ public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) registryLine = registryLine.Remove(1, 1); string imageName = DELETEDKEYIMAGE; + + // Fuzz test for the CheckKeyLineForBrackets method ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); } else if (registryLine.StartsWith('[')) { string imageName = KEYIMAGE; + + // Fuzz test for the CheckKeyLineForBrackets method ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); } else @@ -62,12 +70,12 @@ public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) } } + // Case 1: Fuzz test for StripFirstAndLast public static void FuzzStripFirstAndLast(ReadOnlySpan input) { string registryLine; var filenameText = GenerateRegistryHeader(input); - Console.WriteLine($"\n input1 is {filenameText}"); filenameText = filenameText.Replace("\r\n", "\r"); string[] registryLines = filenameText.Split("\r"); @@ -87,7 +95,6 @@ public static void FuzzStripFirstAndLast(ReadOnlySpan input) int index = 1; registryLine = registryLines[index]; - Console.WriteLine($"\n registryLine1 is {registryLine}"); ParseHelper.ProcessRegistryLine(registryLine); @@ -98,16 +105,16 @@ public static void FuzzStripFirstAndLast(ReadOnlySpan input) string imageName = DELETEDKEYIMAGE; ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); - Console.WriteLine($"\n CheckKeyLineForBrackets is {registryLine}"); + // Fuzz test for the StripFirstAndLast method registryLine = ParseHelper.StripFirstAndLast(registryLine); } else if (registryLine.StartsWith('[')) { string imageName = KEYIMAGE; ParseHelper.CheckKeyLineForBrackets(ref registryLine, ref imageName); - Console.WriteLine($"\n CheckKeyLineForBrackets2 is {registryLine}"); + // Fuzz test for the StripFirstAndLast method registryLine = ParseHelper.StripFirstAndLast(registryLine); } else if (registryLine.StartsWith('"') && registryLine.EndsWith("=-", StringComparison.InvariantCulture)) @@ -115,6 +122,7 @@ public static void FuzzStripFirstAndLast(ReadOnlySpan input) registryLine = registryLine.Replace("=-", string.Empty); // remove the "'s without removing all of them + // Fuzz test for the StripFirstAndLast method registryLine = ParseHelper.StripFirstAndLast(registryLine); } else if (registryLine.StartsWith('"')) @@ -131,6 +139,8 @@ public static void FuzzStripFirstAndLast(ReadOnlySpan input) // trim the whitespace and quotes from the name name = name.Trim(); + + // Fuzz test for the StripFirstAndLast method name = ParseHelper.StripFirstAndLast(name); } else diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj index eef76c93bc08..d59656463e3c 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/RegistryPreview.FuzzTests.csproj @@ -1,8 +1,9 @@ - net7.0 - latest + net8.0-windows10.0.19041.0 + x64;ARM64 + latest enable enable From a6a9f92c2895ff633a650f03b59c457800ff1265 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 25 Feb 2025 09:25:20 +0800 Subject: [PATCH 5/9] merge main into code --- PowerToys.sln | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PowerToys.sln b/PowerToys.sln index 71df360ecf82..c03859446cde 100644 --- a/PowerToys.sln +++ b/PowerToys.sln @@ -2539,7 +2539,7 @@ Global {08F9155D-B6DC-46E5-9C83-AF60B655898B} = {38BDB927-829B-4C65-9CD9-93FB05D66D65} {4382A954-179A-4078-92AF-715187DFFF50} = {38BDB927-829B-4C65-9CD9-93FB05D66D65} {EBED240C-8702-452D-B764-6DB9DA9179AF} = {F05E590D-AD46-42BE-9C25-6A63ADD2E3EA} - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0} = {F05E590D-AD46-42BE-9C25-6A63ADD2E3EA} + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734} = {929C1324-22E8-4412-A9A8-80E85F3985A5} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {C3A2F9D1-7930-4EF4-A6FC-7EE0A99821D0} From 16c2c2b058842c362c64b477822246a572e87b36 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 25 Feb 2025 11:30:15 +0800 Subject: [PATCH 6/9] add registry fuzz sln --- PowerToys.sln | 22 ++++++++-------------- 1 file changed, 8 insertions(+), 14 deletions(-) diff --git a/PowerToys.sln b/PowerToys.sln index c03859446cde..5682f06179e3 100644 --- a/PowerToys.sln +++ b/PowerToys.sln @@ -2254,20 +2254,14 @@ Global {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|ARM64.Build.0 = Release|ARM64 {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x64.ActiveCfg = Release|x64 {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x64.Build.0 = Release|x64 - {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x86.ActiveCfg = Release|x64 - {CA7D8106-30B9-4AEC-9D05-B69B31B8C461}.Release|x86.Build.0 = Release|x64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|ARM64.ActiveCfg = Debug|ARM64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|ARM64.Build.0 = Debug|ARM64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|x64.ActiveCfg = Debug|x64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|x64.Build.0 = Debug|x64 - {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|x86.ActiveCfg = Debug|x64 - {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Debug|x86.Build.0 = Debug|x64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|ARM64.ActiveCfg = Release|ARM64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|ARM64.Build.0 = Release|ARM64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|x64.ActiveCfg = Release|x64 {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|x64.Build.0 = Release|x64 - {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|x86.ActiveCfg = Release|x64 - {A558C25D-2007-498E-8B6F-43405AFAE9E2}.Release|x86.Build.0 = Release|x64 {08F9155D-B6DC-46E5-9C83-AF60B655898B}.Debug|ARM64.ActiveCfg = Debug|ARM64 {08F9155D-B6DC-46E5-9C83-AF60B655898B}.Debug|ARM64.Build.0 = Debug|ARM64 {08F9155D-B6DC-46E5-9C83-AF60B655898B}.Debug|x64.ActiveCfg = Debug|x64 @@ -2292,14 +2286,14 @@ Global {EBED240C-8702-452D-B764-6DB9DA9179AF}.Release|ARM64.Build.0 = Release|ARM64 {EBED240C-8702-452D-B764-6DB9DA9179AF}.Release|x64.ActiveCfg = Release|x64 {EBED240C-8702-452D-B764-6DB9DA9179AF}.Release|x64.Build.0 = Release|x64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Debug|ARM64.ActiveCfg = Debug|ARM64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Debug|ARM64.Build.0 = Debug|ARM64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Debug|x64.ActiveCfg = Debug|x64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Debug|x64.Build.0 = Debug|x64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Release|ARM64.ActiveCfg = Release|ARM64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Release|ARM64.Build.0 = Release|ARM64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Release|x64.ActiveCfg = Release|x64 - {4E0AE3A4-2EE0-44D7-A2D0-8769977254A0}.Release|x64.Build.0 = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|ARM64.ActiveCfg = Debug|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|ARM64.Build.0 = Debug|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x64.ActiveCfg = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Debug|x64.Build.0 = Debug|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|ARM64.ActiveCfg = Release|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|ARM64.Build.0 = Release|ARM64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x64.ActiveCfg = Release|x64 + {50A9F3DE-CF0B-4CF0-AFDE-3A3E245D7734}.Release|x64.Build.0 = Release|x64 EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE From f0951bb4ed6ba01c141f7f94705af9d1f13326ea Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 25 Feb 2025 13:22:30 +0800 Subject: [PATCH 7/9] change fuzzing tests scope --- .pipelines/v2/templates/job-fuzz.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.pipelines/v2/templates/job-fuzz.yml b/.pipelines/v2/templates/job-fuzz.yml index c144fa91fd21..b4e380194e65 100644 --- a/.pipelines/v2/templates/job-fuzz.yml +++ b/.pipelines/v2/templates/job-fuzz.yml @@ -26,7 +26,7 @@ jobs: displayName: Download artifacts artifact: $(ArtifactName) patterns: |- - **/tests/RegistryPreview.FuzzTests/** + **/tests/*.FuzzTests/** - task: onefuzz-task@0 inputs: From 11471bd0e908cd77fb47fbf9f6d838b1a45eb8af Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 25 Feb 2025 15:46:44 +0800 Subject: [PATCH 8/9] remove unuse annotations --- .../RegistryPreviewUILib/ParseHelper.cs | 2 + .../RegistryPreviewMainPage.Utilities.cs | 75 ------------------- 2 files changed, 2 insertions(+), 75 deletions(-) diff --git a/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs b/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs index 617f0b4c4ab6..cdfea8bcee05 100644 --- a/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs +++ b/src/modules/registrypreview/RegistryPreviewUILib/ParseHelper.cs @@ -92,6 +92,8 @@ public static string StripFirstAndLast(string line) return line; } + // special case for when the registryLine begins with a @ - make some tweaks and + // let the regular processing handle the rest. public static string ProcessRegistryLine(string registryLine) { if (registryLine.StartsWith("@=-", StringComparison.InvariantCulture)) diff --git a/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs b/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs index 6a29a387f607..d35a43ca99e2 100644 --- a/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs +++ b/src/modules/registrypreview/RegistryPreviewUILib/RegistryPreviewMainPage.Utilities.cs @@ -227,18 +227,6 @@ private bool ParseRegistryFile(string filenameText) // let the regular processing handle the rest. registryLine = ParseHelper.ProcessRegistryLine(registryLine); - /* if (registryLine.StartsWith("@=-", StringComparison.InvariantCulture)) - { - // REG file has a callout to delete the @ Value which won't work *but* the Registry Editor will - // clear the value of the @ Value instead, so it's still a valid line. - registryLine = registryLine.Replace("@=-", "\"(Default)\"=\"\""); - } - else if (registryLine.StartsWith("@=", StringComparison.InvariantCulture)) - { - // This is the Value called "(Default)" so we tweak the line for the UX - registryLine = registryLine.Replace("@=", "\"(Default)\"="); - }*/ - // continue until we have nothing left to read // switch logic, based off what the current line we're reading is if (registryLine.StartsWith("[-", StringComparison.InvariantCulture)) @@ -1037,34 +1025,6 @@ private void SetValueToolTip(RegistryValue registryValue) registryValue.ToolTipText = value; } - /// - /// Checks a Key line for the closing bracket and treat it as an error if it cannot be found - /// - /* private void CheckKeyLineForBrackets(ref string registryLine, ref string imageName) - { - // following the current behavior of the registry editor, find the last ] and treat everything else as ignorable - int lastBracket = registryLine.LastIndexOf(']'); - if (lastBracket == -1) - { - // since we don't have a last bracket yet, add an extra space and continue processing - registryLine += " "; - imageName = ERRORIMAGE; - } - else - { - // having found the last ] and there is text after it, drop the rest of the string on the floor - if (lastBracket < registryLine.Length - 1) - { - registryLine = registryLine.Substring(0, lastBracket + 1); - } - - if (CheckForKnownGoodBranches(registryLine) == false) - { - imageName = ERRORIMAGE; - } - } - } */ - /// /// Takes a binary registry value, sees if it has a ; and dumps the rest of the line - this does not work for REG_SZ values /// @@ -1081,41 +1041,6 @@ private string ScanAndRemoveComments(string value) return value.TrimEnd(); } - /// - /// Make sure the root of a full path start with one of the five "hard coded" roots. Throw an error for the branch if it doesn't. - /// - /* private bool CheckForKnownGoodBranches(string key) - { - if ((key.StartsWith("[HKEY_CLASSES_ROOT]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKEY_CURRENT_USER]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKEY_USERS]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKEY_LOCAL_MACHINE]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKEY_CURRENT_CONFIG]", StringComparison.InvariantCultureIgnoreCase) == false) - && - (key.StartsWith(@"[HKEY_CLASSES_ROOT\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKEY_CURRENT_USER\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKEY_USERS\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKEY_LOCAL_MACHINE\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKEY_CURRENT_CONFIG\", StringComparison.InvariantCultureIgnoreCase) == false) - && - (key.StartsWith("[HKCR]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKCU]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKU]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKLM]", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith("[HKCC]", StringComparison.InvariantCultureIgnoreCase) == false) - && - (key.StartsWith(@"[HKCR\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKCU\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKU\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKLM\", StringComparison.InvariantCultureIgnoreCase) == false && - key.StartsWith(@"[HKCC\", StringComparison.InvariantCultureIgnoreCase) == false)) - { - return false; - } - - return true; - } */ - /// /// Turns the Open Key button in the command bar on/off, depending on if a key is selected /// From 8ca1c2f47fa43b8926340f51d84e5916f7b1d6b4 Mon Sep 17 00:00:00 2001 From: "Mengyuan Chen (from Dev Box)" Date: Tue, 25 Feb 2025 15:59:39 +0800 Subject: [PATCH 9/9] fix typos --- .../registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs index 58f6e871ae26..b0ebfa3c5e48 100644 --- a/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs +++ b/src/modules/registrypreview/RegistryPreview.FuzzTests/FuzzTests.cs @@ -70,7 +70,7 @@ public static void FuzzCheckKeyLineForBrackets(ReadOnlySpan input) } } - // Case 1: Fuzz test for StripFirstAndLast + // Case 2: Fuzz test for StripFirstAndLast public static void FuzzStripFirstAndLast(ReadOnlySpan input) { string registryLine;