AVG charges infection in Windows service application if add command to Windows Firewall is present
I Have an application in which it is a Windows Service (a Service in Windows) and the room I am trying to add a method to add it to the Firewall the Windows automatically.
Like this:
procedure AddInFirewall(cApplicationName, cEntryName: string);
var
cAppName: string;
begin
if Trim(cApplicationName) = '' then
cAppName := Application.ExeName
else
cAppName := cApplicationName;
if Trim(cEntryName) = '' then
begin
cEntryName := ExtractFileName(cAppName);
end;
WinExec(PAnsiChar(AnsiString('netsh firewall delete allowedprogram ' + cAppName)), SW_HIDE);
WinExec(PAnsiChar(AnsiString('netsh advfirewall firewall delete rule name="'+cEntryName+'" program="'+cAppName+'"')), SW_HIDE);
WinExec(PAnsiChar(AnsiString('netsh firewall add allowedprogram '+cAppName+' "'+cEntryName+'" ENABLE')), SW_HIDE);
WinExec(PAnsiChar(AnsiString('netsh advfirewall firewall add rule name="'+cEntryName+'" dir=in action=allow program="'+cAppName+'" enable=yes')), SW_HIDE);
end;
procedure TServerModule.DataModuleCreate(Sender: TObject);
begin
AddInFirewall(Application.ExeName, 'MeuServico');
FClients := TList.Create;
StartService;
end;
However, the Blessed of AVG Antivirus is complaining that it is infected with:
Win32 / DH{IFVEIS4}
I just comment the lines with WinExec
and compile again that he no longer complains of infection.
How can I solve such a problem?
2 answers
the question itself has already been answered in the other answer so I will try to just supplement it.
This code snippet WinExec(....)
is quite well known( eaten/beaten) by antiviruses because it is doing this in the background, the antivirus is right to consider its application as a malware.
Try to approach this in some other way, such as using the APIs of the Windows Firewall, more precisely using the interfaces INetFwPolicy2
e FWRule
.
See the following example that will try to add a rule to an application (Note: privileges are required to run the application):
program Project1;
{$APPTYPE CONSOLE}
uses
SysUtils,
ActiveX,
ComObj;
// Este código adiciona uma regra de aplicativo usando as APIs do Windows Firewall.
Procedure AddApplicationRule;
Const
NET_FW_ACTION_ALLOW = 1;
NET_FW_IP_PROTOCOL_TCP = 6;
var
CurrentProfiles : OleVariant;
fwPolicy2 : OleVariant;
RulesObject : OleVariant;
NewRule : OleVariant;
begin
// Cria o objeto que permite acessar a política de Firewall
fwPolicy2 := CreateOleObject('HNetCfg.FwPolicy2');
RulesObject := fwPolicy2.Rules;
CurrentProfiles := fwPolicy2.CurrentProfileTypes;
// Cria o objeto que proporcionará acessar as propriedades de uma regra.
NewRule := CreateOleObject('HNetCfg.FWRule');
NewRule.Name := 'Foo Bar'; // Nome da Aplicação
NewRule.Description := 'My Powerful Service Example'; // Descrição da Aplicação
NewRule.Applicationname := ParamStr(0); // Caminho da Aplicaçao
NewRule.Protocol := NET_FW_IP_PROTOCOL_TCP;
NewRule.LocalPorts := 4000; // Porta
NewRule.Enabled := True;
NewRule.Grouping := ''; // Grupo
NewRule.Profiles := CurrentProfiles;
NewRule.Action := NET_FW_ACTION_ALLOW;
// Adiciona a nova regra
RulesObject.Add(NewRule);
end;
begin
try
CoInitialize(nil);
try
AddApplicationRule;
finally
CoUninitialize;
end;
except
on E:EOleException do
Writeln(Format('EOleException %s %x', [E.Message,E.ErrorCode]));
on E:Exception do
Writeln(E.Classname, ':', E.Message);
end;
Writeln('Press Enter to exit');
Readln;
end.
When opening the firewall advanced settings panel (type firewall.cpl
in the windows run - on the left side click advanced settings ) the application will be present there.
I hope I did not escape the focus of the question. For more information on how to manipulate the firewall through the APIs see esse tópico
no MSDN e aqui
precisely in Delphi .
Update
From @Renan's answer, I was able to reproduce what he mentioned, I'm not sure if the antivirus will block or not , it follows the procedure AddInFirewall()
modified ( tested not Windows 7):
procedure AddInFirewall(cApplicationName, cEntryName: string);
Var
TShell: TShellExecuteInfo;
cAppName: string;
begin
if Trim(cApplicationName) = '' then
cAppName := Application.ExeName
else
cAppName := cApplicationName;
if Trim(cEntryName) = '' then
cEntryName := ExtractFileName(cAppName);
FillChar(TShell, sizeof(TShell), 0);
TShell.cbSize := SizeOf(TShell);
TShell.fMask := SEE_MASK_NOCLOSEPROCESS;
TShell.Wnd := Application.Handle;
TShell.lpVerb := Nil;
TShell.nShow := SW_NORMAL; // Utilize SW_HIDE para esconder a janela
TShell.lpFile := 'cmd.exe';
TShell.lpParameters := PWideChar('/k netsh advfirewall firewall add rule name="' + cEntryName + '" dir=in action=allow program="' + cApplicationName + '" enable=yes');
TShell.lpVerb := 'runas';
ShellExecuteEx(@TShell);
WaitForSingleObject(TShell.hProcess, INFINITE);
CloseHandle(TShell.hProcess);
ShowMessage('Procedimento concluido!');
end;
Call the procedure the same way you were doing, like this:
AddInFirewall(Application.ExeName, 'MeuServico');
When calling the function, we will create the process cmd.exe
and pass as a parameter the command responsible for adding the application to the Firewall, a popup of the UAC will appear asking for confirmation to execute cmd.exe
with elevated rights.
Through WaitForSingleObject
we can only continue to use the application after cmd.exe
has been finalized.
If everything goes well, we will see the command Prompt show something like this:
And finally, in the Advanced firewall settings panel:
If an application requires a special firewall configuration, the configuration must be done by an administrator. In your case, the antivirus is correct in assuming that your program is malware.
Think about it. If any application could modify the Firewall rules with a specific call to some API, without alerting any protection system... What would prevent me from distributing some application, a freemium game maybe, that would open all the ports of your firewall and enable all protocols?
In your case, as for adding an application, Windows can take care of it automatically - UAC goes up and asks the user for confirmation to add the application to the whitelist. But remove a firewall rule, programmatically? No. Only and nothing more than no.