Форум программистов, компьютерный форум, киберфорум
C# для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.62/21: Рейтинг темы: голосов - 21, средняя оценка - 4.62
3 / 2 / 1
Регистрация: 13.04.2020
Сообщений: 10
1

Пропинговать все IPv4 адреса в сети за минимальное время

03.06.2020, 18:01. Показов 3915. Ответов 11
Метки c# (Все метки)

Author24 — интернет-сервис помощи студентам
Доброго времени суток!

Недавно задался вопросом как пропинговать все ip адреса в сети (от 0.0.0.0 до 255.255.255.255). Написал небольшую программку на основе примера в доках с асинхронным пингом.
Однако есть одна проблема: программа работает достаточно шустро но пингует асинхронно только младший октет: т.е. например от 192.168.1.0 до 192.168.1.255. Если пробовать пинговать большее количество адресов то ПК начинает "задыхатся".
Пока пришел к решению пинговать пачками по 255 (в моем случае программа работает 2 минуты с хвостиком пингуя от aaa.bbb.0.0 до aaa.bbb.255.255):
C#
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Net;
using System.Net.NetworkInformation;
using System.Threading;
 
namespace ConsoleTEST_app
{
    class Program
    {
        private static List<Ping> pingers = new List<Ping>();
        private static int instances = 0;
        private static object @lock = new object();
        private static int result = 0;
        private static int timeOut = 250;
        private static int ttl = 5;
        static void Main(string[] args)
        {  
            Console.Write(System.Environment.NewLine + "Введите октеты (например 192.168): ");
            string baseIP = Console.ReadLine();
 
            if (IPAddress.TryParse(string.Concat(baseIP, ".1.1"), out IPAddress ip)) Console.WriteLine("Проверка: это верный IP");
            else
            {
                Console.WriteLine("Проверка: это неверный IP" + System.Environment.NewLine);
            }
 
            Console.Write("Пингую " + " {0}*", baseIP);
            Console.WriteLine();
            CreatePingers(255);
 
            PingOptions po = new PingOptions(ttl, true);
            System.Text.ASCIIEncoding enc = new System.Text.ASCIIEncoding();
            byte[] data = enc.GetBytes("PingingIPs-TestBytes");
 
            SpinWait wait = new SpinWait();
            Stopwatch watch = Stopwatch.StartNew();
 
            for (int i = 0; i < 255; i++)
            {
 
                int cnt1 = 1;
                string temp = null;
                foreach (Ping p in pingers)
                {
                    lock (@lock)
                    {
                        instances += 1;
                    }
                    temp = string.Concat(baseIP, ".", i.ToString(), ".", cnt1.ToString());
 
                    try
                    {
                        p.SendAsync(temp, timeOut, data, po);
                    }
                    catch (Exception ex)
                    {
                    }
 
                    cnt1++;
                }
 
                while (instances > 0)
                {
                    wait.SpinOnce();
                }
 
            }
 
            watch.Stop();
            DestroyPingers();
 
            Console.Write("Просканировано за " + " {0}. " +" найдено " + " {1} " + " активных ip " + " ", watch.Elapsed.ToString(), result);
            result = 0;
            Console.WriteLine(System.Environment.NewLine);
 
        }
 
        public static void Ping_completed(object s, PingCompletedEventArgs e)
        {
            lock (@lock)
            {
                instances -= 1;
            }
 
            if (e.Reply.Status == IPStatus.Success)
            {
                Console.WriteLine(string.Concat("Активных ip ", e.Reply.Address.ToString()));
                result += 1;
            }
            else
            {
            }
        }
        private static void CreatePingers(int cnt)
        {
            for (int i = 1; i <= cnt; i++)
            {
                Ping p = new Ping();
                p.PingCompleted += Ping_completed;
                pingers.Add(p);
            }
        }
 
        private static void DestroyPingers()
        {
            foreach (Ping p in pingers)
            {
                p.PingCompleted -= Ping_completed;
                p.Dispose();
            }
            pingers.Clear();
        }
 
    }
}
Вопрос: возможно ли как-то пропинговать на С# все адреса в сети быстрее, чем за несколько дней непрерывной работы ?)) Возможно ли это реализовать через широковещательные адреса или любым иным образом? Что почитать или в каком направлении двигаться (кроме как прямо и немного направо )? Любая помощь будет неоценима.
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
03.06.2020, 18:01
Ответы с готовыми решениями:

Даны части IPv4 адреса и нужно собрать из них все возможные адреса
Здравствуйте, мне нужно написать такой алгоритм. Даны часты IPv4 адреса и нужно собрать из них все...

Пропинговать все адреса из 10 TextBox и покрасить в зеленый цвет если есть пинг
Имеется 10 текстбоксов в которых записаны IP адреса - пропинговать все адреса и покрасить в зеленый...

Напишите программу, которая считывает IPv4 адрес и проверяет ее валидность. Форма записи IPv4 адреса – x.x.x.x
Напишите код для программы Пример: Напишите программу, которая считывает IPv4 адрес и проверяет...

Как пропинговать IP-адреса, содержащиеся в XML-файле?
Есть некий массив из xml файла: &lt;webservers&gt; &lt;server address=&quot;http://1.1.1.1/&quot;/&gt; ...

11
Пора на C++?
370 / 264 / 99
Регистрация: 10.04.2020
Сообщений: 1,275
03.06.2020, 21:49 2
NRG, смотря что вы имеете в виду под словом "сеть". Для локальной сети характерны только следующие адреса:
От 10.0.0.0 до 10.255.255.255;
От 172.16.0.0 до 172.31.255.255;
От 192.168.0.0 до 192.168.255.255;
От 100.64.0.0 до 100.127.255.255.
Если вам нужно пропинговать все адреса интернета, то это будет долго.
0
3 / 2 / 1
Регистрация: 13.04.2020
Сообщений: 10
04.06.2020, 08:38  [ТС] 3
Цитата Сообщение от TrickyBestia Посмотреть сообщение
NRG, смотря что вы имеете в виду под словом "сеть". Для локальной сети характерны только следующие адреса:
От 10.0.0.0 до 10.255.255.255;
От 172.16.0.0 до 172.31.255.255;
От 192.168.0.0 до 192.168.255.255;
От 100.64.0.0 до 100.127.255.255.
Если вам нужно пропинговать все адреса интернета, то это будет долго.
Да. Указанных сетей будет вполне достаточно.
Конечно, хотелось бы чтобы программа обладала некоторой гибкостью и в ней можно было бы задать любой диапазон номеров сети, но это в идеале.
Приведенный код справляется с 192.168.0.0 - 192.168.255.255, но я не думаю что так же быстро он переберет и остальные (где меняется номер первых двух октетов).
По моим прикидкам на это потребуется не менее 18 часов, что ооочень долго.
Есть ли возможность как-то это реализовать с помощью широковещательных запросов?
1
Эксперт .NET
17791 / 12942 / 3381
Регистрация: 17.09.2011
Сообщений: 21,215
04.06.2020, 11:33 4
NRG, весь диапазон IPv4 - это 232 адресов, 4 с лишним миллиарда.
Возьмите калькулятор и посчитайте с какой скоростью их надо пинговать, чтобы проверить все за приемлимое время.
В качестве примера, пингуя по 1000 адресов в секунду (1 пинг за 1мс - реально ли?), проверка всего диапазона займет 50 дней.
0
Пора на C++?
370 / 264 / 99
Регистрация: 10.04.2020
Сообщений: 1,275
04.06.2020, 12:00 5
NRG, если с await не получается, попробуйте потоками. Пинг это несложная задача для процессора, так что потоков может быть и 50 и 100.
0
1517 / 908 / 328
Регистрация: 17.05.2015
Сообщений: 3,430
04.06.2020, 13:34 6
TrickyBestia, у вас какой то волшебный процессор, который генерирует потоки в зависимости от сложности задачи.
А у обычных людей процессор может одновременно выполнять количество задач равное количеству ядер. А создав 100 потоков процессор начинает прыгать с одной задачи на другую, при этом совершая тяжелую операцию переключения контекста
2
83 / 61 / 17
Регистрация: 21.08.2015
Сообщений: 1,091
04.06.2020, 14:39 7
Посылайте широко вещательный сигнал.
Те узлы что откликнулись будут идти как удачный пинг и т.д.

Добавлено через 3 минуты
Пинговать каждый узел через цикл бессмысленно.
Отдельно можно пинговать сервера циклом или важные узлы, но никто не делает отдельный пинг для каждого узла, представьте, какую нагрузку вы дадите на сеть. Это будет DOS атака.

Цитата Сообщение от kolorotur Посмотреть сообщение
NRG, весь диапазон IPv4 - это 232 адресов, 4 с лишним миллиарда.
Как правило, в локальный сети диапазон меньше.
Узел 10,57,100,4
Маска 255,255,0,0
Нету тут 4 с лишним миллиарда.
0
Эксперт .NET
17791 / 12942 / 3381
Регистрация: 17.09.2011
Сообщений: 21,215
04.06.2020, 14:45 8
Цитата Сообщение от Чипс Посмотреть сообщение
Как правило, в локальный сети диапазон меньше.
У автора малость иные амбиции:
Цитата Сообщение от NRG Посмотреть сообщение
задался вопросом как пропинговать все ip адреса в сети (от 0.0.0.0 до 255.255.255.255)
0
83 / 61 / 17
Регистрация: 21.08.2015
Сообщений: 1,091
04.06.2020, 14:52 9
Цитата Сообщение от kolorotur Посмотреть сообщение
У автора малость иные амбиции:
Ну тогда только так
0
3 / 2 / 1
Регистрация: 13.04.2020
Сообщений: 10
04.06.2020, 16:21  [ТС] 10
Верно. Из расчета затрат времени - на моей машине это займет не менее 90 дней на весь диапазон, и около 18 часов на сети выборочно. Трехмесячный DDoS для решения задачи не подойдет))
Также есть ещё один нюанс - более активных ~700 потоков уже заметны невооруженным ухом. Поэтому в примере за раз не более 255.
C широковещательным запросом тоже не все ясно.
Какой алгоритм?
Создаем сокет. Говорим ОС, что он будет широковещательным. Отправляем широковещательный UDP в сеть, все, кто его получил отзываются эхом обратно. Для этого нужен МАС адаптера машины. Вручную прописывать - неприемлемо, значит нужно автоматом узнавать.
Потом сканируем входящий трафик и ловим отклики?
Что то подобное не работает в моей локальной сети. Плюс когда пакеты пойдут назад то их надо будет как-то "ловить", а использование сниферов в сетях явно не приветствуется - многие роутеры не пропускают бродкасты. Придется бороться ещё и с железом.

Может есть какие либо примеры реализации чего-то подобного? Не может быть чтобы за все время никто не задавался похожей задачей. Хотелось бы посмотреть исходники.

Объяснил как смог, надеюсь не запутал еще больше.
0
Пора на C++?
370 / 264 / 99
Регистрация: 10.04.2020
Сообщений: 1,275
05.06.2020, 12:06 11
Рядовой, это понятно, но что будет делать процессор, после того как отправит пинговое icmp сообщение? Ждать ответа? А раз поток ждёт, значит что он не грузит процессор. В это время процессор будет считать другой поток. Лично я когда-то делал похожее приложение, работающее с сетью, так оно работало в 40 потоках, и процессор максимум загружался на 12%, потому что при работе с сетью надо ЖДАТЬ
0
Эксперт .NET
17791 / 12942 / 3381
Регистрация: 17.09.2011
Сообщений: 21,215
05.06.2020, 12:58 12
TrickyBestia, если поток 99% времени спит, то зачем он вообще нужен?
У вас больше времени уйдет на создание и запуск такого потока, чем этот поток сэкономит при работе с I/O.

Добавлено через 15 секунд
TrickyBestia, если поток 99% времени спит, то зачем он вообще нужен?
У вас больше времени уйдет на создание и запуск такого потока, чем этот поток сэкономит при работе с I/O.
0
05.06.2020, 12:58
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
05.06.2020, 12:58
Помогаю со студенческими работами здесь

Автонастройка IPv4 адреса
Добрый день, форумчане. Я был бы благодарен любой помощи и совету. Есть небольшая сеть. На входе...

Определение широковещательного адреса по IPv4 и маске
По адресу узла 10.193.68.59 и маске подсети 255.255.248.0 определить широковещательный адрес. я...

Свободные IPv4-адреса закончатся через 2 месяца
Согласно данным технических координаторов сетевого пространства интернета, последние блоки...

Узнать все IP адреса компьютеров сети
как можно узнать все ip адреса компьютеров в сети и вывести каждый адрес в отдельное текстовое...

Сканер сети проверяет на все IP адреса
***

Как пропинговать компьютер, подключен ли он к сети
Добрый день всем. Как пропинговать компьютер, подключен ли он к сети. Надо в командной строке...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
12
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru