Чому перенаправлення виводу sed на той самий вхідний файл робить мою машину невідповідною?


13

Я намагався sedзамінити деякі ключові слова у великому файлі (100 Мб). Я не знав про -iваріант (inplace), тому першою моєю спробою було перенаправлення так:

sed 's/original/edited/g' file.log >> file.log

Після цього сталося те, що мій комп'ютер зупинився, майже немає клавіатури. Я спробував іншу консоль Ctrl+ Alt+, F1але після повільного введення імені користувача він також зупинився. Без клавіатури, єдиним моїм варіантом було апаратне відновлення машини. Після входу в систему я побачив, що файл file.log становить близько 8 ГБ.

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


7
Це одноядерна машина? Дуже дивно здається, що це повинно було поставити сучасний комп’ютер на коліна. Наповнений диск, так. Так, ви використовуєте 100% одного з ваших сердечників, так. Але повний крах?
тердон

Чи є щось особливе у цьому файлі? якщо це не проблема, чи можете ви розмістити її вміст на пастебіні?
Сергій Колодяжний

Також, яка кількість вашої пам’яті? Не могли б ви надати нам вихід free -h ?
Сергій Колодяжний

Навіщо використовувати редактор потоків в першу чергу, коли потрібно змінити файл? ex -sc '%s/original/edited/ge|x' file.logВи повинні робити те, що Ви хочете, ідіоматичним способом UNIX без sed -iпобічних ефектів.
Девід Онгаро

Зауважте, що навіть якщо ви робите це правильно (будь-яким із методів, які надають люди), це може бути важко робити такий матеріал у файл журналу, що належить до активного процесу.
Випадково832

Відповіді:


10

Як уже було сказано, >>додається до файлу, тож ваша sedкоманда буде сидіти там, читаючи тільки що виведені рядки, а потім виводити їх ще трохи. Якщо ви хочете , щоб замінити файл на місці, >все ще не буде працювати, але ви знаєте про sed«S -iваріант, який, безумовно , той , який ви хочете.

Якщо ви абсолютно впевнені, що хочете додати файл, який ви читаєте як потік, і хочете зробити це лише один пропуск, подумайте про використання spongeз moreutilsпакету;

sed 's/original/edited/g' file.log | sponge >> file.log

spongeчитає з stdin в пам'ять до EOF, потім скидає весь його вміст у stdout, тому sedвін потрапить у кінець файлу, перестане його читати, закрити, а потім губка почне додавати до нього.


2
spongeце хороша утиліта знати, але sedвже є -iваріант: -i[SUFFIX], --in-place[=SUFFIX], edit files in place (makes backup if SUFFIX supplied).
Джошуа Тейлор

@JoshuaTaylor, OP використовував >>, що додає, а не >замінює. Зрозуміло, що ОП спеціально згадував -iу публікації, і це здається набагато більш поширеним випадком використання, ніж цей, але я подумав, що варто зазначити, що конкретна операція, яку ОП розмістила, була можлива без зайвих фафів, якщо ви справді впевнений, що це ти хочеш зробити.
ymbirtt

1
Я згадував це тут, тому що це було ключовим у прийнятій відповіді . Тим НЕ менше, я буду щиро радий дізнатися про губці ; це новий інструмент для мого набору інструментів, і гідний заробіток саме для цього.
Джошуа Тейлор

1
Ах! Я бачу. Я перегляну свою відповідь, щоб зробити це трохи зрозумілішим. Також, якщо вам сподобалось sponge, погляньте vipe. moreutilsце просто чарівний пакет, наповнений речами, які ти ніколи не знав, що тобі потрібно
ymbirtt

18

Ваша sedкоманда намагалася прочитати файл, до якого він додався. Він ніколи не дійде до кінця файлу, але з'їсть багато процесорного часу, намагаючись. Ось чому був винайдений ^ С (процес переривання струму).


Я не думаю, що ^ C був там варіантом ... він перейшов до HALT, тобто жоден миготливий курсор не застряг!
EKons

18

Повернення до файлу, з якого ви читаєте, ні в якому разі не є гарною ідеєю, оскільки ви отримаєте файл, який постійно зростає. Якщо ви дійсно хочете записати назад у файл, вам слід використовувати -iпрапор:

sed -i 's/original/edited/g' file.log

або якщо ви хочете створити резервну копію перед внесенням змін, ви можете додати до -iпрапора суфікс файлу :

sed -i.bak 's/original/edited/g' file.log

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


1
Я здивований, що це прийнята відповідь, оскільки вона навіть не стосується питання ОП"I really would like to understand why the execution of that command was able to make the system so unresponsive, and if mechanisms exist at the system level to trigger alerts and kill the offending process?"
Стів

@Steve Щодо того, як він зупинився, я звернувся, але в другій частині ви праві. Я не звертався до цього, тому що не знаю відповіді на це. Ми обстежили команду після обговорення в чаті і отримали абсолютно різні результати на різних машинах та операційних системах. Приклад: На машині з аркою він дозволяє лише зростати файлам назавжди, але не робить машину безвідповідальною. На моїй машині Ubuntu я отримав такий же результат, як і запитуючий, без шансу вбити процес. Друга машина, що тестувала те саме в Ubuntu VM, зупинилася.
Videonauth

straceВсього процес на інший бік didtn відтворити результат і це на моїй машині і на машині іншого користувача. Звичайно, є механізм, за допомогою якого ви можете вбивати невідповідні програми, але якщо ваш апарат не реагує, вам залишається лише один варіант, скидання його. Я все ще тестую це, і перш ніж я не зрозумів повністю, що викликає описану поведінку, я не в змозі вирішити цю частину питання.
Videonauth

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

Якщо вас цікавить інша точка даних; Я спробував це на машині CentOS з досить невеликим файлом, і він зробив точно так само, як і моє губне рішення нижче. Я гадаю, що для невеликого файлу sedбуде зберігатися вся річ у пам'яті, а потім закрити її, а не тримати ручку. З файлом ~ 100 Мб, як і в ОП, він зростав нескінченно, але не цеглив машину.
ymbirtt
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.