Skip to content

Commit dcd8de5

Browse files
committed
fix defender not disabling
1 parent c7dea06 commit dcd8de5

File tree

2 files changed

+93
-56
lines changed

2 files changed

+93
-56
lines changed

src/lib/core/services/win_registry_service.dart

Lines changed: 31 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,9 @@ class WinRegistryService {
156156
path: r'SYSTEM\ControlSet001\Services',
157157
);
158158
try {
159-
return key.subkeyNames.where((final String e) => e.startsWith(subkey)).toList();
159+
return key.subkeyNames
160+
.where((final String e) => e.startsWith(subkey))
161+
.toList();
160162
} finally {
161163
key.close();
162164
}
@@ -238,7 +240,20 @@ class WinRegistryService {
238240
String name,
239241
T value, {
240242
int retryCount = 0,
243+
bool useTrustedInstaller = false,
241244
}) async {
245+
if (useTrustedInstaller) {
246+
return TrustedInstallerServiceImpl().executeWithTrustedInstaller(
247+
() async => writeRegistryValue<T>(
248+
key,
249+
path,
250+
name,
251+
value,
252+
retryCount: retryCount,
253+
),
254+
);
255+
}
256+
242257
final shouldClose = key != WinRegistryService.currentUser;
243258

244259
try {
@@ -253,7 +268,7 @@ class WinRegistryService {
253268
'$tag(writeRegistryValue): Unsupported type: ${value.runtimeType}',
254269
),
255270
};
256-
271+
257272
final RegistryKey subKey = key.createKey(path);
258273
try {
259274
subKey.createValue(registryValue);
@@ -340,7 +355,14 @@ class WinRegistryService {
340355
String path,
341356
String name, {
342357
int retryCount = 0,
358+
bool useTrustedInstaller = false,
343359
}) async {
360+
if (useTrustedInstaller) {
361+
return TrustedInstallerServiceImpl().executeWithTrustedInstaller(
362+
() async => deleteValue(key, path, name, retryCount: retryCount),
363+
);
364+
}
365+
344366
try {
345367
final RegistryKey subKey = key.createKey(path);
346368
try {
@@ -395,7 +417,14 @@ class WinRegistryService {
395417
RegistryKey key,
396418
String path, {
397419
int retryCount = 0,
420+
bool useTrustedInstaller = false,
398421
}) async {
422+
if (useTrustedInstaller) {
423+
return TrustedInstallerServiceImpl().executeWithTrustedInstaller(
424+
() async => deleteKey(key, path, retryCount: retryCount),
425+
);
426+
}
427+
399428
try {
400429
key.deleteKey(path, recursive: true);
401430
logger.i('$tag(deleteKey): $path');

src/lib/features/tweaks/security/security_service.dart

Lines changed: 62 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -325,68 +325,76 @@ class SecurityServiceImpl implements SecurityService {
325325
@override
326326
Future<void> disableDefender() async {
327327
try {
328-
await WinPackageService.downloadPackage(WinPackageType.defenderRemoval);
329-
330-
await Future.wait([
331-
WinRegistryService.writeRegistryValue(
332-
Registry.localMachine,
333-
r'SOFTWARE\Policies\Microsoft\Windows Defender',
334-
'DisableAntiSpyware',
335-
1,
336-
),
337-
WinRegistryService.writeRegistryValue(
338-
Registry.localMachine,
339-
r'SOFTWARE\Policies\Microsoft\Windows Defender',
340-
'DisableAntiVirus',
341-
1,
342-
),
343-
WinRegistryService.writeRegistryValue(
344-
Registry.localMachine,
345-
r'SOFTWARE\Policies\Microsoft\Windows Defender\Real-Time Protection',
346-
'DisableRealtimeMonitoring',
347-
1,
348-
),
349-
]);
350-
351-
await runPSCommand(
352-
r'& $env:SystemRoot\System32\gpupdate.exe /Target:Computer /Force',
328+
final String packagePath = await WinPackageService.downloadPackage(
329+
WinPackageType.defenderRemoval,
353330
);
354331

355-
if (File(_mpCmdRunString).existsSync()) {
332+
/// Internal helper
333+
Future<void> applyPolicyWrites() async {
334+
await Future.wait([
335+
WinRegistryService.writeRegistryValue(
336+
Registry.localMachine,
337+
r'SOFTWARE\Policies\Microsoft\Windows Defender',
338+
'DisableAntiSpyware',
339+
1,
340+
),
341+
WinRegistryService.writeRegistryValue(
342+
Registry.localMachine,
343+
r'SOFTWARE\Policies\Microsoft\Windows Defender',
344+
'DisableAntiVirus',
345+
1,
346+
),
347+
WinRegistryService.writeRegistryValue(
348+
Registry.localMachine,
349+
r'SOFTWARE\Policies\Microsoft\Windows Defender\Real-Time Protection',
350+
'DisableRealtimeMonitoring',
351+
1,
352+
),
353+
]);
356354
await runPSCommand(
357-
'Start-Process -FilePath "$_mpCmdRunString" -ArgumentList "-RemoveDefinitions -All" -NoNewWindow -Wait',
355+
r'& $env:SystemRoot\System32\gpupdate.exe /Target:Computer /Force',
358356
);
357+
if (File(_mpCmdRunString).existsSync()) {
358+
await runPSCommand(
359+
'Start-Process -FilePath "$_mpCmdRunString" -ArgumentList "-RemoveDefinitions -All" -NoNewWindow -Wait',
360+
);
361+
}
359362
}
360363

361-
await Future.wait([
362-
WinRegistryService.writeRegistryValue(
363-
Registry.localMachine,
364-
r'SOFTWARE\Microsoft\Windows Defender',
365-
'DisableAntiSpyware',
366-
1,
367-
),
368-
WinRegistryService.writeRegistryValue(
369-
Registry.localMachine,
370-
r'SOFTWARE\Microsoft\Windows Defender',
371-
'DisableAntiVirus',
372-
1,
373-
),
374-
WinRegistryService.writeRegistryValue(
375-
Registry.localMachine,
376-
r'System\ControlSet001\Services\MDCoreSvc',
377-
'Start',
378-
4,
379-
),
380-
WinRegistryService.deleteValue(
381-
Registry.localMachine,
382-
r'SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce',
383-
'RevisionEnableDefenderCMD',
384-
),
385-
]);
364+
await applyPolicyWrites();
386365

387-
final String packagePath = await WinPackageService.downloadPackage(
388-
WinPackageType.defenderRemoval,
366+
await WinRegistryService.writeRegistryValue(
367+
Registry.localMachine,
368+
r'SOFTWARE\Microsoft\Windows Defender',
369+
'DisableAntiSpyware',
370+
1,
371+
useTrustedInstaller: true,
389372
);
373+
await WinRegistryService.writeRegistryValue(
374+
Registry.localMachine,
375+
r'SOFTWARE\Microsoft\Windows Defender',
376+
'DisableAntiVirus',
377+
1,
378+
useTrustedInstaller: true,
379+
);
380+
381+
// WORKAROUND: Force a second policy update after modifying the core Defender registry keys. After the January 2026 security updates, 'gpupdate' automatically removes 'DisableAntiSpyware' in the Policies path, when security intelligence updates is installed. Re-applying policies after modifying the core Defender registries ensures both locations are synchronized, resolving permission errors that occur when trying to disable Defender services directly.
382+
await applyPolicyWrites();
383+
384+
await WinRegistryService.writeRegistryValue(
385+
Registry.localMachine,
386+
r'System\ControlSet001\Services\MDCoreSvc',
387+
'Start',
388+
4,
389+
useTrustedInstaller: true,
390+
);
391+
392+
await WinRegistryService.deleteValue(
393+
Registry.localMachine,
394+
r'SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce',
395+
'RevisionEnableDefenderCMD',
396+
);
397+
390398
await WinPackageService.installPackage(packagePath);
391399
} on Exception catch (e) {
392400
throw DefenderOperationException('Failed to disable Windows Defender', e);

0 commit comments

Comments
 (0)