<p>I am writing some code to see if there is a hole in the firewall exception list for <strong>WinXP</strong> and <strong>Vista</strong> for a specific port used by our client software. </p>

<p>I can see that I can use the <code>NetFwMgr.LocalPolicy.CurrentProfile.GloballyOpenPorts</code> to get a list of the current Open port exceptions.  But i can not figure out how to get that enumerated list in to something that I can use in my Delphi program. </p>

<p>My latest try is listed below. It's giving me an access violation when I use <code>port_list.Item</code>. I know that's wrong, it was mostly wishful thinking on my part. Any help would be appreciated.</p>

<pre><code>function TFirewallUtility.IsPortInExceptionList(iPortNumber: integer): boolean;
var
  i, h: integer;
  port_list, port: OleVariant;
begin
  Result := False;
  port_list := mxFirewallManager.LocalPolicy.CurrentProfile.GloballyOpenPorts;
  for i := 0 to port_list.Count - 1 do
  begin
    port := port_list.Item[i];
    if (port.PortNumber = iPortNumber) then
    begin
      Result := True;
      break;
    end;
  end;
end;
</code></pre>

[{'answer_id': 78144, 'author': 'Jim McKeeth', 'author_id': 255, 'author_profile': 'https://Stackoverflow.com/users/255', 'pm_score': 0, 'selected': False, 'text': '<p>Without setting up an application to test with, I\'ll suggest the following.  Let me know if it works.</p>\n\n<p>I looked at the <a href="http://blogs.msdn.com/joncole/archive/2005/12/06/managed-classes-to-view-manipulate-the-windows-firewall.aspx" rel="nofollow noreferrer">C# example here</a>, and it looks like you need to do something like the following:</p>\n\n<pre><code>Result := False;\nport_enum := mxFirewallManager.LocalPolicy.CurrentProfile.GloballyOpenPorts._NewEnum;\nwhile port_enum.MoveNext &lt;&gt; Null do // try assigned if that doesn\'t work\nbegin\n  port = e.Current as INetFwOpenPort;\n  if (port.PortNumber = iPortNumber) then\n  begin\n    Result := True;\n    break;\n  end;\nend;\n</code></pre>\n\n<p>Not sure if that will compile, but the <strong>_NewEnum</strong>, <strong>MoveNext</strong> and <strong>Current</strong> are the members you want to use.</p>\n'}, {'answer_id': 105813, 'author': 'Ray Jenkins', 'author_id': 12425, 'author_profile': 'https://Stackoverflow.com/users/12425', 'pm_score': 1, 'selected': False, 'text': "<p>OK, I think that I have it figured out. </p>\n\n<p>I had to create a type library file of the hnetcfg.dll. I did that when I first started but have learned a lot about the firewall objects since then. It didn't work then, but its working now. You can create your own file from Component|Import Component. And then follow the wizard. </p>\n\n<p>The wrapping code uses exceptions which I normally don't like to do, but I don't know how to tell whether an Interface that is returning an Interface is actually returning data that I can work off of... So that would be an improvement if somebody can point me in the right direction.</p>\n\n<p>And now to the code, with a thanks to Jim for his response.</p>\n\n<pre><code>constructor TFirewallUtility.Create;\nbegin\n  inherited Create;\n  CoInitialize(nil);\n  mxCurrentFirewallProfile := INetFwMgr(CreateOLEObject('HNetCfg.FwMgr')).LocalPolicy.CurrentProfile;\nend;\n\nfunction TFirewallUtility.IsPortInExceptionList(iPortNumber: integer): boolean;\nbegin\n  try\n    Result := mxCurrentFirewallProfile.GloballyOpenPorts.Item(iPortNumber, NET_FW_IP_PROTOCOL_TCP).Port = iPortNumber;\n  except\n    Result := False;\n  end;\nend;\n\nfunction TFirewallUtility.IsPortEnabled(iPortNumber: integer): boolean;\nbegin\n  try\n    Result := mxCurrentFirewallProfile.GloballyOpenPorts.Item(iPortNumber, NET_FW_IP_PROTOCOL_TCP).Enabled;\n  except\n    Result := False;\n  end;\nend;\n\nprocedure TFirewallUtility.SetPortEnabled(iPortNumber: integer; sPortName: string; xProtocol: TFirewallPortProtocol);\nbegin\n  try\n   mxCurrentFirewallProfile.GloballyOpenPorts.Item(iPortNumber, CFirewallPortProtocalConsts[xProtocol]).Enabled := True;\n  except\n    HaltIf(True, 'xFirewallManager.TFirewallUtility.IsPortEnabled: Port not in exception list.');\n  end;\nend;\n\nprocedure TFirewallUtility.AddPortToFirewall(sPortName: string; iPortNumber: Cardinal; xProtocol: TFirewallPortProtocol);\nvar\n  port: INetFwOpenPort;\nbegin\n  port := INetFwOpenPort(CreateOLEObject('HNetCfg.FWOpenPort'));\n  port.Name := sPortName;\n  port.Protocol := CFirewallPortProtocalConsts[xProtocol];\n  port.Port := iPortNumber;\n  port.Scope := NET_FW_SCOPE_ALL;\n  port.Enabled := true;\n  mxCurrentFirewallProfile.GloballyOpenPorts.Add(port);\nend;\n</code></pre>\n"}, {'answer_id': 1613254, 'author': 'jpfollenius', 'author_id': 62391, 'author_profile': 'https://Stackoverflow.com/users/62391', 'pm_score': 1, 'selected': False, 'text': "<p>You can loop through the enum like this:</p>\n\n<pre><code>type\n  IEnumVariant = interface(IUnknown)\n  ['{00020404-0000-0000-C000-000000000046}']\n    function Next(celt: LongWord; var rgvar : OleVariant;\n                 pceltFetched: PLongWord): HResult; stdcall;\n    function Skip(celt: LongWord): HResult; stdcall;\n    function Reset: HResult; stdcall;\n    function Clone(out Enum : IEnumVariant) : HResult; stdcall;\n  end;\n\nvar\n  Enum : IEnumVariant;\n  Port : OleVariant;\n  Count : Integer;\n...\nCount := 1;\nIUnknown (Profile.GloballyOpenPorts._NewEnum).QueryInterface (IEnumVariant, Enum);\nEnum.Reset;\nwhile (Enum.Next (1, FirewallPort, @Count) = S_OK) do\n  begin\n  if (FirewallPort.Port = Port) then\n    Exit (True)\n  end;\n</code></pre>\n"}]
['https://Stackoverflow.com/questions/77890', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/12425/']