Чому pinging 192.168.072 (лише 2 крапки) повертає відповідь з 192.168.0.58?


379

Я помилково пропустив крапку IP-адреси та ввів 192.168.072.
На моє здивування я підключився до машини в192.168.0.58

Якщо я пінг, 192.168.072я отримую відповіді 192.168.0.58.

Чому це?


Я на ПК з Windows в домені Windows.


Якщо я пінг, 192.168.72я отримую відповідь 192.168.0.72, тому здається, що 0в 072(за моєю первісною помилкою) важливо.


Це питання було питанням суперкористувача тижня .
Прочитайте запис у блозі для отримання більш детальної інформації або допишіть до себе



2
Цікаво, що саме те саме відбувається і в Linux: ping 192.168.072друкує PING 192.168.072 (192.168.0.58) 56(84) bytes of data.[...].
Механічний равлик

9
що ще більш випадково - це те, що у вас була машина, 192.168.0.58щоб отримати відповідь. Які шанси на це?
Джеймс Мерц

3
@KronoS це насправді не так дивно, якщо ти знаходишся в школі чи мережі компаній. Деякі сервери DHCP надаватимуть адреси в порядку більшого порядку, і більшість з них буде використовуватися.
Таум

5
192.168.0.58настає час для мене .. чи можуть усі запити ping якось вибити сервер ?!
примхливий

Відповіді:


570

Усі надмірно ускладнюють це RFC, IP класами тощо. Просто проведіть кілька тестів, щоб побачити, як pingкоманда аналізує вхід IP-адресою користувачем (стороннє обрив видалено):

> ping 1
Pinging 0.0.0.1 with 32 bytes of data:

> ping 1.2
Pinging 1.0.0.2 with 32 bytes of data:

> ping 1.2.3
Pinging 1.2.0.3 with 32 bytes of data:

> ping 1.2.3.4
Pinging 1.2.3.4 with 32 bytes of data:

> ping 1.2.3.4.5
Ping request could not find host 1.2.3.4.5. Please check the name and try again.

> ping 255
Pinging 0.0.0.255 with 32 bytes of data:

> ping 256
Pinging 0.0.1.0 with 32 bytes of data:

Як бачите, pingкоманда (в Windows) дозволяє використовувати різні формати IP-адреси. Адреса IPv4 може бути розбита на чотири частини ("пунктирний квадратик") так:, A.B.C.Dі pingкоманда дозволяє залишити деякі, заповнюючи за замовчуванням 0наступне:

1 part  (ping A)       : 0.0.0.A
2 parts (ping A.B)     : A.0.0.B
3 parts (ping A.B.C)   : A.B.0.C
4 parts (ping A.B.C.D) : A.B.C.D

Якщо ви подаєте лише одну частину, то якщо вона менше 255 (максимум для октету), вона обробляється як октет, як вище, але якщо вона більша за 255, вона перетворюється і перекочується в наступне поле (тобто mod 256).

Є кілька крайових випадків, таких як надання більш ніж чотирьох частин, схоже, не працює (наприклад, google.comIP-адреса Pinging не буде працювати ні для одного, 0.74.125.226.4ні для 74.125.226.4.0).

Ви також можете використовувати шістнадцяткові позначення як у пунктирній, так і у плоскій формі, але потрібно відформатувати їх, попередньо очікуючи 0xна кожен октет.


Отже, існує безліч способів представити IP-адресу (IPv4). Ви можете використовувати плоский або крапковий (або пунктирний-потрійний, пунктирний-подвійний або навіть крапковий-одинарний) формат, і для кожного з них ви можете використовувати (або навіть змішувати та зіставляти) десятковий, вісімковий і шістнадцятковий. Наприклад, ви можете ввести пінг google.comтакими способами:

  • google.com  (Доменне ім'я)
  • 74.125.226.4  (пунктир)
  • 1249763844  (плоска десяткова)
  • 0112.0175.0342.0004  (пунктир)
  • 011237361004  (плоский восьмикутник)
  • 0x4A.0x7D.0xE2.0x04  (пунктир)
  • 0x4A7DE204  (плоский шестигранник)
  • 74.0175.0xe2.4  (ಠ_ಠ)

(Слава богу, що підтримка бінарних нотацій не додана!)


Застосування :

У вашому випадку pinging 192.168.072використовує третій формат у наведеній вище таблиці ( A.B.0.C), тож ви насправді пінгінгу 192.168.0.072. Далі, оскільки у вас є попередній нуль на останній частині, він трактується як вісімковий, який у десятковій частині дорівнює 58.

Таємниця вирішена.


Зауважте, що, хоча команда Windows pingдозволяє настільки широкий спектр форматів для введення та інтерпретує нестандартні формати у видимий спосіб, це не обов'язково означає, що ви можете використовувати такі формати скрізь. Деякі програми можуть змусити вас надати всі чотири частини крапки з пунктиром, інші можуть не дозволяти змішувати та співставляти десятковий і восьмеричний тощо.

Також адреси IPv6 ще більше ускладнюють логіку розбору та прийнятність формату введення.


Додаток :

syss вказував, що якщо ви використовуєте недійсний символ в одному з чисел (наприклад, 8або 9при використанні восьмеричного, gв шістнадцятковому режимі тощо), то pingце досить розумно, щоб розпізнати це і інтерпретувати його як рядок (-al? -ic?) URL, а не як числова IP-адреса.

(Оскільки той, хто мав численні аневризми та серцеві напади, намагаючись написати нібито «простий» код для розміщення експоненціально вибухової кількості перестановок значень даних, я розумію, що це, здається, - правильно обробляє всі вхідні зміни; в цьому випадку, принаймні 3 1 +3 2 +3 3 +3 4 = 120 варіантів.)

Отже, визначаючи, як 010.020.030.040буде ping, 8.16.24.32як очікувалося, перехід 010.020.030.080до pingбуде розглядатися як URL-адреса, а не IP-адреса, як, наприклад, foo.bar.baz.comяка (але, на жаль, не існує). Іншими словами, він намагається пінг піддомену 010на піддомен 020в домені 030на домені верхнього рівня 080. Однак, оскільки 080не є дійсним TLD (як .com, .netі їхні приятелі), з'єднання не вдається відразу на першому кроці.

Те саме відбувається з тим, 090.010.010.010де недійсний символ знаходиться в іншому октеті. Так само 0xf.0xf.0xf.0xfпінг 15.15.15.15, але 0xh1.0x1.0xg0.0fне вдається.

Ну добре, я думаю, що це ви отримуєте за те, що не володієте кількома базами даних.

Напевно, простіше і безпечніше просто переконатися, що завжди використовувати 4-крапкові ("40q"? "Quaddy-quad"? "Cutie-q"?) Адреси.

Тому продовжуйте вивчати основи чисел . Ви зможете продемонструвати себе і прожити життя партій, і, як кажуть, є 10 типів людей: тих, хто знає бінарне, і тих, хто цього не робить.

Давайте навіть не думати про IPv6 адреси; Я думаю, що вони одна з 111 печаток !!!


39
Надмірне ускладнення? Експериментація може бути дуже корисною і в цьому випадку дала хорошу відповідь; але без теорії чи документації чи стандартів ви можете пропустити критичний фактор і не знати цього. Або ви можете визначити, як працює одна конкретна версія, і помилитесь приблизно в 90% реалізацій там. Або ви можете придумати правила, які пояснюють результати ваших експериментів, але вони складніші за передбачені правила. У цьому випадку я думаю, що правила документації (для inet_aton()) простіші в одному відношенні - ніяких умов для "під / понад 255".
LarsH

71
Гей, дивись! "Наукова" частина Інформатики робить вигляд! (гіпотезувати, експериментувати, перевірити)
Ізката

13
@LarsH, але це мій погляд, що pingкоманда (принаймні, в Windows) подібна до багатьох програм Microsoft (особливо горезвісного) IE. Він намагається бути надто прощальним і приймати все, що ви кинете на нього, і намагається його інтерпретувати. Так, є офіційний документ про формати IP-адреси, але це не питання про ISO та RFC, це практично, я щось зробив і на це дивне питання, на яке можна відповісти, не вдаючись до (правда, довгий, сухий, нудний) технічні умови) - хоча посилання на них, якщо ОП хоче їх прочитати, також добре.
Synetech

6
0-префіксальний восьмеричний аналіз слід повністю відмовитися, окрім chmod. Це воно. Це єдиний виняток для дозволеного восьмерика. Період.
Джеймс Данн

6
це корисно для перетворення REX HEX в DEC. lol ~C:\>ping 0xffffcc Pinging 0.255.255.204 with 32 bytes of data:
wilson

147

Для цього є дві причини:

По-перше, префікс '0' вказує восьмеричне число. Оскільки oct (072) = dec (58), 192.168.072 = 192.168.58.

По-друге, "0 до останнього" 0 можна скинути з IP-адреси як скорочення . 127.0.1 інтерпретується як 127.0.0.1, а у вашому випадку 192.168.58 інтерпретується як 192.168.0.58.


7
Він не групує нулі. Він фактично розглядає кожну крапку як роздільник, відповідний наступній границі байтів. Таким чином, IP-адреси 2130706433 та 127.0.0.1 - це однакові адреси.
Серж

2
точніше, це чотиризначні позначення у випадку IP-адреси
Guillaume86,

4
Знаменитий ведучий нуль потрапив ще раз!
Люк М

2
тепер це справжня відповідь!
l --'''''--------- '' '' '' '' ''

2
Ця відповідь є невірною та оманливою. Випадання 0 в 1.0.2.3 (1.2.3) дає іншу IP-адресу (1.2.0.3).
sch

101

Окрім важливого моменту @ neu242 щодо восьмеричного позначення та зауваження, що IP-адреси можна скоротити, інший критичний фрагмент - це те, як інтерпретуються скорочені IP-адреси.

Можна наївно здогадуватися, що якщо деякі з чотирьох чисел відсутні, аналізатор додасть заповнені нулем байти в кінець (або на початок) послідовності байтів. Але це не відповідає поведінці, про яку повідомляє ОП: 192.168.072 було розбито на 192.168. 0 .58, а не як 192.168.58. 0 , ні 0 .192.168.58.

Мабуть, для Windows та Linux ping (версія, яку ви пробували, та ті, яку я спробував) використовуйте щось еквівалентне inet_aton () для розбору аргументу IP-адреси. Сторінка man для inet_aton () говорить:

The address supplied in cp can have one of the following forms:

 a.b.c.d   Each of the four numeric parts specifies a byte of the address; the
           bytes are assigned in left-to-right order to produce the binary
           address.

 a.b.c     Parts a and b specify the first two bytes of the binary address.
           Part c is interpreted as a 16-bit value that defines the rightmost
           two bytes of the binary address.  This notation is suitable for
           specifying (outmoded) Class B network addresses.

 a.b       Part a specifies the first byte of the binary address.  Part b is
           interpreted as a 24-bit value that defines the rightmost three bytes
           of the binary address.  This notation is suitable for specifying
           (outmoded) Class C network addresses.

 a         The value a is interpreted as a 32-bit value that is stored directly
            into the binary address without any byte rearrangement.

Отож, у вас він є ... 192.168.072підходить до abc-шаблону, тому 072(після розбору як восьмеричного числа) інтерпретувався як 16-бітове значення, яке визначає найправіші 2 байти двійкової адреси, еквівалентні 0.58.

Наведені вище правила еквівалентні тому, що якщо будь-яке з чотирьох чисел відсутнє, необхідні заповнені нулем байти додаються безпосередньо перед останнім заданим числом ... не в кінці, ані на початку рядка байтів. (Виражаючи це таким чином, працює, якщо останнє вказане число менше 256.)

Зауважте, що новіші версії ping можуть не допускати такого виду скорочень, а також восьмеричного тлумачення. Джерело 2010 Номер iputils (включаючи пінг) , які я знайшов використовує inet_pton () , а не inet_aton () для розбору IP - адреса аргументу. Сторінка man для inet_pton () говорить:

На відміну від inet_aton (3) та inet_addr (3), inet_pton () підтримує IPv6 адреси. З іншого боку, inet_pton () приймає лише адреси IPv4 у крапково-десятковій нотації, тоді як inet_aton (3) та inet_addr (3) дозволяють більш загальні позначення чисел і крапок (шістнадцятковий і восьмеричний формати чисел та формати, які не містять " t вимагати, щоб усі чотири байти були чітко записані).


12
Це, безумовно, найкраща відповідь ІМХО.
Джош

У Windows, яку ви шукаєте inet_addrв Winsock.
користувач7116

24

Ви також повинні врахувати, що ip може бути представлений цілими числами, що додаються разом за значенням їх позиції.

192.168.0.58 is :
  192 * 256^3
+ 168 * 256^2
+   0 * 256^1
+  58 * 256^0

Ось класна річ:

192.168.58 буде 192.168.0.58, оскільки

    0 * 256^1 
+  58 * 256^0 
=  58

192.11010106 також буде 192.168.0.58, оскільки

  168 * 256^2 
+   0 * 256^1 
+  58 * 256^0 
= 11010106

3232235578 також буде 192.168.0.58, оскільки

  192 * 256^3 
+ 168 * 256^2 
+   0 * 256^1 
+  58 * 256^0 
= 3232235578

1
"192.168.56 буде 192.168.0.56, тому що 0 * 256 ^ 1 + 58 * 256 ^ 0 = 58" Ви впевнені? Ви очікували, що 168 у першому випадку буде помножено на 256 ^ 1, а в другому - 256 ^ 2. Аналогічно 192 було б помножено на 256 ^ 2 проти 256 ^ 3. Тож 192.168.56 міг би = = 192.168.0.56, лише якщо існують додаткові правила, такі як падіння нулів.
LarsH

@LarsH, я думаю, що тут йдеться про те, що це базується зліва направо, на відміну від "нормального" підрахунку, де ми базуємо все з місця 1. Отже, перша крапка призводить до того, що ліворуч від неї множиться на 256 ^ 3, друга на 256 ^ 2, третя на 256. Якщо зліва від неї немає точки, то вона додається без множення на 256 ^ н. Так 1.2.3. (1.2.3.0) був би іншим, ніж 1.2.3 (1.2.0.3), якщо я правильно розумію.
iX3

@ iX3: якби це було так, то "192.168.56 буде 192.168.0.56" було б невірно, оскільки в першому випадку 56 було б помножено на 256 ^ 1, тоді як у другому випадку 56 було б помножено лише y 256 ^ 0. І 192.168.072 ОП трактуватиметься як 192.168.58.0 замість 192.168.0.58.
LarsH

Трохи оманливим є той факт, що адреса 0 має 3-ю цифру. Розглянемо цю адресу 192.168.1.56 3-цифрова форма буде 192.168.312 Тому, що 1 * 256 ^ 1 + 56 * 256 ^ 0 - 312
vesquam

1
Точки служать лише для того, щоб окреслити, які числа слід помножити на потужність 256. Парсер шукає першу крапку і помножує число перед нею на 256 ^ 3. Повторіть для 2-ї та 3-ї крапки, але відповідно на 256 ^ 2 і 256 ^ 1 відповідно. Потім він додає всі результати разом (деякі імпл. Можуть замість цього тримати загальний результат, хоча результат той самий). Якщо будь-яка з цих точок відсутня, вона просто не робить множення і просто додає кінцеве число до поточного загального числа. Ось чому це 1.2.3.призводить до помилки, оскільки аналізатор не може знайти останнє число, яке слід додати до загальної суми.
Джастін ᚅᚔᚈᚄᚒᚔ
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.