diff --git a/src/libraries/Common/tests/System/IO/ReparsePointUtilities.cs b/src/libraries/Common/tests/System/IO/ReparsePointUtilities.cs index 8a146c9b0dc19..205e045617d91 100644 --- a/src/libraries/Common/tests/System/IO/ReparsePointUtilities.cs +++ b/src/libraries/Common/tests/System/IO/ReparsePointUtilities.cs @@ -60,7 +60,7 @@ public static partial class MountHelper // Reduce the risk we accidentally stop running these altogether // on Windows, due to a bug in CreateSymbolicLink if (!success && PlatformDetection.IsWindows) - Assert.True(!PlatformDetection.IsWindowsAndElevated); + Assert.False(PlatformDetection.IsPrivilegedProcess); return success; }); diff --git a/src/libraries/Common/tests/TestUtilities/System/AdminHelpers.cs b/src/libraries/Common/tests/TestUtilities/System/AdminHelpers.cs index bf64c9ffea37a..6c523ce780312 100644 --- a/src/libraries/Common/tests/TestUtilities/System/AdminHelpers.cs +++ b/src/libraries/Common/tests/TestUtilities/System/AdminHelpers.cs @@ -34,6 +34,12 @@ public static int RunAsSudo(string commandLine) public static unsafe bool IsProcessElevated() { + // Browser does not have the concept of an elevated process + if (RuntimeInformation.IsOSPlatform(OSPlatform.Create("BROWSER"))) + { + return false; + } + if (!RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) { uint userId = Interop.Sys.GetEUid(); diff --git a/src/libraries/Common/tests/TestUtilities/System/IO/FileCleanupTestBase.cs b/src/libraries/Common/tests/TestUtilities/System/IO/FileCleanupTestBase.cs index 326786de7e9c4..0629483be0730 100644 --- a/src/libraries/Common/tests/TestUtilities/System/IO/FileCleanupTestBase.cs +++ b/src/libraries/Common/tests/TestUtilities/System/IO/FileCleanupTestBase.cs @@ -14,12 +14,8 @@ namespace System.IO /// Base class for test classes the use temporary files that need to be cleaned up. public abstract partial class FileCleanupTestBase : IDisposable { - private static readonly Lazy s_isElevated = new Lazy(() => AdminHelpers.IsProcessElevated()); - private string fallbackGuid = Guid.NewGuid().ToString("N").Substring(0, 10); - protected static bool IsProcessElevated => s_isElevated.Value; - /// Initialize the test class base. This creates the associated test directory. protected FileCleanupTestBase(string tempDirectory = null) { diff --git a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Unix.cs b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Unix.cs index 33d0d80c97ce2..258572fced24c 100644 --- a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Unix.cs +++ b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Unix.cs @@ -55,10 +55,6 @@ public static partial class PlatformDetection public static bool IsNotFedoraOrRedHatFamily => !IsFedora && !IsRedHatFamily; public static bool IsNotDebian10 => !IsDebian10; - public static bool IsSuperUser => IsBrowser || IsWindows ? false : libc.geteuid() == 0; - - public static bool IsUnixAndSuperUser => !IsWindows && IsSuperUser; - public static Version OpenSslVersion => !IsOSXLike && !IsWindows && !IsAndroid ? GetOpenSslVersion() : throw new PlatformNotSupportedException(); diff --git a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Windows.cs b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Windows.cs index 7d2c35de4ff11..1b570872d06d9 100644 --- a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Windows.cs +++ b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.Windows.cs @@ -248,31 +248,8 @@ public static bool IsInAppContainer } } - public static bool CanRunImpersonatedTests => PlatformDetection.IsNotWindowsNanoServer && PlatformDetection.IsWindowsAndElevated; + public static bool CanRunImpersonatedTests => PlatformDetection.IsNotWindowsNanoServer && PlatformDetection.IsWindows && PlatformDetection.IsPrivilegedProcess; public static bool IsWindowsX86OrX64 => PlatformDetection.IsWindows && (PlatformDetection.IsX86Process || PlatformDetection.IsX64Process); - - private static int s_isWindowsElevated = -1; - public static bool IsWindowsAndElevated - { - get - { - if (s_isWindowsElevated != -1) - return s_isWindowsElevated == 1; - - if (!IsWindows || IsInAppContainer) - { - s_isWindowsElevated = 0; - return false; - } - - s_isWindowsElevated = AdminHelpers.IsProcessElevated() ? 1 : 0; - - return s_isWindowsElevated == 1; - } - } - - public static bool IsWindowsAndNotElevated - => IsWindows && !IsWindowsAndElevated; } } diff --git a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.cs b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.cs index f4e4ec8a168bf..245ff9ccaee00 100644 --- a/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.cs +++ b/src/libraries/Common/tests/TestUtilities/System/PlatformDetection.cs @@ -73,6 +73,23 @@ public static partial class PlatformDetection public static bool Is64BitProcess => IntPtr.Size == 8; public static bool IsNotWindows => !IsWindows; + private static volatile int s_isPrivilegedProcess = -1; + public static bool IsPrivilegedProcess + { + get + { + int p = s_isPrivilegedProcess; + if (p == -1) + { + s_isPrivilegedProcess = p = AdminHelpers.IsProcessElevated() ? 1 : 0; + } + + return p == 1; + } + } + + public static bool IsNotPrivilegedProcess => !IsPrivilegedProcess; + public static bool IsMarshalGetExceptionPointersSupported => !IsMonoRuntime && !IsNativeAot; private static readonly Lazy s_isCheckedRuntime = new Lazy(() => AssemblyConfigurationEquals("Checked")); diff --git a/src/libraries/Common/tests/TestUtilities/System/WindowsIdentityFixture.cs b/src/libraries/Common/tests/TestUtilities/System/WindowsIdentityFixture.cs index 794f09beeba73..708c22c078173 100644 --- a/src/libraries/Common/tests/TestUtilities/System/WindowsIdentityFixture.cs +++ b/src/libraries/Common/tests/TestUtilities/System/WindowsIdentityFixture.cs @@ -39,7 +39,8 @@ public sealed partial class WindowsTestAccount : IDisposable public WindowsTestAccount(string userName) { - Assert.True(PlatformDetection.IsWindowsAndElevated); + Assert.True(PlatformDetection.IsWindows); + Assert.True(PlatformDetection.IsPrivilegedProcess); _userName = userName; Password = GeneratePassword(); diff --git a/src/libraries/System.Diagnostics.Process/tests/ProcessStartInfoTests.cs b/src/libraries/System.Diagnostics.Process/tests/ProcessStartInfoTests.cs index 1fbe26a087691..66fe0a2dabf4a 100644 --- a/src/libraries/System.Diagnostics.Process/tests/ProcessStartInfoTests.cs +++ b/src/libraries/System.Diagnostics.Process/tests/ProcessStartInfoTests.cs @@ -27,7 +27,8 @@ public class ProcessStartInfoTests : ProcessTestBase private const string ItemSeparator = "CAFF9451396B4EEF8A5155A15BDC2080"; // random string that shouldn't be in any env vars; used instead of newline to separate env var strings private static bool IsAdmin_IsNotNano_RemoteExecutorIsSupported - => PlatformDetection.IsWindowsAndElevated && PlatformDetection.IsNotWindowsNanoServer && RemoteExecutor.IsSupported; + => PlatformDetection.IsWindows && PlatformDetection.IsNotWindowsNanoServer + && PlatformDetection.IsPrivilegedProcess && RemoteExecutor.IsSupported; [Fact] public void TestEnvironmentProperty() diff --git a/src/libraries/System.Diagnostics.Process/tests/ProcessTests.Unix.cs b/src/libraries/System.Diagnostics.Process/tests/ProcessTests.Unix.cs index 3a99e7d1c68c5..b29de573446e7 100644 --- a/src/libraries/System.Diagnostics.Process/tests/ProcessTests.Unix.cs +++ b/src/libraries/System.Diagnostics.Process/tests/ProcessTests.Unix.cs @@ -20,7 +20,7 @@ namespace System.Diagnostics.Tests { public partial class ProcessTests : ProcessTestBase { - private static bool IsRemoteExecutorSupportedAndOnUnixAndSuperUser => RemoteExecutor.IsSupported && PlatformDetection.IsUnixAndSuperUser; + private static bool IsRemoteExecutorSupportedAndPrivilegedProcess => RemoteExecutor.IsSupported && PlatformDetection.IsPrivilegedProcess; [Fact] private void TestWindowApisUnix() @@ -456,7 +456,7 @@ public void ProcessStart_UseShellExecuteTrue_OpenUrl_SuccessfullyReadsArgumentAr } } - [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsUnixAndSuperUser))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestPriorityClassUnix() { CreateDefaultProcess(); @@ -478,11 +478,11 @@ public void TestPriorityClassUnix() } catch (Win32Exception ex) { - Assert.True(!PlatformDetection.IsSuperUser, $"Failed even though superuser {ex.ToString()}"); + Assert.False(PlatformDetection.IsPrivilegedProcess, $"Failed even though superuser {ex.ToString()}"); } } - [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsUnixAndSuperUser))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestBasePriorityOnUnix() { CreateDefaultProcess(); @@ -499,7 +499,7 @@ public void TestBasePriorityOnUnix() } catch (Win32Exception ex) { - Assert.True(!PlatformDetection.IsSuperUser, $"Failed even though superuser {ex.ToString()}"); + Assert.False(PlatformDetection.IsPrivilegedProcess, $"Failed even though superuser {ex.ToString()}"); } } @@ -596,8 +596,7 @@ public void TestCheckChildProcessUserAndGroupIds() /// Tests when running as root and starting a new process as a normal user, /// the new process doesn't have elevated privileges. /// - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] - [OuterLoop("Needs sudo access")] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(true)] [InlineData(false)] public unsafe void TestCheckChildProcessUserAndGroupIdsElevated(bool useRootGroups) @@ -743,7 +742,6 @@ private static async Task TryWaitProcessReapedAsync(int pid, int timeoutMs /// Tests the ProcessWaitState reference count drops to zero. /// [ConditionalFact(typeof(RemoteExecutor), nameof(RemoteExecutor.IsSupported))] - [PlatformSpecific(TestPlatforms.AnyUnix)] // Test validates Unix implementation public async Task TestProcessWaitStateReferenceCount() { using (var exitedEventSemaphore = new SemaphoreSlim(0, 1)) @@ -833,7 +831,6 @@ public void TestProcessRecycledPid() Assert.True(foundRecycled); } - [PlatformSpecific(TestPlatforms.AnyUnix)] [ConditionalTheory(typeof(RemoteExecutor), nameof(RemoteExecutor.IsSupported))] [InlineData("/dev/stdin", O_RDONLY)] [InlineData("/dev/stdout", O_WRONLY)] diff --git a/src/libraries/System.Diagnostics.Process/tests/ProcessTests.cs b/src/libraries/System.Diagnostics.Process/tests/ProcessTests.cs index b1a0e42577f5c..542869f962a98 100644 --- a/src/libraries/System.Diagnostics.Process/tests/ProcessTests.cs +++ b/src/libraries/System.Diagnostics.Process/tests/ProcessTests.cs @@ -2546,7 +2546,8 @@ public void Start_PassesArgumentsList_WhichGetsEscaped() } } - [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsWindowsAndNotElevated))] + [PlatformSpecific(TestPlatforms.Windows)] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotPrivilegedProcess))] public void NonElevatedUser_QueryProcessNameOfSystemProcess() { const string Services = "services"; diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/FuzzyTests.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/FuzzyTests.Etw.cs index dcf3a4673a7f1..d15c1d4a09552 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/FuzzyTests.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/FuzzyTests.Etw.cs @@ -1,6 +1,7 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. +using System; using System.Collections.Generic; #if USE_MDT_EVENTSOURCE using Microsoft.Diagnostics.Tracing; @@ -14,7 +15,7 @@ public partial class FuzzyTests { static partial void Test_Write_Fuzzy_TestEtw(List tests, EventSource logger) { - if (TestUtilities.IsProcessElevated) + if (PlatformDetection.IsPrivilegedProcess) { using (var listener = new EtwListener()) { diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestEventCounter.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestEventCounter.Etw.cs index 94d6532f4eea9..a1c04cc13ba6f 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestEventCounter.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestEventCounter.Etw.cs @@ -8,10 +8,7 @@ namespace BasicEventSourceTests { public partial class TestEventCounter { - // Specifies whether the process is elevated or not. - private static bool IsProcessElevated => Environment.IsPrivilegedProcess; - - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] [ActiveIssue("https://github.com/dotnet/runtime/issues/25035")] public void Test_Write_Metric_ETW() { diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestUtilities.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestUtilities.cs index 995c9f7512da5..62382c1d82dab 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestUtilities.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestUtilities.cs @@ -15,9 +15,6 @@ namespace BasicEventSourceTests { internal class TestUtilities { - // Specifies whether the process is elevated or not. - internal static bool IsProcessElevated => Environment.IsPrivilegedProcess; - /// /// Confirms that there are no EventSources running. /// diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsManifestGeneration.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsManifestGeneration.Etw.cs index a07e673a62274..7c2f5d3eb1592 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsManifestGeneration.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsManifestGeneration.Etw.cs @@ -25,9 +25,8 @@ namespace BasicEventSourceTests public partial class TestsManifestGeneration { // Specifies whether the process is elevated or not. - private static bool IsProcessElevated => Environment.IsPrivilegedProcess; private static bool IsProcessElevatedAndNotWindowsNanoServerAndRemoteExecutorSupported => - IsProcessElevated && PlatformDetection.IsNotWindowsNanoServer && RemoteExecutor.IsSupported; + PlatformDetection.IsPrivilegedProcess && PlatformDetection.IsNotWindowsNanoServer && RemoteExecutor.IsSupported; /// ETW only works with elevated process [ConditionalFact(nameof(IsProcessElevatedAndNotWindowsNanoServerAndRemoteExecutorSupported))] diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsUserErrors.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsUserErrors.Etw.cs index fdfb9d33ed000..c5743cfa7c4cf 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsUserErrors.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsUserErrors.Etw.cs @@ -21,7 +21,7 @@ public void Test_BadEventSource_MismatchedIds_WithEtwListener() { // We expect only one session to be on when running the test but if a ETW session was left // hanging, it will confuse the EventListener tests. - if (TestUtilities.IsProcessElevated) + if (PlatformDetection.IsPrivilegedProcess) { EtwListener.EnsureStopped(); } @@ -31,7 +31,7 @@ public void Test_BadEventSource_MismatchedIds_WithEtwListener() var listenerGenerators = new List> { () => new EventListenerListener() }; - if (TestUtilities.IsProcessElevated) + if (PlatformDetection.IsPrivilegedProcess) { listenerGenerators.Add(() => new EtwListener()); } diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWrite.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWrite.Etw.cs index e2b604ee75c34..35788ac712dea 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWrite.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWrite.Etw.cs @@ -11,9 +11,8 @@ namespace BasicEventSourceTests public partial class TestsWrite { // Specifies whether the process is elevated or not. - private static bool IsProcessElevated => Environment.IsPrivilegedProcess; private static bool IsProcessElevatedAndNotWindowsNanoServer => - IsProcessElevated && PlatformDetection.IsNotWindowsNanoServer; // ActiveIssue: https://github.com/dotnet/runtime/issues/26197 + PlatformDetection.IsPrivilegedProcess && PlatformDetection.IsNotWindowsNanoServer; // ActiveIssue: https://github.com/dotnet/runtime/issues/26197 /// /// Tests the EventSource.Write[T] method (can only use the self-describing mechanism). @@ -30,7 +29,7 @@ public void Test_Write_T_ETW() [ActiveIssue("https://github.com/dotnet/runtime/issues/21295", TargetFrameworkMonikers.NetFramework)] [ActiveIssue("https://github.com/dotnet/runtime/issues/25035")] - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Test_Write_T_In_Manifest_Serialization_WithEtwListener() { using (var eventListener = new EventListenerListener()) diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEvent.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEvent.Etw.cs index 7c1975836107b..088eafad41c63 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEvent.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEvent.Etw.cs @@ -11,9 +11,8 @@ namespace BasicEventSourceTests partial class TestsWriteEvent { // Specifies whether the process is elevated or not. - private static bool IsProcessElevated => Environment.IsPrivilegedProcess; private static bool IsProcessElevatedAndNotWindowsNanoServer => - IsProcessElevated && PlatformDetection.IsNotWindowsNanoServer; // ActiveIssue: https://github.com/dotnet/runtime/issues/26197 + PlatformDetection.IsPrivilegedProcess && PlatformDetection.IsNotWindowsNanoServer; // ActiveIssue: https://github.com/dotnet/runtime/issues/26197 /// /// Tests WriteEvent using the manifest based mechanism. @@ -84,7 +83,7 @@ public void Test_WriteEvent_ByteArray_SelfDescribing_ETW() static partial void Test_WriteEvent_AddEtwTests(List tests, EventSourceTest logger) { - if (!IsProcessElevated) + if (!PlatformDetection.IsPrivilegedProcess) { return; } diff --git a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEventToListener.Etw.cs b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEventToListener.Etw.cs index fb38678b1e303..6d3eb85fc0e24 100644 --- a/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEventToListener.Etw.cs +++ b/src/libraries/System.Diagnostics.Tracing/tests/BasicEventSourceTest/TestsWriteEventToListener.Etw.cs @@ -14,10 +14,7 @@ namespace BasicEventSourceTests { public partial class TestsWriteEventToListener { - // Specifies whether the process is elevated or not. - private static bool IsProcessElevated => Environment.IsPrivilegedProcess; - - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Test_WriteEvent_TransferEvents() { TestUtilities.CheckNoEventSourcesRunning("Start"); diff --git a/src/libraries/System.Formats.Tar/tests/TarEntry/TarEntry.ExtractToFile.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarEntry/TarEntry.ExtractToFile.Tests.Unix.cs index cee5f6bc7dfd8..d5438928a59dd 100644 --- a/src/libraries/System.Formats.Tar/tests/TarEntry/TarEntry.ExtractToFile.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarEntry/TarEntry.ExtractToFile.Tests.Unix.cs @@ -23,7 +23,7 @@ public static IEnumerable GetFormatsAndSpecialFiles() } } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [MemberData(nameof(GetFormatsAndSpecialFiles))] public void Extract_SpecialFiles(TarEntryFormat format, TarEntryType entryType) { @@ -36,7 +36,7 @@ public void Extract_SpecialFiles(TarEntryFormat format, TarEntryType entryType) Verify_Extract_SpecialFiles(destination, entry, entryType); } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [MemberData(nameof(GetFormatsAndSpecialFiles))] public async Task Extract_SpecialFiles_Async(TarEntryFormat format, TarEntryType entryType) { diff --git a/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectory.File.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectory.File.Tests.Unix.cs index 96e05721aa0e2..9a4076b52134b 100644 --- a/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectory.File.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectory.File.Tests.Unix.cs @@ -9,7 +9,7 @@ namespace System.Formats.Tar.Tests { public partial class TarFile_ExtractToDirectory_File_Tests : TarTestsBase { - [ConditionalFact(nameof(IsUnixButNotSuperUser))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotPrivilegedProcess))] public void Extract_SpecialFiles_Unix_Unelevated_ThrowsUnauthorizedAccess() { string originalFileName = GetTarFilePath(CompressionMethod.Uncompressed, TestTarFormat.ustar, "specialfiles"); diff --git a/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectoryAsync.File.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectoryAsync.File.Tests.Unix.cs index 47639642433e8..37205ff1548c4 100644 --- a/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectoryAsync.File.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarFile/TarFile.ExtractToDirectoryAsync.File.Tests.Unix.cs @@ -10,7 +10,7 @@ namespace System.Formats.Tar.Tests { public partial class TarFile_ExtractToDirectoryAsync_File_Tests : TarTestsBase { - [ConditionalFact(nameof(IsUnixButNotSuperUser))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotPrivilegedProcess))] public async Task Extract_SpecialFiles_Unix_Unelevated_ThrowsUnauthorizedAccess_Async() { using (TempDirectory root = new TempDirectory()) diff --git a/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFile.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFile.Tests.Unix.cs index a17bec1a92a84..cd78bbb6b5d3c 100644 --- a/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFile.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFile.Tests.Unix.cs @@ -9,8 +9,9 @@ namespace System.Formats.Tar.Tests { public partial class TarReader_TarEntry_ExtractToFile_Tests : TarTestsBase { - [PlatformSpecific(TestPlatforms.AnyUnix & ~TestPlatforms.tvOS)] // https://github.com/dotnet/runtime/issues/68360 - [ConditionalFact(nameof(IsUnixButNotSuperUser), nameof(IsNotLinuxBionic))] + [SkipOnPlatform(TestPlatforms.tvOS, "https://github.com/dotnet/runtime/issues/68360")] + [SkipOnPlatform(TestPlatforms.LinuxBionic, "Not supported on Bionic")] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotPrivilegedProcess))] public void SpecialFile_Unelevated_Throws() { using TempDirectory root = new TempDirectory(); diff --git a/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFileAsync.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFileAsync.Tests.Unix.cs index 07e9b6b673d40..38ae06f0652f0 100644 --- a/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFileAsync.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarReader/TarReader.TarEntry.ExtractToFileAsync.Tests.Unix.cs @@ -9,8 +9,9 @@ namespace System.Formats.Tar.Tests { public partial class TarReader_TarEntry_ExtractToFileAsync_Tests : TarTestsBase { - [PlatformSpecific(TestPlatforms.AnyUnix & ~TestPlatforms.tvOS)] // https://github.com/dotnet/runtime/issues/68360 - [ConditionalFact(nameof(IsUnixButNotSuperUser), nameof(IsNotLinuxBionic))] + [SkipOnPlatform(TestPlatforms.LinuxBionic, "Unsupported on Bionic")] + [SkipOnPlatform(TestPlatforms.tvOS, "https://github.com/dotnet/runtime/issues/68360")] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsNotPrivilegedProcess))] public async Task SpecialFile_Unelevated_Throws_Async() { using (TempDirectory root = new TempDirectory()) diff --git a/src/libraries/System.Formats.Tar/tests/TarTestsBase.cs b/src/libraries/System.Formats.Tar/tests/TarTestsBase.cs index 7a4aca955bf32..3363d27946395 100644 --- a/src/libraries/System.Formats.Tar/tests/TarTestsBase.cs +++ b/src/libraries/System.Formats.Tar/tests/TarTestsBase.cs @@ -12,6 +12,8 @@ namespace System.Formats.Tar.Tests { public abstract partial class TarTestsBase : FileCleanupTestBase { + protected static bool IsRemoteExecutorSupportedAndPrivilegedProcess => RemoteExecutor.IsSupported && PlatformDetection.IsPrivilegedProcess; + protected const string InitialEntryName = "InitialEntryName.ext"; protected readonly string ModifiedEntryName = "ModifiedEntryName.ext"; @@ -208,11 +210,6 @@ public enum TestTarFormat // GNU formatted files. Format used by GNU tar versions up to 1.13.25. gnu } - protected static bool IsRemoteExecutorSupportedAndOnUnixAndSuperUser => RemoteExecutor.IsSupported && PlatformDetection.IsUnixAndSuperUser; - - protected static bool IsUnixButNotSuperUser => !PlatformDetection.IsWindows && !PlatformDetection.IsSuperUser; - - protected static bool IsNotLinuxBionic => !PlatformDetection.IsLinuxBionic; protected TarTestsBase() { diff --git a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.File.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.File.Tests.Unix.cs index 5ca600f992f93..f9dfde9f3bacd 100644 --- a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.File.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.File.Tests.Unix.cs @@ -9,7 +9,7 @@ namespace System.Formats.Tar.Tests { public partial class TarWriter_WriteEntry_File_Tests : TarWriter_File_Base { - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] @@ -51,7 +51,7 @@ public void Add_Fifo(TarEntryFormat format) }, format.ToString(), new RemoteInvokeOptions { RunAsSudo = true }).Dispose(); } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] @@ -96,7 +96,7 @@ public void Add_BlockDevice(TarEntryFormat format) }, format.ToString(), new RemoteInvokeOptions { RunAsSudo = true }).Dispose(); } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] diff --git a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntryAsync.File.Tests.Unix.cs b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntryAsync.File.Tests.Unix.cs index ba4a5600ae81d..771f7ab2620e8 100644 --- a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntryAsync.File.Tests.Unix.cs +++ b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntryAsync.File.Tests.Unix.cs @@ -10,7 +10,7 @@ namespace System.Formats.Tar.Tests { public partial class TarWriter_WriteEntryAsync_File_Tests : TarWriter_File_Base { - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] @@ -55,7 +55,7 @@ public void Add_Fifo_Async(TarEntryFormat format) }, format.ToString(), new RemoteInvokeOptions { RunAsSudo = true }).Dispose(); } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] @@ -103,7 +103,7 @@ public void Add_BlockDevice_Async(TarEntryFormat format) }, format.ToString(), new RemoteInvokeOptions { RunAsSudo = true }).Dispose(); } - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(TarEntryFormat.Ustar)] [InlineData(TarEntryFormat.Pax)] [InlineData(TarEntryFormat.Gnu)] diff --git a/src/libraries/System.IO.FileSystem/tests/Directory/Delete.cs b/src/libraries/System.IO.FileSystem/tests/Directory/Delete.cs index f86cae23145af..5595984f7a1f7 100644 --- a/src/libraries/System.IO.FileSystem/tests/Directory/Delete.cs +++ b/src/libraries/System.IO.FileSystem/tests/Directory/Delete.cs @@ -12,7 +12,7 @@ public class Directory_Delete_str : FileSystemTest { static bool IsBindMountSupported => OperatingSystem.IsLinux() && !PlatformDetection.IsInContainer; - static bool IsBindMountSupportedAndOnUnixAndSuperUser => IsBindMountSupported && PlatformDetection.IsUnixAndSuperUser; + static bool IsBindMountSupportedAndPrivilegedProcess => IsBindMountSupported && PlatformDetection.IsPrivilegedProcess; static bool IsRemoteExecutorSupportedAndUsingNewNormalization => RemoteExecutor.IsSupported && UsingNewNormalization; @@ -218,7 +218,7 @@ public void UnixShouldBeAbleToDeleteHiddenDirectory() Assert.False(Directory.Exists(testDir)); } - [ConditionalFact(nameof(IsBindMountSupportedAndOnUnixAndSuperUser))] + [ConditionalFact(nameof(IsBindMountSupportedAndPrivilegedProcess))] [OuterLoop("Needs sudo access")] [PlatformSpecific(TestPlatforms.Linux)] public void Unix_NotFoundDirectory_ReadOnlyVolume() diff --git a/src/libraries/System.IO.FileSystem/tests/File/Delete.cs b/src/libraries/System.IO.FileSystem/tests/File/Delete.cs index e3228140b82d3..59b381e4b06d6 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/Delete.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/Delete.cs @@ -10,7 +10,7 @@ public class File_Delete : FileSystemTest { static bool IsBindMountSupported => OperatingSystem.IsLinux() && !PlatformDetection.IsInContainer; - private static bool IsBindMountSupportedAndOnUnixAndSuperUser => IsBindMountSupported && PlatformDetection.IsUnixAndSuperUser; + private static bool IsBindMountSupportedAndPrivilegedProcess => IsBindMountSupported && PlatformDetection.IsPrivilegedProcess; protected virtual void Delete(string path) { @@ -116,7 +116,7 @@ public void NonExistentPath_Throws_DirectoryNotFoundException() #region PlatformSpecific - [ConditionalFact(nameof(IsBindMountSupportedAndOnUnixAndSuperUser))] + [ConditionalFact(nameof(IsBindMountSupportedAndPrivilegedProcess))] [OuterLoop("Needs sudo access")] [PlatformSpecific(TestPlatforms.Linux)] public void Unix_NonExistentPath_ReadOnlyVolume() @@ -127,7 +127,7 @@ public void Unix_NonExistentPath_ReadOnlyVolume() }); } - [ConditionalFact(nameof(IsBindMountSupportedAndOnUnixAndSuperUser))] + [ConditionalFact(nameof(IsBindMountSupportedAndPrivilegedProcess))] [OuterLoop("Needs sudo access")] [PlatformSpecific(TestPlatforms.Linux)] public void Unix_ExistingDirectory_ReadOnlyVolume() diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytes.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytes.cs index b6e6c1f147613..0f5ecbec91782 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytes.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytes.cs @@ -83,7 +83,7 @@ public void OpenFile_ThrowsIOException() /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public void WriteToReadOnlyFile() @@ -93,8 +93,7 @@ public void WriteToReadOnlyFile() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { File.WriteAllBytes(path, "text"u8.ToArray()); Assert.Equal("text"u8.ToArray(), File.ReadAllBytes(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytesAsync.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytesAsync.cs index fca2d0d439b63..62772f2ee1e86 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytesAsync.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllBytesAsync.cs @@ -94,7 +94,7 @@ public async Task OpenFile_ThrowsIOExceptionAsync() /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public async Task WriteToReadOnlyFileAsync() @@ -104,8 +104,7 @@ public async Task WriteToReadOnlyFileAsync() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { await File.WriteAllBytesAsync(path, "text"u8.ToArray()); Assert.Equal("text"u8.ToArray(), await File.ReadAllBytesAsync(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLines.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLines.cs index bbd5ceeed4c25..961bb489f8fcc 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLines.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLines.cs @@ -115,7 +115,7 @@ public void Read_FileNotFound() /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public void WriteToReadOnlyFile() @@ -125,8 +125,7 @@ public void WriteToReadOnlyFile() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { Write(path, new string[] { "text" }); Assert.Equal(new string[] { "text" }, Read(path)); @@ -303,7 +302,7 @@ public void Read_FileNotFound() /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public void WriteToReadOnlyFile() @@ -313,8 +312,7 @@ public void WriteToReadOnlyFile() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { Write(path, new string[] { "text" }); Assert.Equal(new string[] { "text" }, Read(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLinesAsync.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLinesAsync.cs index 17c6e565bc79d..441771f05675e 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLinesAsync.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllLinesAsync.cs @@ -110,7 +110,7 @@ public Task Read_FileNotFound() => /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public async Task WriteToReadOnlyFile() @@ -120,8 +120,7 @@ public async Task WriteToReadOnlyFile() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { await WriteAsync(path, new string[] { "text" }); Assert.Equal(new string[] { "text" }, await ReadAsync(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllText.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllText.cs index fd4abc7b60166..749877010e6c1 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllText.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllText.cs @@ -128,7 +128,7 @@ public void Read_FileNotFound() /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public void WriteToReadOnlyFile() @@ -138,8 +138,7 @@ public void WriteToReadOnlyFile() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { Write(path, "text"); Assert.Equal("text", Read(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllTextAsync.cs b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllTextAsync.cs index 0c9d7cb699c45..09825f49f5c26 100644 --- a/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllTextAsync.cs +++ b/src/libraries/System.IO.FileSystem/tests/File/ReadWriteAllTextAsync.cs @@ -119,7 +119,7 @@ public Task Read_FileNotFoundAsync() => /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// [Fact] public async Task WriteToReadOnlyFileAsync() @@ -129,8 +129,7 @@ public async Task WriteToReadOnlyFileAsync() File.SetAttributes(path, FileAttributes.ReadOnly); try { - // Operation succeeds when being run by the Unix superuser - if (PlatformDetection.IsSuperUser) + if (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess) { await WriteAsync(path, "text"); Assert.Equal("text", await ReadAsync(path)); diff --git a/src/libraries/System.IO.FileSystem/tests/FileStream/FileStreamConformanceTests.Windows.cs b/src/libraries/System.IO.FileSystem/tests/FileStream/FileStreamConformanceTests.Windows.cs index c3fea537d8c34..5f78df2e58c41 100644 --- a/src/libraries/System.IO.FileSystem/tests/FileStream/FileStreamConformanceTests.Windows.cs +++ b/src/libraries/System.IO.FileSystem/tests/FileStream/FileStreamConformanceTests.Windows.cs @@ -75,7 +75,7 @@ protected override string GetTestFilePath(int? index = null, [CallerMemberName] private static extern bool GetVolumeNameForVolumeMountPoint(string volumeName, StringBuilder uniqueVolumeName, int uniqueNameBufferCapacity); } - [PlatformSpecific(TestPlatforms.Windows)] // the test setup is Windows-specifc + [PlatformSpecific(TestPlatforms.Windows)] // the test setup is Windows-specific [Collection(nameof(DisableParallelization))] // don't run in parallel, as file sharing logic is not thread-safe [OuterLoop("Requires admin privileges to create a file share")] [ConditionalClass(typeof(UncFilePathFileStreamStandaloneConformanceTests), nameof(CanShareFiles))] @@ -85,7 +85,7 @@ public class UncFilePathFileStreamStandaloneConformanceTests : UnbufferedAsyncFi private static Lazy _canShareFiles = new Lazy(() => { - if (!PlatformDetection.IsWindowsAndElevated) + if (!PlatformDetection.IsPrivilegedProcess) { return false; } diff --git a/src/libraries/System.IO.FileSystem/tests/RandomAccess/GetLength.cs b/src/libraries/System.IO.FileSystem/tests/RandomAccess/GetLength.cs index e4b482c675db4..5e1017cd333e4 100644 --- a/src/libraries/System.IO.FileSystem/tests/RandomAccess/GetLength.cs +++ b/src/libraries/System.IO.FileSystem/tests/RandomAccess/GetLength.cs @@ -37,7 +37,8 @@ public void ReturnsExactSizeForNonEmptyFiles(FileOptions options) } } - [ConditionalTheory(typeof(PlatformDetection), nameof(PlatformDetection.IsWindowsAndElevated))] + [PlatformSpecific(TestPlatforms.Windows)] + [ConditionalTheory(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] [MemberData(nameof(GetSyncAsyncOptions))] public void ReturnsActualLengthForDevices(FileOptions options) { diff --git a/src/libraries/System.IO.MemoryMappedFiles/tests/MemoryMappedFile.CreateFromFile.Tests.cs b/src/libraries/System.IO.MemoryMappedFiles/tests/MemoryMappedFile.CreateFromFile.Tests.cs index 8a93056692f5b..4e06fb078c8ef 100644 --- a/src/libraries/System.IO.MemoryMappedFiles/tests/MemoryMappedFile.CreateFromFile.Tests.cs +++ b/src/libraries/System.IO.MemoryMappedFiles/tests/MemoryMappedFile.CreateFromFile.Tests.cs @@ -672,9 +672,13 @@ public void FileNotOpenedForExecute(MemoryMappedFileAccess access) /// /// On Unix, modifying a file that is ReadOnly will fail under normal permissions. /// If the test is being run under the superuser, however, modification of a ReadOnly - /// file is allowed. + /// file is allowed. On Windows, modifying a file that is ReadOnly will always fail. /// - private void WriteToReadOnlyFile(MemoryMappedFileAccess access, bool succeeds) + [Theory] + [InlineData(MemoryMappedFileAccess.Read, true)] + [InlineData(MemoryMappedFileAccess.ReadWrite, false)] + [InlineData(MemoryMappedFileAccess.CopyOnWrite, false)] + public void WriteToReadOnlyFile(MemoryMappedFileAccess access, bool shouldSucceedWithoutPrivilege) { const int Capacity = 4096; using (TempFile file = new TempFile(GetTestFilePath(), Capacity)) @@ -683,11 +687,15 @@ private void WriteToReadOnlyFile(MemoryMappedFileAccess access, bool succeeds) File.SetAttributes(file.Path, FileAttributes.ReadOnly); try { - if (succeeds) + if (shouldSucceedWithoutPrivilege || (PlatformDetection.IsNotWindows && PlatformDetection.IsPrivilegedProcess)) + { using (MemoryMappedFile mmf = MemoryMappedFile.CreateFromFile(file.Path, FileMode.Open, null, Capacity, access)) ValidateMemoryMappedFile(mmf, Capacity, MemoryMappedFileAccess.Read); + } else + { Assert.Throws(() => MemoryMappedFile.CreateFromFile(file.Path, FileMode.Open, null, Capacity, access)); + } } finally { @@ -696,21 +704,6 @@ private void WriteToReadOnlyFile(MemoryMappedFileAccess access, bool succeeds) } } - [Theory] - [InlineData(MemoryMappedFileAccess.Read)] - [InlineData(MemoryMappedFileAccess.ReadWrite)] - public void WriteToReadOnlyFile_ReadWrite(MemoryMappedFileAccess access) - { - WriteToReadOnlyFile(access, access == MemoryMappedFileAccess.Read || - PlatformDetection.IsSuperUser); - } - - [Fact] - public void WriteToReadOnlyFile_CopyOnWrite() - { - WriteToReadOnlyFile(MemoryMappedFileAccess.CopyOnWrite, PlatformDetection.IsSuperUser); - } - /// /// Test to ensure that leaveOpen is appropriately respected, either leaving the FileStream open /// or closing it on disposal. diff --git a/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.CurrentUserOnly.Windows.cs b/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.CurrentUserOnly.Windows.cs index e7b08aacebf46..33ebc1c5e33c3 100644 --- a/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.CurrentUserOnly.Windows.cs +++ b/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.CurrentUserOnly.Windows.cs @@ -120,7 +120,8 @@ public void RunImpersonated(Action action) /// public class NamedPipeTest_CurrentUserOnly_Windows : IClassFixture { - public static bool IsAdminOnSupportedWindowsVersions => PlatformDetection.IsWindowsAndElevated + public static bool IsSupportedWindowsVersionAndPrivilegedProcess => PlatformDetection.IsPrivilegedProcess + && PlatformDetection.IsWindows && !PlatformDetection.IsWindows7 && !PlatformDetection.IsWindowsNanoServer && !PlatformDetection.IsWindowsServerCore; @@ -132,8 +133,8 @@ public NamedPipeTest_CurrentUserOnly_Windows(TestAccountImpersonator testAccount _testAccountImpersonator = testAccountImpersonator; } - [OuterLoop] - [ConditionalFact(nameof(IsAdminOnSupportedWindowsVersions))] + [OuterLoop("Requires admin privileges")] + [ConditionalFact(nameof(IsSupportedWindowsVersionAndPrivilegedProcess))] public async Task Connection_UnderDifferentUsers_CurrentUserOnlyOnServer_InvalidClientConnectionAttempts_DoNotBlockSuccessfulClient() { string name = PipeStreamConformanceTests.GetUniquePipeName(); @@ -167,8 +168,7 @@ public async Task Connection_UnderDifferentUsers_CurrentUserOnlyOnServer_Invalid Volatile.Write(ref invalidClientShouldStop, true); } - [OuterLoop] - [ConditionalTheory(nameof(IsAdminOnSupportedWindowsVersions))] + [ConditionalTheory(nameof(IsSupportedWindowsVersionAndPrivilegedProcess))] [InlineData(PipeOptions.None, PipeOptions.None, PipeDirection.InOut)] // Fails even without CurrentUserOnly, because under the default pipe ACL, other users are denied Write access, and client is requesting PipeDirection.InOut [InlineData(PipeOptions.None, PipeOptions.CurrentUserOnly, PipeDirection.In)] [InlineData(PipeOptions.None, PipeOptions.CurrentUserOnly, PipeDirection.InOut)] @@ -209,8 +209,7 @@ public void Connection_UnderDifferentUsers_BehavesAsExpected( } } - [OuterLoop] - [ConditionalTheory(nameof(IsAdminOnSupportedWindowsVersions))] + [ConditionalTheory(nameof(IsSupportedWindowsVersionAndPrivilegedProcess))] [InlineData(false)] [InlineData(true)] public void Allow_Connection_UnderDifferentUsers_ForClientReading(bool useTimeSpan) diff --git a/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.RunAsClient.Unix.cs b/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.RunAsClient.Unix.cs index 9c93d00b833a6..150ec5e0df5dd 100644 --- a/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.RunAsClient.Unix.cs +++ b/src/libraries/System.IO.Pipes/tests/NamedPipeTests/NamedPipeTest.RunAsClient.Unix.cs @@ -19,10 +19,9 @@ public class NamedPipeTest_RunAsClient [DllImport("libc", SetLastError = true)] internal static extern unsafe uint geteuid(); - public static bool IsSuperUserAndRemoteExecutorSupported => Environment.IsPrivilegedProcess && RemoteExecutor.IsSupported; + public static bool IsRemoteExecutorSupportedAndPrivilegedProcess => RemoteExecutor.IsSupported && PlatformDetection.IsPrivilegedProcess; - [ConditionalFact(nameof(IsSuperUserAndRemoteExecutorSupported))] - [PlatformSpecific(TestPlatforms.AnyUnix)] // Uses P/Invokes + [ConditionalFact(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [ActiveIssue("https://github.com/dotnet/runtime/issues/0")] public void RunAsClient_Unix() { @@ -38,7 +37,7 @@ private static void ServerConnectAsId(string pipeName, string pairIDString) using (var outbound = new NamedPipeServerStream(pipeName, PipeDirection.Out)) using (var handle = RemoteExecutor.Invoke(new Action(ClientConnectAsID), pipeName, pairIDString)) { - // Connect as the unpriveleged user, but RunAsClient as the superuser + // Connect as the unprivileged user, but RunAsClient as the superuser outbound.WaitForConnection(); Assert.NotEqual(-1, seteuid(0)); diff --git a/src/libraries/System.Net.Ping/tests/FunctionalTests/PingTest.cs b/src/libraries/System.Net.Ping/tests/FunctionalTests/PingTest.cs index 754a26a60fd4e..43b4bb3be6d08 100644 --- a/src/libraries/System.Net.Ping/tests/FunctionalTests/PingTest.cs +++ b/src/libraries/System.Net.Ping/tests/FunctionalTests/PingTest.cs @@ -793,13 +793,13 @@ public async Task Ping_TimedOut_TAP_Success() Assert.Equal(IPStatus.TimedOut, reply.Status); } - private static bool IsRemoteExecutorSupportedAndOnUnixAndSuperUser => RemoteExecutor.IsSupported && PlatformDetection.IsUnixAndSuperUser; + private static bool IsRemoteExecutorSupportedAndPrivilegedProcess => RemoteExecutor.IsSupported && PlatformDetection.IsPrivilegedProcess; [PlatformSpecific(TestPlatforms.AnyUnix)] - [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndOnUnixAndSuperUser))] + [ConditionalTheory(nameof(IsRemoteExecutorSupportedAndPrivilegedProcess))] [InlineData(AddressFamily.InterNetwork)] [InlineData(AddressFamily.InterNetworkV6)] - [OuterLoop] // Depends on sudo + [OuterLoop("Requires sudo access")] public void SendPingWithIPAddressAndTimeoutAndBufferAndPingOptions_ElevatedUnix(AddressFamily addressFamily) { IPAddress localIpAddress = TestSettings.GetLocalIPAddress(addressFamily); diff --git a/src/libraries/System.Runtime.Extensions/tests/System/Environment.GetEnvironmentVariable.cs b/src/libraries/System.Runtime.Extensions/tests/System/Environment.GetEnvironmentVariable.cs index 854862bd7f370..125b274b4b2ae 100644 --- a/src/libraries/System.Runtime.Extensions/tests/System/Environment.GetEnvironmentVariable.cs +++ b/src/libraries/System.Runtime.Extensions/tests/System/Environment.GetEnvironmentVariable.cs @@ -217,7 +217,8 @@ public void EnumerateYieldsDictionaryEntryFromIEnumerable_SpecificTarget(Environ [MemberData(nameof(EnvironmentTests.EnvironmentVariableTargets), MemberType = typeof(EnvironmentTests))] public void EnumerateEnvironmentVariables(EnvironmentVariableTarget target) { - bool lookForSetValue = (target == EnvironmentVariableTarget.Process) || PlatformDetection.IsWindowsAndElevated; + bool lookForSetValue = (target == EnvironmentVariableTarget.Process) + || (PlatformDetection.IsWindows && PlatformDetection.IsPrivilegedProcess); // [ActiveIssue("https://github.com/dotnet/runtime/issues/30566")] if (PlatformDetection.IsWindowsNanoServer && target == EnvironmentVariableTarget.User) diff --git a/src/libraries/System.Runtime.Extensions/tests/System/Environment.IsPrivilegedProcess.cs b/src/libraries/System.Runtime.Extensions/tests/System/Environment.IsPrivilegedProcess.cs index 55096f3ad2ab9..0dba40816cb6d 100644 --- a/src/libraries/System.Runtime.Extensions/tests/System/Environment.IsPrivilegedProcess.cs +++ b/src/libraries/System.Runtime.Extensions/tests/System/Environment.IsPrivilegedProcess.cs @@ -9,7 +9,6 @@ namespace System.Tests public class Environment_IsPrivilegedProcess { [Fact] - [SkipOnPlatform(TestPlatforms.Browser, "Browser doesn't support geteuid")] public void TestIsPrivilegedProcess() { Assert.Equal(AdminHelpers.IsProcessElevated(), Environment.IsPrivilegedProcess); diff --git a/src/libraries/System.Runtime.Extensions/tests/System/Environment.SetEnvironmentVariable.cs b/src/libraries/System.Runtime.Extensions/tests/System/Environment.SetEnvironmentVariable.cs index 2d43aed654f84..4554ccccafb2e 100644 --- a/src/libraries/System.Runtime.Extensions/tests/System/Environment.SetEnvironmentVariable.cs +++ b/src/libraries/System.Runtime.Extensions/tests/System/Environment.SetEnvironmentVariable.cs @@ -160,7 +160,7 @@ private static void ExecuteAgainstTarget( shouldCleanUp = false; Assert.True(target == EnvironmentVariableTarget.Machine, "only machine target should have access issues"); Assert.True(PlatformDetection.IsWindows, "and it should be Windows"); - Assert.False(PlatformDetection.IsWindowsAndElevated, "and we shouldn't be elevated"); + Assert.False(PlatformDetection.IsPrivilegedProcess, "and we shouldn't be elevated"); } finally { diff --git a/src/libraries/System.Security.Cryptography.Cng/tests/SymmetricCngTestHelpers.cs b/src/libraries/System.Security.Cryptography.Cng/tests/SymmetricCngTestHelpers.cs index fae33a6349850..f64f60362520e 100644 --- a/src/libraries/System.Security.Cryptography.Cng/tests/SymmetricCngTestHelpers.cs +++ b/src/libraries/System.Security.Cryptography.Cng/tests/SymmetricCngTestHelpers.cs @@ -373,7 +373,7 @@ internal static void VerifyMismatchAlgorithmFails( // in the Microsoft Software KSP internal static bool SupportsPersistedSymmetricKeys => PlatformDetection.IsWindows8xOrLater; - internal static bool IsAdministrator => PlatformDetection.IsWindowsAndElevated; + internal static bool IsAdministrator => PlatformDetection.IsWindows && PlatformDetection.IsPrivilegedProcess; internal static void AssertTransformsEqual(byte[] plainTextBytes, ICryptoTransform decryptor, byte[] encryptedBytes) { diff --git a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceBaseTests.cs b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceBaseTests.cs index 03bbb7cbae523..2d097c766c332 100644 --- a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceBaseTests.cs +++ b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceBaseTests.cs @@ -17,10 +17,8 @@ public class ServiceBaseTests : IDisposable private const int connectionTimeout = 30000; private readonly TestServiceProvider _testService; - private static readonly Lazy s_isElevated = new Lazy(() => AdminHelpers.IsProcessElevated()); - protected static bool IsProcessElevated => s_isElevated.Value; - protected static bool IsElevatedAndSupportsEventLogs => IsProcessElevated && PlatformDetection.IsNotWindowsNanoServer; - protected static bool IsElevatedAndWindows10OrLater => IsProcessElevated && PlatformDetection.IsWindows10OrLater; + protected static bool IsElevatedAndSupportsEventLogs => PlatformDetection.IsPrivilegedProcess && PlatformDetection.IsNotWindowsNanoServer; + protected static bool IsElevatedAndWindows10OrLater => PlatformDetection.IsPrivilegedProcess && PlatformDetection.IsWindows10OrLater; private bool _disposed; @@ -73,7 +71,7 @@ private void Cleanup() } #if NETCOREAPP - [ConditionalTheory(nameof(IsProcessElevated))] + [ConditionalTheory(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] [InlineData(-2)] [InlineData((long)int.MaxValue + 1)] public void RequestAdditionalTime_Throws_ArgumentOutOfRangeException(long milliseconds) @@ -84,7 +82,7 @@ public void RequestAdditionalTime_Throws_ArgumentOutOfRangeException(long millis } #endif - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestOnStartThenStop() { ServiceController controller = ConnectToServer(); @@ -120,7 +118,7 @@ public void TestOnStartWithArgsThenStop() controller.WaitForStatus(ServiceControllerStatus.Stopped); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestOnPauseThenStop() { ServiceController controller = ConnectToServer(); @@ -134,7 +132,7 @@ public void TestOnPauseThenStop() controller.WaitForStatus(ServiceControllerStatus.Stopped); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestOnPauseAndContinueThenStop() { ServiceController controller = ConnectToServer(); @@ -152,7 +150,7 @@ public void TestOnPauseAndContinueThenStop() controller.WaitForStatus(ServiceControllerStatus.Stopped); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestOnExecuteCustomCommand() { if (PlatformDetection.IsWindowsServerCore) @@ -179,7 +177,7 @@ public void TestOnExecuteCustomCommand() controller.WaitForStatus(ServiceControllerStatus.Stopped); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void TestOnContinueBeforePause() { ServiceController controller = ConnectToServer(); @@ -211,7 +209,7 @@ public void LogWritten_AutoLog_False() testService.DeleteTestServices(); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] [SkipOnTargetFramework(TargetFrameworkMonikers.NetFramework, ".NET Framework receives the Connected Byte Code after the Exception Thrown Byte Code")] public void PropagateExceptionFromOnStart() { diff --git a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.cs b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.cs index 8a73b2dc41ddd..44be0445dd1d9 100644 --- a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.cs +++ b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.cs @@ -12,9 +12,6 @@ public partial class ServiceControllerTests : IDisposable private const int connectionTimeout = 30000; private readonly TestServiceProvider _testService; - private static readonly Lazy s_isElevated = new Lazy(() => AdminHelpers.IsProcessElevated()); - protected static bool IsProcessElevated => s_isElevated.Value; - private bool _disposed; public ServiceControllerTests() @@ -30,28 +27,28 @@ private void AssertExpectedProperties(ServiceController testServiceController) Assert.Equal(ServiceType.Win32OwnProcess, testServiceController.ServiceType); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ConstructWithServiceName() { var controller = new ServiceController(_testService.TestServiceName); AssertExpectedProperties(controller); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ConstructWithServiceName_ToUpper() { var controller = new ServiceController(_testService.TestServiceName.ToUpperInvariant()); AssertExpectedProperties(controller); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ConstructWithDisplayName() { var controller = new ServiceController(_testService.TestServiceDisplayName); AssertExpectedProperties(controller); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ConstructWithMachineName() { var controller = new ServiceController(_testService.TestServiceName, _testService.TestMachineName); @@ -60,7 +57,7 @@ public void ConstructWithMachineName() AssertExtensions.Throws(null, () => { new ServiceController(_testService.TestServiceName, ""); }); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ControlCapabilities() { var controller = new ServiceController(_testService.TestServiceName); @@ -71,14 +68,14 @@ public void ControlCapabilities() Assert.True(controller.CanShutdown); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Start_NullArg_ThrowsArgumentNullException() { var controller = new ServiceController(_testService.TestServiceName); Assert.Throws(() => controller.Start(new string[] { null } )); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void StopAndStart() { var controller = new ServiceController(_testService.TestServiceName); @@ -97,7 +94,7 @@ public void StopAndStart() } } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void PauseAndContinue() { string serviceName = _testService.TestServiceName; @@ -128,7 +125,7 @@ public void PauseAndContinue() Assert.Equal(ServiceControllerStatus.Stopped, controller.Status); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void GetServices_FindSelf() { bool foundTestService = false; @@ -145,7 +142,7 @@ public void GetServices_FindSelf() Assert.True(foundTestService, "Test service was not enumerated with all services"); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Dependencies() { var controller = new ServiceController(_testService.TestServiceName); @@ -160,7 +157,7 @@ public void Dependencies() Assert.Equal(prerequisiteServiceController.DependentServices[0].ServiceName, controller.ServiceName); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void ServicesStartMode() { var controller = new ServiceController(_testService.TestServiceName); diff --git a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.netcoreapp.cs b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.netcoreapp.cs index 687fd2654b533..0172fcb0bbf1c 100644 --- a/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.netcoreapp.cs +++ b/src/libraries/System.ServiceProcess.ServiceController/tests/ServiceControllerTests.netcoreapp.cs @@ -8,7 +8,7 @@ namespace System.ServiceProcess.Tests [OuterLoop(/* Modifies machine state */)] public partial class ServiceControllerTests : IDisposable { - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Stop_FalseArg_WithDependentServices_ThrowsInvalidOperationException() { var controller = new ServiceController(_testService.TestServiceName); @@ -23,7 +23,7 @@ public void Stop_FalseArg_WithDependentServices_ThrowsInvalidOperationException( Assert.Throws(() => prerequisiteServiceController.Stop(stopDependentServices: false)); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void Stop_TrueArg_WithDependentServices_StopsTheServiceAndItsDependents() { var controller = new ServiceController(_testService.TestServiceName); @@ -36,7 +36,7 @@ public void Stop_TrueArg_WithDependentServices_StopsTheServiceAndItsDependents() Assert.All(controller.DependentServices, service => Assert.Equal(ServiceControllerStatus.Stopped, service.Status)); } - [ConditionalFact(nameof(IsProcessElevated))] + [ConditionalFact(typeof(PlatformDetection), nameof(PlatformDetection.IsPrivilegedProcess))] public void StopTheServiceAndItsDependentsManually() { var controller = new ServiceController(_testService.TestServiceName);