Home » Ошибки » Диск занят на 100% и не понятно чем, df и du показывают разные значения

Диск занят на 100% и не понятно чем, df и du показывают разные значения

Столкнулся сегодня с нестандартной ситуацией, когда на сервере исчезало место на диске, а я не мог понять кто его занимает. Хотя ситуация не такая уж нестандартная, но из-за ряда случайностей, она получилась в какой-то мере курьезной. Я по сути на ерундовую ошибку потратил много времени.

Началось все с того, что один из разработчиков написал мне, что на сервере кончается место и он не понимает, кто его занимает. У меня не было времени подробно разбираться, я просто добавил на сервер места. Для справки, расскажу как это сделать, полезная информация.

В данном случае сервер это виртуальная машина, у нее один диск и один корневой раздел, на котором все расположено. На диске ext4 поверх lvm. Задача увеличить свободное место в корневом разделе без перезагрузки сервера. С lvm все очень просто. Добавляем к виртуальной машине диск нужного размера и выполняем в консоли:

# vgextend vg00 /dev/sdb
# lvextend -r -l +100%FREE /dev/vg00/root

Иногда конструкция -l +100%FREE не срабатывает при увеличении раздела, хотя при создании все в порядке. Тогда можно указать добавляемый размер явно:

# lvextend -r -L+10G /dev/vg00/root

В моем примере есть системный диск sda, на котором расположен том vg00, а на нем логический раздел root. Мы расширяем том vg00 с помощью нового диска sdb, а затем расширяем логический раздел root до 100% свободного места тома.

После этого системный раздел будет увеличен сразу, перезагрузка не требуется. Можно не добавлять отдельный диск, а увеличить существующий через свойства диска в панели гипервизора. Тогда вам нужно будет на новом свободном месте на диске sda сделать новый раздел, например, sda2 и расширить том с его помощью. Как делать лучше, увеличивать диск или добавлять новый — не знаю, я и так, и так делаю. Тем не менее, считаю это плохой практикой, лучше сразу спланировать раздел диска и потом уже его не трогать. Данный способ это крайний случай, когда по-другому уже никак.

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

# du -s *|sort -nr|cut -f 2-|while read a;do du -hs $a;done

Получим сразу в консоли размер всех директорий. У меня получилось так, что если сложить объем всех директорий, то получится занятыми где-то 6 Гб диска. А если выполнить команду

# df -h

То видно, что корень занят на 100%, а его размер равен 20-ти Гб. Кто занял остальные 14 гигабайт места было не понятно.

Стал рассуждать, как такое может быть. Ситуация не такая уж и редкая, раньше встречался с этим. Суть в том, что удален какой-то большой файл, который до сих пор открыт приложением. Но смысл в том, что на этом сервере такого файла никогда не было. Разработчик сказал, что ничего особенного последнее время на сервере не делал.

Более того, я посмотрел мониторинг сервера и заметил, что свободное место уменьшалось плавно в течении последних двух дней. Никакого скачка не было. Какой-то директории с миллионами мелких файлов не было то же. Подобная директория теоретически может создать такую непонятку со свободным местом, если размер одного файла меньше блока, в котором этот файл хранится.

Переходим к конкретике. Когда у вас сложилась ситуация, что не понятно, куда делось свободное место, которое ничем не занято, первым делом проверьте удаленные файлы, которые все еще открыты каким-то приложением:

# lsof | grep '(deleted)'

Предпоследний столбец это размер файла. На самом деле, эту команду я сразу же выполнил на сервере, но невнимательно посмотрел. В выводе команды была всякая мелочь и пару логов nginx в самом начале. Я не посмотрел внимательно на размер этих логов, так как никак не думал, что они могут быть огромными.

А причина проблем со свободным место была вот в чем. Пару недель назад разработчик зашел на сервер и просто удалил лог ошибок nginx. И не перезапустил его. Он где-то неделю так проработал, а потом резко увеличил интенсивность записи в этот файл. Он постоянно рос, пока не занял все пространство раздела. После этого я увеличил раздел, и он снова плавно все занял.

Смысл в том, что nginx несколько дней писал в удаленный файл, который занимал место на диске. Если бы разработчик не трогал этот лог, то он бы ротировался раз в сутки и проблемы бы не было. А так он из системы был удален, но реально постоянно рос, его не было видно и он не обрабатывался с помощью logrotate.

В итоге через пару часов, когда я уже готовил подменный сервер, еще раз внимательно все проверил и обратил внимание на удаленные логи и место, которое они занимают. Вопрос решился простым перезапуском службы nginx. Он тут же отцепил свой лог файл и начал писать в новый. А старый реально удалился из системы и освободил место.

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

Можно оценить примерно, сколько стоит аккуратная работа. Если бы я просто перезагрузил сервер, то решил бы вопрос за 5 минут. Но пришлось действовать наверняка и тратить время. Когда-то это оправданно, когда-то нет. Лично я всегда перестраховываюсь и действую наверняка.

11 комментариев

  1. Аноним

    Стоило упомянуть правильный способ ручной очистки логов, вроде cat /dev/null > ./file.log

  2. Аноним

    Утилиткой ncdu можно размер каталогов посмотреть.

  3. Можно еще так (топ-10):
    du . —max-depth=1 -ah | sort -rh | head -10

  4. Не слабую раскрутил головоломку. Поздравляю.

  5. А у меня в FreeBsd на команду : lsof | grep ‘(deleted)’ вот что пишет:
    lsof: WARNING: compiled for FreeBSD release 11.1-RELEASE-p10; this is 11.2-RELEASE.
    lsof: WARNING: /root/.lsof_A9t was updated.

    Что делать как посмотреть?

    • Так в ошибке все написано. У вас бинарник lsof скомпилирован под версию 11.1, а у вас стоит 11.2 Надо обновить, как я понимаю, lsof. Если это возможно, конечно. Я уже давно не работают с freebsd и отвык от нее.

  6. Руслан

    Добавляем к виртуальной машине диск нужного размера и выполняем в консоли:

    # vgextend vg00 /dev/sdb

    как тебе это удалось сделать интересно, увеличить корневой раздел без его размонитирования ???

    У тебя по идее должна была вылезти ошибка из серии exclusively. Mounted filesystem?

    • Так и удалось. LVM позволяет на ходу увеличивать размер тома и расширять файловую систему (даже корень / ) без остановки и перезагрузки. Если не веришь — просто проверь. Я постоянно использую эту возможность.

Добавить комментарий

Ваш e-mail не будет опубликован.

Нажимая кнопку "Отправить комментарий" Я даю согласие на обработку персональных данных.