Пінг смерті! FreeBSD виправляє аварійну помилку в мережевому інструменті PlatoBlockchain Data Intelligence. Вертикальний пошук. Ai.

Пінг смерті! FreeBSD виправляє аварійну помилку в мережевому інструменті

Одним із перших низькорівневих мережевих інструментів, про який дізнається будь-який користувач комп’ютера, є venerable ping утиліта

Команда, названа на честь однойменного звукового ефекту з будь-якої сцени старовинного військового фільму про підводні човни, є метафоричним відлунням (бачите, що ми там зробили?) підводної версії RADAR, відомої як SONAR.

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

Інтригуюче те, що ви, напевно, чули абревіатуру TCP/IP, яка використовується як загальний опис зв’язуючого протоколу, який підтримує Інтернет, ping технічно взагалі не використовує TCP/IP.

Фактично TCP/IP є скороченням від протокол керування передачею через Інтернет-протокол, і стосується механізму досить високого рівня для надсилання даних через Інтернет таким чином, що сама мережа вносить багато запитань «чи справді це працювало належним чином?» зусилля для вас.

Наприклад, у TCP-з’єднаннях будь-які фрагменти даних, які ви надсилаєте, гарантовано надійдуть на інший кінець неушкодженими або спричинять помилку, щоб ви знали, що вони цього не зробили.

Крім того, навіть якщо різні фрагменти даних в кінцевому підсумку йдуть різними маршрутами через Інтернет (наприклад, через балансування навантаження, тимчасові збої або інші помилки, які можна виправити), і навіть якщо деякі фрагменти надходять довше, ніж інші, дані TCP будуть правильно буферизовані і представлені в правильному порядку на іншому кінці.

Пінг буває різним

Команда ping однак зазвичай використовується для перевірки того, чи комп’ютер, який вас цікавить, взагалі підключений до Інтернету, особливо якщо він не підтримує TCP-з’єднання високого рівня, які ви очікуєте, наприклад отримання електронної пошти чи дозвіл входу через SSH.

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

В результаті ping використовує протокол набагато нижчого рівня, ніж TCP.

Справді, ping навіть не використовує більш звичайний двоюрідний брат TCP, UDP, скорочення від протокол дейтаграм користувача, який є способом передачі блоків даних, який є швидким і легким, але в народі його називають "надсилай і сподівайся" (або, якщо ви цинічний сорт, як "спрей і молись").

Сам UDP не інформує вас про те, чи потрапили ваші дані на інший кінець, чи ні, і навіть якщо вони надходять неушкодженими, UDP не відстежує порядок, у якому ваші пакети були надіслані спочатку, тому він не може перегрупувати їх у інший кінець, якщо вони потрапляють туди не по порядку.

Ping, якщо це варте, використовує протокол дуже низького рівня, спеціально розроблений для цілей усунення несправностей і переконфігурації мережі, відомий як ICMP, або протокол повідомлень керування Інтернетом.

Зазвичай ICMP обробляється прямо в ядрі операційної системи, тому пакети ICMP/IP майже напевно пройдуть, навіть якщо мережеве програмне забезпечення вищого рівня не встановлено належним чином. ICMP, зокрема, включає два спеціальні типи повідомлень:

  • Введіть 0x08. Офіційно зателефонували ICMP Echo, Це свого роду пакет зазвичай називається ехо-запитом. Це те, що ping програма надсилає, щоб перевірити наявність активних комп’ютерів у мережі.
  • Введіть 0x00. Офіційно зателефонували ICMP Echo Reply, цей тип пакета саме те, що там написано. Комп’ютер, який активний, знаходиться в режимі онлайн і не налаштований на блокування трафіку ICMP Echo, має надсилати такий пакет прямо на комп’ютер, який його запитав.

Подобається це:

$ ping -C 3 -p 4e414b45445345435552495459 nakeSecurity.sophos.com Шаблон: 0x4e414b45445345435552495459 ping news -sophos.go -vip.net (192.0.66.227) 56 (84). 64 байти з 192.0.66.227 (192.0.66.227): icmp_seq=1 ttl=53 час=84.0 мс 64 байти з 192.0.66.227 (192.0.66.227): icmp_seq=2 ttl=53 час=85.1 мс 64 байти з 192.0.66.227 .192.0.66.227 (3): icmp_seq=53 ttl=84.8 time=3 мс --- статистика пінгу news-sophos.go-vip.net --- 3 пакети передано, 0 отримано, 2004% втрат пакетів, час 84.025 мс rtt хв/ середнє/макс./середнє відхилення = 84.644/85.062/0.446/XNUMX мс

Щоб побачити a ping у дії на дещо нижчому рівні ми використаємо код Lua, який ви знайдете в кінці статті, щоб створити власний пакет ICMP Echo та прочитати відповідь, яка надходить, якщо така є:

$ sudo luax ping.lua nakedsecurity.sophos.com Надсилання запиту ICMP ECHO на 192.0.66.227 --> 00000000 08 00 03 02 bb 5a 6f 1d 50 69 6e 67 52 65 71 75 |.....Zo.PingRequ| 00000010 65 73 74 4d 65 73 73 61 67 65 20 42 42 35 41 36 |estMessage BB5A6| 00000020 46 31 44 |F1D | Повернувся--> 00000000 45 00 00 37 f6 af 00 00 35 01 94 7f c0 00 42 e3 |E..7....5.....B.| 00000010 XX XX XX XX 00 00 0b 02 bb 5a 6f 1d 50 69 6e 67 |.........Zo.Ping| 00000020 52 65 71 75 65 73 74 4d 65 73 73 61 67 65 20 42 |Повідомлення запиту B| 00000030 42 35 41 36 46 31 44 |B5A6F1D |

До речі, нам потрібно було скористатися sudo вище, щоб запустити наш сценарій із правами суперкористувача, оскільки ми створили так званий a необроблений IP-сокет – той, який може бути створений у будь-якому базовому форматі, який нам подобається, включаючи TCP, UDP і, за потреби, ICMP.

У багатьох системах Linux/Unix ping Команда, надана вашим дистрибутивом, працює без явного надання привілеїв адміністратора, зазвичай через те, що вона встановлена ​​зі спеціальними можливостями безпеки або з setuid встановлено прапорець, що означає, що він починає працювати під іншим обліковим записом користувача, ніж той, хто його запустив.

Добре розроблений ping програми, звичайно, автоматично відкидають свої додаткові привілеї, коли вони відкривають потрібний їм необроблений сокет.

Ми пропустили цей код для скидання привілеїв у нашому прикладі сценарію задля стислості. Ви можете використовувати posix.unistd.setpid() функція перемикання на непривілейований обліковий запис після створення сокета, але перед надсиланням або отриманням будь-яких даних.

Вивчення відповіді

Як ви могли впізнати в дампі даних із нашого сценарію вище, функція мережевого сокета, яку ми використовуємо для зчитування даних із сервера-відповідача, включає не лише дані ICMP Echo Reply, але й низькорівневий IP (заголовки Інтернет-протоколу) у базовому пакеті.

Ми не намагалися проаналізувати або іншим чином обробити ці дані, але FreeBSD ping програмі потрібно зробити це, щоб зрозуміти відповідь, включаючи будь-які повідомлення про помилки, які повертаються.

Якщо ping буде певним чином відхилено, Echo Reply зазвичай включатиме не лише власні IP-заголовки (як показано вище), але й еталонну копію IP-заголовків і даних ICMP, які з’явилися в оригінальному вихідному запиті.

Заголовки пакетів IPv4 зазвичай виглядають приблизно так, як ви бачите вище, де починаються заголовки IP 45 00 00 37... і продовжуйте загалом 20 байт, до байтів, показаних як ...XX XX XX XX, яка є IP-адресою мого ноутбука.

Подобається це:

00000000 45 00 00 37 f6 af 00 00 35 01 94 7f c0 00 42 e3 |E..7....5.....B.| 00000010 ХХ ХХ ХХ ХХ |.... | Версія IP і довжина заголовка: 0x45 (4 = IPv4, 5 = п'ять 32-розрядних слів, тобто 20 байт. Тип служби та дані про перевантаження: 0x00 Загальна довжина пакета: 0x0037 (десяткове 55) Інформація про послідовність: F6 AF 00 00 Час до -live (стрибки вліво): 0x35 (десятковий 53) Тип протоколу: 0x01 (ICMP) Контрольна сума: 0x947F (десятковий 38015) IP-номер комп’ютера-відправника: C0 00 42 E3 (192.0.66.227 = nakedsecurity.sophos.com) IP-адреса одержувача (мій ноутбук): XX XX XX XX (ВИДАЛЕНО = мій власний IP-номер)

FreeBSD ping програмісти, схоже, припускали, що заголовки такого типу справді завжди будуть рівно 20 байтів, виходячи з цього значення довжини заголовка в першому байті 0x45, що позначає IPv4 (0x4?) із 5-DWORD (0x?5), або 20-байтовий заголовок.

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

Ви можете здогадатися, куди це йде.

Цей перший байт у заголовку IPv4 законно може мати будь-яке значення 0x45 (мінімальний розмір заголовка 5 DWORD, або 20 байт, як показано) до 0x4F (що позначає 15 DWORD, оскільки 0xF є десятковим числом 15 або загалом 60 байтів даних заголовка), таким чином акуратно дозволяючи додаткові 40 байт даних заголовка.

Ці рідкісні, але допустимі додаткові байти заголовка можна використовувати для різноманітних дивних і незвичайних «функцій» із цікавими назвами, такими як Вибіркове режисерське мовлення, Контроль експериментального потоку та Вихідний багатоадресний пакет – речі, про які ми чули, але ніколи свідомо не використовували чи навіть бачили.

Остерігайтеся кіберзлочинців, які випробовують вас

Як ви можете собі уявити, враховуючи, що ці додаткові поля майже ніколи не використовуються, ви можете ніколи не побачити пакет IPv4 з чимось іншим, ніж 0x45 на початку та з 20 байтами даних заголовка загалом, якщо ви не зіткнулися з купою кіберзлочинців, які готові випробувати вас.

На жаль, нічого не може завадити зловмиснику підлаштувати сервер, який здогадується, чи використовуєте ви FreeBSD, і навмисно генерує великі пакети ICMP/IP Echo Reply, щоб спровокувати переповнення буфера стека всередині вашого ping програми.

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

У кращому випадку ваші ping програма завершить роботу; у гіршому випадку, як великодушно визнає консультація з безпеки FreeBSD, «зловмисний хост може ініціювати віддалене виконання коду під час ping».

На щастя, як і автори FreeBSD вказати, «Процес ping працює в пісочниці в режимі можливостей на всіх уражених версіях FreeBSD і тому дуже обмежений у тому, як він може взаємодіяти з рештою системи в точці, де може виникнути помилка».

Іншими словами, латати обов'язково потрібно, але ризики можна вважати скромними.

Помітно, що ping програма не лише заблокована в пісочниці, але й не працює від імені користувача root, коли виникає помилковий код, як підтверджено в пораді щодо безпеки: "Коли ping запускається, він створює необроблений сокет, необхідний для виконання своєї роботи, а потім скасовує свої підвищені привілеї».

Як описано вище, повноваження суперкористувача потрібні лише для отримання необробленого IP-сокета від операційної системи, а не для використання sendto() та recvfrom() функціонує на цьому розетці згодом.

Ця помилка отримала офіційний ідентифікатор CVE-2022-23093; це задокументовано в консультації з безпеки FreeBSD-SA-22:15.ping.

Що ж робити?

  • Якщо ви користувач FreeBSD, просто оновіть уражені випуски (FreeBSD 12 і FreeBSD 13) до їхніх останніх версій, де цю помилку виправлено.
  • Якщо ви мережевий програміст, завжди переконайтеся, що ви врахували заголовки пакетів, які можуть вказувати на незвичні варіації розміру. Той факт, що ви самі ніколи не бачили жодної варіації, не завадить вам зіткнутися завтра з пакетом, який є незвичайним, але цілком законним.
  • Якщо ви менеджер мережі, подумайте про блокування пакетів IPv4 із заголовками IP, розмір яких не перевищує 20 байт. Якщо вам справді здається, що потрібно дозволити деяким програмним продуктам використовувати незвичайні параметри заголовка IPv4, подумайте про реєстрацію цих незвичайних пакетів, щоб дізнатися, чому.

Бережіть себе там!


ПРИКЛАД КОДУ ДЛЯ ДЕМОНСТРАЦІЇ ПІНГ-ТРАФІКУ


Часова мітка:

Більше від Гола безпека