C #: перечислить IP-адреса в диапазоне

Как выполнять итерацию по диапазону IP-адресов, предоставляемых пользователем?

Я гибкий в формате, если он позволяет указать все диапазоны. Возможно, что-то вроде nmap-стиля:

'192.0.2.1' # one IP address '192.0.2.0-31' # one block with 32 IP addresses. '192.0.2-3.1-254' # two blocks with 254 IP addresses. '0-255.0-255.0-255.0-255' # the whole IPv4 address space 

Например, если пользователь ввел 192.0.2-3.1-254 , я хотел бы знать, как создать список всех допустимых IP-адресов в этом диапазоне, чтобы я мог выполнять итерацию через них.

Например:

 using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Net; using System.Text.RegularExpressions; namespace IpRanges { public class IPRange { public IPRange(string ipRange) { if (ipRange == null) throw new ArgumentNullException(); if (!TryParseCIDRNotation(ipRange) && !TryParseSimpleRange(ipRange)) throw new ArgumentException(); } public IEnumerable GetAllIP() { int capacity = 1; for (int i = 0; i < 4; i++) capacity *= endIP[i] - beginIP[i] + 1; List ips = new List(capacity); for (int i0 = beginIP[0]; i0 <= endIP[0]; i0++) { for (int i1 = beginIP[1]; i1 <= endIP[1]; i1++) { for (int i2 = beginIP[2]; i2 <= endIP[2]; i2++) { for (int i3 = beginIP[3]; i3 <= endIP[3]; i3++) { ips.Add(new IPAddress(new byte[] { (byte)i0, (byte)i1, (byte)i2, (byte)i3 })); } } } } return ips; } ///  /// Parse IP-range string in CIDR notation. /// For example "12.15.0.0/16". ///  ///  ///  private bool TryParseCIDRNotation(string ipRange) { string[] x = ipRange.Split('/'); if (x.Length != 2) return false; byte bits = byte.Parse(x[1]); uint ip = 0; String[] ipParts0 = x[0].Split('.'); for (int i = 0; i < 4; i++) { ip = ip << 8; ip += uint.Parse(ipParts0[i]); } byte shiftBits = (byte)(32 - bits); uint ip1 = (ip >> shiftBits) << shiftBits; if (ip1 != ip) // Check correct subnet address return false; uint ip2 = ip1 >> shiftBits; for (int k = 0; k < shiftBits; k++) { ip2 = (ip2 << 1) + 1; } beginIP = new byte[4]; endIP = new byte[4]; for (int i = 0; i < 4; i++) { beginIP[i] = (byte) ((ip1 >> (3 - i) * 8) & 255); endIP[i] = (byte)((ip2 >> (3 - i) * 8) & 255); } return true; } ///  /// Parse IP-range string "12.15-16.1-30.10-255" ///  ///  ///  private bool TryParseSimpleRange(string ipRange) { String[] ipParts = ipRange.Split('.'); beginIP = new byte[4]; endIP = new byte[4]; for (int i = 0; i < 4; i++) { string[] rangeParts = ipParts[i].Split('-'); if (rangeParts.Length < 1 || rangeParts.Length > 2) return false; beginIP[i] = byte.Parse(rangeParts[0]); endIP[i] = (rangeParts.Length == 1) ? beginIP[i] : byte.Parse(rangeParts[1]); } return true; } private byte [] beginIP; private byte [] endIP; } } 

Посмотрите fragment здесь . Держите кредиты на месте, если вы используете это, пожалуйста.

 using System; using System.Collections.Generic; using System.ComponentModel; using System.Linq; using System.Net; /* ==================================================================================== C# IP address range finder helper class (C) Nahum Bazes * Free for private & commercial use - no restriction applied, please leave credits. * DO NOT REMOVE THIS COMMENT * ==================================================================================== */ namespace IPAddressTools { public class RangeFinder { public IEnumerable GetIPRange(IPAddress startIP, IPAddress endIP) { uint sIP = ipToUint(startIP.GetAddressBytes()); uint eIP = ipToUint(endIP.GetAddressBytes()); while (sIP <= eIP) { yield return new IPAddress(reverseBytesArray(sIP)).ToString(); sIP++; } } /* reverse byte order in array */ protected uint reverseBytesArray(uint ip) { byte[] bytes = BitConverter.GetBytes(ip); bytes = bytes.Reverse().ToArray(); return (uint)BitConverter.ToInt32(bytes, 0); } /* Convert bytes array to 32 bit long value */ protected uint ipToUint(byte[] ipBytes) { ByteConverter bConvert = new ByteConverter(); uint ipUint = 0; int shift = 24; // indicates number of bits left for shifting foreach (byte b in ipBytes) { if (ipUint == 0) { ipUint = (uint)bConvert.ConvertTo(b, typeof(uint)) << shift; shift -= 8; continue; } if (shift >= 8) ipUint += (uint)bConvert.ConvertTo(b, typeof(uint)) << shift; else ipUint += (uint)bConvert.ConvertTo(b, typeof(uint)); shift -= 8; } return ipUint; } } } 

Я думаю, это должно сделать это.

 static void TestFunc() { byte[,] range = ParseRange("192.0.2-5.14-28"); foreach (IPAddress addr in Enumerate(range)) { Console.WriteLine(addr); } } static byte[,] ParseRange(string str) { if (string.IsNullOrEmpty(str)) throw new ArgumentException("str"); string[] partStr = str.Split('.'); if (partStr.Length != 4) throw new FormatException(); byte[,] range = new byte[4, 2]; for (int i = 0; i < 4; i++) { string[] rangeStr = partStr[i].Split('-'); if (rangeStr.Length > 2) throw new FormatException(); range[i, 0] = byte.Parse(rangeStr[0]); range[i, 1] = byte.Parse(rangeStr[Math.Min(rangeStr.Length - 1, 1)]); // Remove this to allow ranges to wrap around. // For example: 254-4 = 254, 255, 0, 1, 2, 3, 4 if (range[i, 1] < range[i, 0]) throw new FormatException(); } return range; } static IEnumerable Enumerate(byte[,] range) { if (range.GetLength(0) != 4) throw new ArgumentException("range"); if (range.GetLength(1) != 2) throw new ArgumentException("range"); for (byte a = range[0, 0]; a != (byte)(range[0, 1] + 1); a++) { for (byte b = range[1, 0]; b != (byte)(range[1, 1] + 1); b++) { for (byte c = range[2, 0]; c != (byte)(range[2, 1] + 1); c++) { for (byte d = range[3, 0]; d != (byte)(range[3, 1] + 1); d++) { yield return new IPAddress(new byte[] { a, b, c, d }); } } } } } 

Я опаздываю на игру, но ваш вопрос упоминался в двух экземплярах, поэтому я просто добавлю ответ здесь. Используя библиотеку IPAddressRange , вы можете перечислять свои IP-адреса следующим образом:

 var start = IPAddress.Parse("192.168.0.2"); var end = IPAddress.Parse("192.168.0.254"); var range = new IPAddressRange(start, end); foreach (var ip in range) { Console.WriteLine(ip); } 

Библиотека также поддерживает записи CIDR и строки диапазонов

  • Как получить ближайшее число из списка с LINQ?
  • Внутренняя реализация Lock (Monitor) в .NET.
  • Внедрение ресурсов в исполняемый файл с использованием GCC
  • Файл запроса Xml для записей с использованием Linq
  • Вы (действительно) пишете безопасный код исключения?
  • addFontFile из ресурсов
  • Понимание макроса container_of в ядре Linux
  • Является ли list :: size () действительно O (n)?
  • Создание экранной клавиатуры
  • Простой пример состояния машины в C #?
  • Как получить и установить переменные среды в C #?
  • Interesting Posts

    Почему я не могу удалить все разделы на флэш-диске в Windows 7?

    Как сохранить настройки OSX под управлением версии?

    Самый быстрый способ удалить все непечатаемые символы из строки Java

    Плата Wi-Fi Fedora 14 не активируется

    Ошибка Google Drive CSS / JS 404

    $ Windows. ~ WS в папке C: \ после установки Windows 10, обновления или создания носителя?

    Конфигурация сети VirtualBox

    Выполнение вложений и обновлений с помощью Dapper

    Как запретить разработчикам использовать reflection для доступа к приватным методам и конструкторам в Java?

    Получить текущее имя представления в ASP.NET MVC?

    Как мне получить X11 Forwarding для работы с Windows с PuTTY и Xming?

    Токен-маркер анти-подделки и маркер поля формы не совпадают с MVC 4

    Какие компьютерные компоненты в настоящее время уязвимы для магнитов?

    Настройки удаленного рабочего стола отсутствуют

    Можете ли вы настроить элемент с помощью CSS только в том случае, если присутствуют 2 classа?

    Давайте будем гением компьютера.