/// <summary> /// Executes the OpenPortCollector on Windows. Uses the .NET Core /// APIs to gather active TCP and UDP listeners and writes them /// to the database. /// </summary> public void ExecuteWindows() { var properties = IPGlobalProperties.GetIPGlobalProperties(); foreach (var endpoint in properties.GetActiveTcpListeners()) { var obj = new OpenPortObject(endpoint.Port, TRANSPORT.TCP, (ADDRESS_FAMILY)endpoint.AddressFamily) { Address = endpoint.Address.ToString(), }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.ProcessName = p.ProcessName; } Results.Push(obj); } foreach (var endpoint in properties.GetActiveUdpListeners()) { var obj = new OpenPortObject(endpoint.Port, TRANSPORT.UDP, (ADDRESS_FAMILY)endpoint.AddressFamily) { Address = endpoint.Address.ToString() }; obj.ProcessName = Win32ProcessPorts.ProcessPortMap.Find(x => x.PortNumber == endpoint.Port)?.ProcessName; Results.Push(obj); } }
/// <summary> /// Executes the OpenPortCollector on Windows. Uses the .NET Core /// APIs to gather active TCP and UDP listeners and writes them /// to the database. /// </summary> internal void ExecuteWindows(CancellationToken cancellationToken) { var properties = IPGlobalProperties.GetIPGlobalProperties(); foreach (var endpoint in properties.GetActiveTcpListeners()) { if (cancellationToken.IsCancellationRequested) { return; } var obj = new OpenPortObject(endpoint.Port, TRANSPORT.TCP, (ADDRESS_FAMILY)endpoint.AddressFamily) { Address = endpoint.Address.ToString(), }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.ProcessName = p.ProcessName; } HandleChange(obj); } foreach (var endpoint in properties.GetActiveUdpListeners()) { var obj = new OpenPortObject(endpoint.Port, TRANSPORT.UDP, (ADDRESS_FAMILY)endpoint.AddressFamily) { Address = endpoint.Address.ToString() }; obj.ProcessName = Win32ProcessPorts.ProcessPortMap.Find(x => x.PortNumber == endpoint.Port)?.ProcessName; HandleChange(obj); } }
/// <summary> /// Executes the OpenPortCollector on OS X. Calls out to the `lsof` /// command and parses the output, sending the output to the database. /// </summary> private void ExecuteOsX() { try { string result = ExternalCommandRunner.RunExternalCommand("lsof", "-Pn -i4 -i6"); foreach (var _line in result.Split('\n')) { var line = _line.ToUpperInvariant(); if (!line.Contains("LISTEN")) { continue; // Skip any lines which aren't open listeners } var parts = Regex.Split(line, @"\s+"); if (parts.Length <= 9) { continue; // Not long enough } var addressMatches = Regex.Match(parts[8], @"^(.*):(\d+)$"); if (addressMatches.Success) { var address = addressMatches.Groups[1].ToString(); var port = addressMatches.Groups[2].ToString(); if (int.TryParse(port, out int portInt)) { var transport = parts[7].ToUpperInvariant().Equals("TCP") ? TRANSPORT.TCP : parts[7].ToUpperInvariant().Equals("TCP") ? TRANSPORT.UDP : TRANSPORT.UNKNOWN; var family = ADDRESS_FAMILY.Unknown; switch (parts[4]) { case "IPv4": family = ADDRESS_FAMILY.InterNetwork; break; case "IPv6": family = ADDRESS_FAMILY.InterNetworkV6; break; default: family = ADDRESS_FAMILY.Unknown; break; } var obj = new OpenPortObject(portInt, transport, family) { Address = address, ProcessName = parts[0] }; Results.Push(obj); } } } } catch (Exception e) { Log.Error(e, Strings.Get("Err_Lsof")); } }
public void Write(OpenPortObject obj) { _numCollected++; var objStr = obj.ToString(); if (this.processedObjects.Contains(objStr)) { Log.Debug("Object already exists, ignoring: {0}", objStr); return; } this.processedObjects.Add(objStr); var cmd = new SqliteCommand(SQL_INSERT, DatabaseManager.Connection, DatabaseManager.Transaction); cmd.Parameters.AddWithValue("@run_id", this.runId); cmd.Parameters.AddWithValue("@row_key", obj.RowKey); cmd.Parameters.AddWithValue("@family", obj.family); cmd.Parameters.AddWithValue("@address", obj.address); cmd.Parameters.AddWithValue("@type", obj.type); cmd.Parameters.AddWithValue("@port", obj.port); cmd.Parameters.AddWithValue("@process_name", obj.processName ?? ""); cmd.Parameters.AddWithValue("@serialized", JsonConvert.SerializeObject(obj)); cmd.ExecuteNonQuery(); }
public void Compare(string beforeKey, string afterKey) { var beforeSet = new HashSet <OpenPortObject>(); var afterSet = new HashSet <OpenPortObject>(); var cmd = new SqliteCommand("select * from network_ports where run_id = @before_run_id or run_id = @after_run_id", DatabaseManager.Connection); cmd.Parameters.AddWithValue("@before_run_id", beforeKey); cmd.Parameters.AddWithValue("@after_run_id", beforeKey); using (SqliteDataReader rdr = cmd.ExecuteReader()) { while (rdr.Read()) { var runId = rdr["run_id"].ToString(); var obj = new OpenPortObject() { address = rdr["address"].ToString(), family = rdr["family"].ToString(), port = rdr["port"].ToString(), processName = rdr["process_name"].ToString() }; if (runId == beforeKey) { beforeSet.Add(obj); } else if (runId == afterKey) { afterSet.Add(obj); } } } var newEntries = new HashSet <OpenPortObject>(); var goneEntries = new HashSet <OpenPortObject>(); newEntries.UnionWith(beforeSet); foreach (var b in beforeSet) { foreach (var a in afterSet) { if (a.Equals(b)) { } } if (!afterSet.Contains(b)) { Log.Information("Open port no longer open: {0}", b.ToString()); } } foreach (var b in afterSet) { if (!beforeSet.Contains(b)) { Log.Information("New open port: {0}", b.ToString()); } } }
/// <summary> /// Executes the OpenPortCollector on OS X. Calls out to the `lsof` /// command and parses the output, sending the output to the database. /// The 'ss' command used on Linux isn't available on OS X. /// </summary> private void ExecuteOsX() { try { var result = ExternalCommandRunner.RunExternalCommand("sudo", "lsof -Pn -i4 -i6"); foreach (var _line in result.Split('\n')) { var line = _line.ToLower(); if (!line.Contains("listen")) { continue; // Skip any lines which aren't open listeners } var parts = Regex.Split(line, @"\s+"); if (parts.Length <= 9) { continue; // Not long enough } string address = null; string port = null; var addressMatches = Regex.Match(parts[8], @"^(.*):(\d+)$"); if (addressMatches.Success) { address = addressMatches.Groups[1].ToString(); port = addressMatches.Groups[2].ToString(); var obj = new OpenPortObject() { // Assuming family means IPv6 vs IPv4 family = parts[4], address = address, port = port, type = parts[7], processName = parts[0] }; try { DatabaseManager.Write(obj, this.runId); } catch (Exception e) { Logger.DebugException(e); } } } } catch (Exception e) { Log.Error(Strings.Get("Err_Lsof")); Logger.DebugException(e); } }
/// <summary> /// Executes the OpenPortCollector on Linux. Calls out to the `ss` /// command and parses the output, sending the output to the database. /// </summary> internal void ExecuteLinux(CancellationToken cancellationToken) { try { var result = ExternalCommandRunner.RunExternalCommand("ss", "-ln"); foreach (var _line in result.Split('\n')) { if (cancellationToken.IsCancellationRequested) { return; } var line = _line; line = line.ToUpperInvariant(); if (!line.Contains("LISTEN")) { continue; } var parts = Regex.Split(line, @"\s+"); if (parts.Length < 5) { continue; // Not long enough, must be an error } var addressMatches = Regex.Match(parts[4], @"^(.*):(\d+)$"); if (addressMatches.Success) { var address = addressMatches.Groups[1].ToString(); var port = addressMatches.Groups[2].ToString(); if (int.TryParse(port, out int portInt)) { var transport = parts[0].ToUpperInvariant().Equals("TCP") ? TRANSPORT.TCP : TRANSPORT.UDP; var family = address.Contains('.') ? ADDRESS_FAMILY.InterNetwork : address.Contains(':') ? ADDRESS_FAMILY.InterNetworkV6 : ADDRESS_FAMILY.Unknown; var obj = new OpenPortObject(portInt, transport, family) { Address = address }; HandleChange(obj); } } } } catch (Exception e) { Log.Warning(Strings.Get("Err_Iproute2")); Log.Debug(e, ""); } }
/// <summary> /// Executes the OpenPortCollector on Linux. Calls out to the `ss` /// command and parses the output, sending the output to the database. /// </summary> private void ExecuteLinux() { try { var result = ExternalCommandRunner.RunExternalCommand("ss", "-ln"); foreach (var _line in result.Split('\n')) { var line = _line; line = line.ToUpperInvariant(); if (!line.Contains("LISTEN")) { continue; } var parts = Regex.Split(line, @"\s+"); if (parts.Length < 5) { continue; // Not long enough, must be an error } string address = null; string port = null; var addressMatches = Regex.Match(parts[4], @"^(.*):(\d+)$"); if (addressMatches.Success) { address = addressMatches.Groups[1].ToString(); port = addressMatches.Groups[2].ToString(); var obj = new OpenPortObject() { Family = parts[0],//@TODO: Determine IPV4 vs IPv6 via looking at the address Address = address, Port = port, Type = parts[0] }; DatabaseManager.Write(obj, this.RunId); } } } catch (Exception e) { Log.Warning(Strings.Get("Err_Iproute2")); Log.Debug(e, ""); } }
/// <summary> /// Executes the OpenPortCollector on OS X. Calls out to the `lsof` /// command and parses the output, sending the output to the database. /// The 'ss' command used on Linux isn't available on OS X. /// </summary> private void ExecuteOsX() { try { string result = ExternalCommandRunner.RunExternalCommand("lsof", "-Pn -i4 -i6"); foreach (var _line in result.Split('\n')) { var line = _line.ToUpperInvariant(); if (!line.Contains("LISTEN")) { continue; // Skip any lines which aren't open listeners } var parts = Regex.Split(line, @"\s+"); if (parts.Length <= 9) { continue; // Not long enough } var addressMatches = Regex.Match(parts[8], @"^(.*):(\d+)$"); if (addressMatches.Success) { var address = addressMatches.Groups[1].ToString(); var port = addressMatches.Groups[2].ToString(); if (int.TryParse(port, out int portInt)) { var obj = new OpenPortObject(portInt) { // Assuming family means IPv6 vs IPv4 Family = parts[4], Address = address, Type = parts[7], ProcessName = parts[0] }; DatabaseManager.Write(obj, RunId); } } } } catch (Exception e) { Log.Error(e, Strings.Get("Err_Lsof")); } }
/// <summary> /// Executes the OpenPortCollector on Windows. Uses the .NET Core /// APIs to gather active TCP and UDP listeners and writes them /// to the database. /// </summary> public void ExecuteWindows() { Log.Debug("Collecting open port information (Windows implementation)"); var properties = IPGlobalProperties.GetIPGlobalProperties(); foreach (var endpoint in properties.GetActiveTcpListeners()) { var obj = new OpenPortObject() { family = endpoint.AddressFamily.ToString(), address = endpoint.Address.ToString(), port = endpoint.Port.ToString(), type = "tcp" }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.processName = p.ProcessName; } DatabaseManager.Write(obj, this.runId); } foreach (var endpoint in properties.GetActiveUdpListeners()) { var obj = new OpenPortObject() { family = endpoint.AddressFamily.ToString(), address = endpoint.Address.ToString(), port = endpoint.Port.ToString(), type = "udp" }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.processName = p.ProcessName; } DatabaseManager.Write(obj, this.runId); } }
/// <summary> /// Executes the OpenPortCollector on Linux. Calls out to the `ss` /// command and parses the output, sending the output to the database. /// </summary> private void ExecuteLinux() { Log.Debug("ExecuteLinux()"); var result = ExternalCommandRunner.RunExternalCommand("ss", "-ln"); foreach (var _line in result.Split('\n')) { var line = _line; line = line.ToLower(); if (!line.Contains("listen")) { continue; } var parts = Regex.Split(line, @"\s+"); if (parts.Length < 5) { continue; // Not long enough, must be an error } string address = null; string port = null; var addressMatches = Regex.Match(parts[4], @"^(.*):(\d+)$"); if (addressMatches.Success) { address = addressMatches.Groups[1].ToString(); port = addressMatches.Groups[2].ToString(); var obj = new OpenPortObject() { family = parts[0],//@TODO: Determine IPV4 vs IPv6 via looking at the address address = address, port = port, type = parts[0] }; DatabaseManager.Write(obj, this.runId); } } }
/// <summary> /// Executes the OpenPortCollector on Windows. Uses the .NET Core /// APIs to gather active TCP and UDP listeners and writes them /// to the database. /// </summary> public void ExecuteWindows() { var properties = IPGlobalProperties.GetIPGlobalProperties(); foreach (var endpoint in properties.GetActiveTcpListeners()) { var obj = new OpenPortObject() { Family = endpoint.AddressFamily.ToString(), Address = endpoint.Address.ToString(), Port = endpoint.Port.ToString(CultureInfo.InvariantCulture), Type = "tcp" }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.ProcessName = p.ProcessName; } DatabaseManager.Write(obj, this.RunId); } foreach (var endpoint in properties.GetActiveUdpListeners()) { var obj = new OpenPortObject() { Family = endpoint.AddressFamily.ToString(), Address = endpoint.Address.ToString(), Port = endpoint.Port.ToString(CultureInfo.InvariantCulture), Type = "udp" }; foreach (ProcessPort p in Win32ProcessPorts.ProcessPortMap.FindAll(x => x.PortNumber == endpoint.Port)) { obj.ProcessName = p.ProcessName; } DatabaseManager.Write(obj, this.RunId); } }
public void TestSerializeAndDeserializeOpenPortObject() { var opo = new OpenPortObject(1024, TRANSPORT.TCP); Assert.IsTrue(opo.RowKey.Equals(JsonUtils.Hydrate(JsonUtils.Dehydrate(opo), RESULT_TYPE.PORT)?.RowKey)); }