Форум русскоязычного сообщества Ubuntu


Хотите сделать посильный вклад в развитие Ubuntu и русскоязычного сообщества?
Помогите нам с документацией!

Автор Тема: Утилита проверки фрагментированности ФС (btrfs/XFS/EXT2-3-4 b и другие)  (Прочитано 9735 раз)

0 Пользователей и 1 Гость просматривают эту тему.

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Утилита подсчитывает количество фрагментов во всех файлах (с учетом вложенных подкаталогов).
Создается лог с перечнем в виде <число фрагментов> <путь и имя файла> в файле /tmp/frag.log
Подсчитывается и показывается статистика.

Фрагментация свободного пространства или каталогов - не оценивается. Вся информация только по файлам. Если во вложенном каталоге смонтирована другая FS, то файлы с этой ФС сканироваться не будут. Для сканирования файлов к ним необходи доступ на чтение от лица пользователя исполняющего скрипт.

Последний вариант скрипта:
#!/usr/bin/env python3

import sys, subprocess, os, re

if len(sys.argv) > 1:
  wd = sys.argv[1]
  if not os.path.exists(wd):
    print ('Usage: frag_info.py [path_to_scan]\n'
           'When path_to_scan is not specified then it scans from current directory')
    quit()
else:
  wd = os.getcwd()
print('Fragmentation within %s\n' % wd)

cmd = ("find %s -xdev -type f -exec filefrag '{}' +  | " % wd +
       r"sed -e 's/^\(.*\): \(.*\) extent.* found$/\2 \1/' | "
       "sort -nr > /tmp/frag.log")
subprocess.call([cmd], shell=True)

total = totalf = fragmented = frags = 0
cnt = [0, 0, 0, 0]

with open('/tmp/frag.log', 'rt', newline='\n') as f:
  for line in f:
    totalf += 1
    fr, fn = re.findall(r'(\d+) (.*)', line)[0]
    fr = int(fr)
    if fr > 0:
      total += 1
      frags += fr
      if fr > 1:
        fragmented += 1
        if fr == 2:
          cnt[0] += 1
        elif fr <= 10:
          cnt[1] += 1
        elif fr <= 100:
          cnt[2] += 1
        else:
          cnt[3] += 1

if fragmented:
  cnt = [c/fragmented*100 for c in cnt]

exfrags = frags - total
tot =  'Totally: %d files (%d not empty) stored within %d fragments\n' % (totalf, total, frags)
tot += ('Totally %d fragments in %d fragmented files\n' % (exfrags, fragmented) if fragmented
                                                                                else '')
tot += ('Fragmentation factor by files {fragmented/total in %%}: %0.2f%%\n' %
                                                                 (fragmented / totalf * 100))
tot += 'Fragmentation factor by fragments {(fragments - files)/ files}: %0.3f\n' % (exfrags / total)
tot += '\nFragments per files:\n'
tot += ('   2   fragments: %0.2f%%\n 3-10  fragments: %0.2f%%\n'
        '11-100 fragments: %0.2f%%\n > 100 fragments: %0.2f%%'
        % (cnt[0], cnt[1], cnt[2], cnt[3]) if fragmented else '')
tot += '\n\nSee detailed log in /tmp/frag.log'
print(tot)

установка:
sudo -i
nano /usr/local/bin/frag_info
Вставляем код скрипта, только аккуратно - целиком.
далее: жмем CTRL+x, Y, Enter.
chmod a+x /usr/local/bin/frag_info

Далее переходим в желаемый каталог и там запускаем
sudo frag_info
Или запускаем в любом месте
sudo frag_info /путь_который_надо_просканировать


Сама идея утилиты изначально обсуждалась в теме BTRFS. Готова ли к использованию в 16.04?, но в дальнейшем тема была разделена т.к. утилита подсчитывает фактическую фрагментацию на любой файловой системе.

__________________________

AnrDaemon, можно в принципе и на баше это все сделать, но я в нем - не силен (мне на питоне как-то проще).

Вот в двух словах:

1. Вызываем filefrag (подавляем выводы об ошибках)
2. обрезаем пробелы - .strip())
3. Делим вывод по ":" - .split(': ')
4. Делим вторую часть [1] по пробелу - .split(' ')
5. берем первую половинку [ 0 ]
6. преобразуем в целое - int(...)

Это мы получили количество фрагментов у файла в виде числа.

Сам скрипт идет по всем вложенным каталогам и для каждого найденного файла (на баше будет что-то типа: find . --type f) пытается получить размер, если размер получили, то пробуем получить количество фрагментов, и если фрагментов больше одного то имя файла, размер и количество фрагментов сохраняется в список.

Полученный список сортируем по числу фрагментов (от большего к меньшему) и скидываем его в лог, далее формируем саммари.

« Последнее редактирование: 02 Апрель 2017, 13:15:56 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн AnrDaemon

  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 26070
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #1 : 14 Ноябрь 2016, 18:43:05 »
Как-то так и предполагал. Можно обойтись одним find . -type f -execdir /usr/bin/filefrag '{}' + - будет намного быстрее, чем вызывать filefrag на каждый чих. Плюс sort и немного awk для подсчётов.
Хотите получить помощь? Потрудитесь представить запрошенную информацию в полном объёме.

Прежде чем [Отправить], нажми [Просмотр] и прочти собственное сообщение. Сам-то понял, что написал?…

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #2 : 14 Ноябрь 2016, 22:55:03 »
AnrDaemon, что-то не работает команда :-\

Да и говорю же - в баше - не силен, к сожалению  :( поэтом взял готовый код, что theurs, предложил и чутка подправил.

... а понял что имелось в виду:
find . -type f -exec filefrag {} + Ща попробую еще sed прикрутить....

во
find . -type f -exec filefrag {} + | sed 's/: / /;s/ extent.*//'
дает список <файл> <число фрагментов>

Тлко как к нему сорт прикрутить - уже не понимаю.... сортировать то нужно по второму значению да еще не в строчном а в численном представлении....
« Последнее редактирование: 14 Ноябрь 2016, 23:37:19 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн AnrDaemon

  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 26070
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #3 : 14 Ноябрь 2016, 23:36:30 »
-execdir рекомендуется использовать всегда. Это безопаснее и имена файлов получаются короче.
А не получается, видимо, потому, что /usr/sbin/filefrag :)
Хотите получить помощь? Потрудитесь представить запрошенную информацию в полном объёме.

Прежде чем [Отправить], нажми [Просмотр] и прочти собственное сообщение. Сам-то понял, что написал?…

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #4 : 15 Ноябрь 2016, 01:44:04 »
AnrDaemon, Так без путей не понятно где лежит файл. :(
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн AnrDaemon

  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 26070
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #5 : 15 Ноябрь 2016, 01:50:05 »
Да пофигу. :) Имя файла обычно уникальное, а если нет - найти все и посчитать не проблема. Проблема - сам подсчёт. Вот тут надо будет AWK полирнуть.
Хотите получить помощь? Потрудитесь представить запрошенную информацию в полном объёме.

Прежде чем [Отправить], нажми [Просмотр] и прочти собственное сообщение. Сам-то понял, что написал?…

Оффлайн theurs

  • Активист
  • *
  • Сообщений: 457
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #6 : 15 Ноябрь 2016, 03:50:32 »
Как-то так и предполагал. Можно обойтись одним find . -type f -execdir /usr/bin/filefrag '{}' + - будет намного быстрее, чем вызывать filefrag на каждый чих. Плюс sort и немного awk для подсчётов.

Почему быстрее? filefrag и так вызывается только для файлов у которых размер больше 0.

а такие папки как /sys будут пропущены? Я первый раз запустил без пропуска и от рута, у меня комп через минуту перезагрузился, причем непонятно как - не было слышно пост сигналов и вообще как то это слишком быстро произошло (комп отдельно стоящий без монитора с доступом через ssh, стоит рядом так что все шумы от него хорошо слышны)

Пользователь добавил сообщение 15 Ноябрь 2016, 04:00:05:
Для ехт4 можно получить список файлов и их фрагментацию командой e4defrag -cv  /dev/sda1

<File>                                         now/best       size/ext
[1/50626][2/50626][3/50626][4/50626][5/50626].[79;0H.[K[5/50626]/lib/firmware/usbduxfast_firmware.bin
                                                 1/1              4 KB
[6/50626][7/50626].[79;0H.[K[7/50626]/lib/firmware/rtlwifi/rtl8723aufw_B_NoBT.bin
                                                 1/1             20 KB
[8/50626].[79;0H.[K[8/50626]/lib/firmware/rtlwifi/rtl8192cufw.bin
                                                 1/1             16 KB
[9/50626].[79;0H.[K[9/50626]/lib/firmware/rtlwifi/rtl8192cfw.bin
                                                 1/1             16 KB
[10/50626].[79;0H.[K[10/50626]/lib/firmware/rtlwifi/rtl8188eufw.bin
                                                 1/1             16 KB
[11/50626].[79;0H.[K[11/50626]/lib/firmware/rtlwifi/rtl8723befw.bin
                                                 1/1             32 KB
[12/50626].[79;0H.[K[12/50626]/lib/firmware/rtlwifi/rtl8723aufw_B.bin
                                                 1/1             24 KB
[13/50626].[79;0H.[K[13/50626]/lib/firmware/rtlwifi/rtl8192cufw_B.bin

...

[50625/50626].[79;0H.[K[50625/50626]/home/theurs/.bash_history          1/1              4 KB
[50626/50626].[79;0H.[K[50626/50626]/home/theurs/.profile               1/1              4 KB

<Fragmented files>                             now/best       size/ext
1. /var/log/samba/log.192.168.254.16           105/1              4 KB
2. /var/log/ppp0_watchdog                      175/1              4 KB
3. /var/log/samba/log.192.168.254.15            82/1              4 KB
4. /var/log/samba/log.192.168.254.18            80/1              4 KB
5. /var/log/samba/log.192.168.254.13            73/1              4 KB

 Total/best extents                             43868/41606
 Average size per extent                        36 KB
 Fragmentation score                            5
 [0-30 no problem: 31-55 a little bit fragmented: 56- needs defrag]
 This device (/dev/sda1) does not need defragmentation.
 Done.

возможно что то подобное есть и для бтрфс
« Последнее редактирование: 15 Ноябрь 2016, 04:00:05 от theurs »

Оффлайн AnrDaemon

  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 26070
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #7 : 15 Ноябрь 2016, 04:08:21 »
А при чём тут /sys ? …
И, да, зачем было запускать это на корень системы? Надо запускать на корень раздела.
А по поводу размера (и по поводу /sys, /proc и иже с ними тоже…),
find . -xdev -maxdepth 1 -type f -size +4k -exec /usr/sbin/filefrag '{}' + | while IFS=: read -r _n _t; do _c="${_t#" "}"; echo "${_c%% *} $_n"; done | sort -nr
("-maxdepth 1" - это для тестов… Для реальных прогонов это, естественно, надо убрать.)
Хотите получить помощь? Потрудитесь представить запрошенную информацию в полном объёме.

Прежде чем [Отправить], нажми [Просмотр] и прочти собственное сообщение. Сам-то понял, что написал?…

Оффлайн theurs

  • Активист
  • *
  • Сообщений: 457
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #8 : 15 Ноябрь 2016, 04:30:07 »
А при чём тут /sys ? …
И, да, зачем было запускать это на корень системы? Надо запускать на корень раздела.
А по поводу размера (и по поводу /sys, /proc и иже с ними тоже…),
find . -xdev -maxdepth 1 -type f -size +4k -exec /usr/sbin/filefrag '{}' + | while IFS=: read -r _n _t; do _c="${_t#" "}"; echo "${_c%% *} $_n"; done | sort -nr
("-maxdepth 1" - это для тестов… Для реальных прогонов это, естественно, надо убрать.)

/sys или /proc или что еще не знаю, но факт такой что из за применения к какому то файлу из этих папок команды filefrag комп перезагрузился

На корне надо запускать потому что диск в компе один и раздел в нем тоже один и это корень и есть, так размечается диск по дефолту установщиком убунты и я не вижу смысла делать как то иначе. Если надо просканировать диск смонтированный куда-нибудь в /media/blabla тогда надо просто изменить строчку со стартовой папкой, если надо исключить из корня смонтированные диски то можно добавить в список исключений папку /media

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #9 : 15 Ноябрь 2016, 10:24:01 »
На корне надо запускать потому что диск в компе один и раздел в нем тоже один и это корень и есть, так размечается диск по дефолту установщиком убунты и я не вижу смысла делать как то иначе. Если надо просканировать диск смонтированный куда-нибудь в /media/blabla тогда надо просто изменить строчку со стартовой папкой, если надо исключить из корня смонтированные диски то можно добавить в список исключений папку /media
Т.е. исключить то и се  и еще /run забыли.... а если у меня еще и /home сделан в XFS - тоже надо исключать..... А нафига такой сырбор? Проще смонтировать корневой подтом btrfs и на него сканер и натравливать.

Пользователь добавил сообщение 15 Ноябрь 2016, 10:25:47:
AnrDaemon, что то опять ваша команда не пашет  :-\ что хоть она сделать должна была - не совсем понял что там в цикле - расскажите плиз.

Пользователь добавил сообщение 15 Ноябрь 2016, 10:27:26:
возможно что то подобное есть и для бтрфс
искал - пока не нашел :)
« Последнее редактирование: 15 Ноябрь 2016, 10:27:26 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн theurs

  • Активист
  • *
  • Сообщений: 457
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #10 : 15 Ноябрь 2016, 12:52:38 »
AnrDaemon, что то опять ваша команда не пашет   что хоть она сделать должна была - не совсем понял что там в цикле - расскажите плиз.

у меня пашет, причем очень быстро. из нее надо убрать -maxdepth 1 и запускать из папки которую надо просканировать

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #11 : 15 Ноябрь 2016, 13:23:19 »
Вот какой у меня вариант получился (гугло-баш-программинг :)):

find . -type f -exec filefrag '{}' + | sed 's/: /*/;s/ extent.* found//' | awk -F* '{ print $2 " " $1 }' | sort -nr
Дает тот самый лог который давал изначальный скрипт theurs-а (только файлы с одним и 0 фрагментами - тоже попадут в лог). Если нужно саммари - то можно уже этот файл перелопатить и собрать статистику.


Вобщем вот мой скриптик с красивым выводом саммари по логу созданному командой выше (добавил только -xdev в find):
(Нажмите, чтобы показать/скрыть)

Лог с всеми файлами создается в /tmp/frag.log (в него попадают все найденные файлы, даже если они пустые или не фрагментированные)
Далее скрип его шерстит и собирает статистику. Она выводится на экран в таком виде:

/home/stc
Total: 66546 files (64738 not empty) and 70221 fragments
Totally 5483 fragments in 1123 fragmented files
Fragmentation factor by files {fragmented/total}: 1.69%
Fragmentation factor by fragments {(total_fragments - total)/total}: 8.47%

   2   fragments: 47%
 3-10  fragments: 46%
11-100 fragments: 4%
 > 101 fragments: 1%

Работает в разы быстрее нежели старые варианты и можно запускать в корне btrfs (да собственно любой другой FS тоже, я в примере запускал на XFS) и за пределы файловой системы (которая смонтирована именно в корень) find не уйдет благодаря опции -xdev.
« Последнее редактирование: 15 Ноябрь 2016, 14:55:58 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн AnrDaemon

  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 26070
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #12 : 15 Ноябрь 2016, 14:57:38 »
AnrDaemon, что то опять ваша команда не пашет что хоть она сделать должна была - не совсем понял что там в цикле - расскажите плиз.
У вас какой-то неправильный линукс. Я же прямо из терминала копирую. Должно работать.
А делается там очень простая штука. IFS - input field separator. Установив его в ":", я говорю последующим командам, парсящим ввод, разделять строку по двоеточию на токены. Поскольку я устанавливаю эту переменную только для текущего вызова read, мне не надо потом её восстанавливать. Дальше всё ещё проще. Я удаляю первый пробел из второй подстроки и печатаю всё в обратном порядке, дополнительно удаляя из второй подстроки всё, начиная со второго пробела. Это всё можно найти в man dash, поискав, например, "%%".
/sys или /proc или что еще не знаю
-xdev
Хотите получить помощь? Потрудитесь представить запрошенную информацию в полном объёме.

Прежде чем [Отправить], нажми [Просмотр] и прочти собственное сообщение. Сам-то понял, что написал?…

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #13 : 15 Ноябрь 2016, 15:10:01 »
AnrDaemon, я в резульате чуть иначе пошел. Просто я наступил на грабли с файлами, в имени которых есть двоеточие... :idiot2:

Поэтому я заменяю регуляркой sed-а двоеточие с пробелом на звездочку, а потом awk-ом меняю колонки местами. Почему-то sed-ом переставить два выделеных матча не получилось  :( как ни бился я с этим...  :-\

Во  :) победил sed:

find . -xdev -type f -exec filefrag '{}' +  | sed -e 's/^\(.*\): \(.*\) extent.* found$/\2 \1/' | sort -nr
Так наиболее правильно т.к. число фрагментов и имя файла однозначно вырезаются регуляркой и никакие двоеточия в названии файла не портят картину.
« Последнее редактирование: 15 Ноябрь 2016, 15:22:36 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

Оффлайн Sly_tom_cat

  • Автор темы
  • Don't worry, be happy!
  • Заслуженный пользователь
  • Старожил
  • *
  • Сообщений: 11891
  • Xubuntu 18.04 (64bit)
    • Просмотр профиля
Re: Re: BTRFS. Готова ли к использованию в 16.04?
« Ответ #14 : 15 Ноябрь 2016, 15:39:14 »
Последняя версия утилитки:

Сделал все через sed и за счет укорочения цепочки процессов в пайпе стало еще быстрее  :coolsmiley:

(Нажмите, чтобы показать/скрыть)

Выхлоп:
/home/stc
Total: 66593 files (64785 not empty) and 70281 fragments
Totally 5496 fragments in 1125 fragmented files
Fragmentation factor by files {fragmented/total}: 1.69%
Fragmentation factor by fragments {(total_fragments - total)/total}: 8.48%

   2   fragments: 47%
 3-10  fragments: 47%
11-100 fragments: 4%
 > 101 fragments: 1%
« Последнее редактирование: 15 Ноябрь 2016, 15:41:19 от Sly_tom_cat »
Индикатор для Yandex-Disk: https://forum.ubuntu.ru/index.php?topic=241992
UEFI-Boot - грузимся без загрузчика: http://help.ubuntu.ru/wiki/uefiboot

 

Страница сгенерирована за 0.092 секунд. Запросов: 25.