четверг, 30 июня 2011 г.

ipfw call / return

28 июня официально начался "Code Slush for 9.0-RELEASE", который так же известен как "Feature Freeze". Т.е. теперь в head/ бранч не разрешается вносить новый функционал. Цель этого мероприятия - стабилизировать состояние системы и сосредоточиться на поиске и исправлении ошибок. На 17-ое июля запланирован "Code Freeze" после которого последует выход первой бета версии FreeBSD 9.0.

Теперь о теме. Вадим Гончаров, узнав о предстоящем "Code Slush", выдал очередной патч для ipfw, который во что бы то ни стало должен оказаться в 9.0-RELEASE. :)
Патч добавляет два новых действия в ipfw: "call" и "return". Первая команда выполняет "вызов" подпрограммы, вторая - возврат из подпрограммы к следующему правилу. На практике, конечно, никаких подпрограмм не вызывается. Команда "call" принимает в качестве аргумента номер правила, к которому нужно выполнить переход. Переход осуществляется аналогично тому, как это делается для команды "skipto", только он может осуществляться в любом направлении по отношению к текущему правилу. Кроме того, перед выполнением перехода команда "call" сохраняет во внутреннем стеке номер своего правила в качестве точки возвращения. Размер стека ограничен 16 элементами. Это значит, что "подпрограмма" может содержать в себе другие вызовы "call" в другие "подпрограммы".
Возврат из "подпрограммы" осуществляется размещением правила с командой "return". У неё нет аргументов. Она находит в стеке первый элемент (по дисциплине LIFO), извлекает сохранённый номер правила и осуществляет возврат к следующему правилу с номером большим на 1.

Теперь о применении этого. Несомненно, есть несколько задач, в которых данный функционал может оказаться полезным. Но в то же время, скорость появления этого патча и практически полное отсутствие его тестирования ставит под сомнение плюсы, которые можно получить от него. Так что, если найдутся желающие на широких каналах протестировать этот функционал, было бы неплохо. Для этого, в общем-то, достаточно скачать образ 9.0-CURRENT и протестировать ;)

Кстати, Hiroki Sato сообщил о возобновлении сборки снепшотов FreeBSD CURRENT на ресурсе allbsd.org. Что является отличной новостью, для меня по крайней мере. Обычно для тестирования чего-либо бывает быстрее скачать образ и установить систему, чем обновляться из исходников.

пятница, 24 июня 2011 г.

Что нового?

Последние несколько недель в свободное время занимался обработкой открытых PR. В основном они были связаны с ipfw, dummynet и ipfw_nat, но не все. В общем, сократил количество открытых проблем где-то на полтора десятка, может даже на два. Считать, если честно - лень :)

Что хотелось бы отметить - это несколько исправлений и патчей, добавляющих новую функциональность. Желательно бы их получше оттестировать перед MFC. И, кстати говоря, вот уже почти неделю назад должен был начаться "code slush" в связи с подготовкой к выпуску 9.0-RELEASE.

Итак, первое исправление затрагивает kern/136695, kern/147720 и kern/150798. Связано оно с функцией форвардинга пакетов в ipfw и использованием динамических правил. Теперь реализация аналога reply-to из PF не должна составить труда и в ipfw (описание этого случая можно найти у Вадима Гончарова в блоге).

Следующее исправление связано с kern/122109, kern/129093 и kern/157379. Оно делает поведение ipfw_nat более похожим на natd. Возможно, те кто говорил, что ipfw_nat работает не так с правилами, с которыми работает natd, теперь вздохнут с облегчением. Теперь ipfw_nat будет более "гуманно" относится к пакетам, которые libalias не захотела обрабатывать. Раньше такие пакеты просто отбрасывались, что приводило к симптомам, хорошо показанным в перечисленных PR.

Теперь о новом функционале в ipfw_nat - kern/157867. Это аналог опции globalport для natd. Если у вас сконфигурировано несколько NAT'ов, то теперь можно одним правилом заставить ipfw проверять пакет сразу для всех таблиц трансляций. Для этого добавлено новое "кодовое слово"- nat global. Пакет будет обрабатываться в соответствии с конфигурацией той таблицы, в которой найдётся подходящее состояние.


В модуль libalias, обрабатывающий FTP соединения внесены изменения kern/157957, благодаря которым он корректно работает при использование опции redirect_port для ipfw_nat. Кстати, Глеб Смирнов изменил обработку опций NAT для ipfw(8). Теперь командная строка не ограничена длиной NAT_BUF_LEN и при настройках NAT можно указывать сколько угодно опций.

Кроме того, для ipfw setfib добавлена поддержка tablearg - kern/156410.

Еще было несколько мелких исправлений, которые не так интересны. Но в общем, за большинство из этих изменений и исправлений можно поблагодарить Александра Черникова. Именно у него хватило терпения и желания, копаться в коде, который местами далеко не очевиден, писать патчи и продвигать их, чтобы они оказались в системе.

Да, ещё. По проблеме с загрузкой с ZFS. Вчера John Baldwin добавил исправление в загрузочный код, которое, вероятно исправит большинство проблем.

четверг, 9 июня 2011 г.

Выравнивание разделов в gpart. Итоги.

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

Многие из вас слышали, что некоторые современные жесткие диски уже выпускаются с размером сектора в 4 Кбайт. Хотя на данный момент я не слышал ни об одном из них, который бы честно в этом признавался. Все они продолжают рапортовать о том, что у них размер сектора равен 512 Байтам. В связи с чем часто возникают проблемы с производительностью при работе с такими дисками. Для обхода этой проблемы есть несколько решений. Одно из последних появилось во FreeBSD 9.0 совсем недавно - с ревизией r222520.

Александр Мотин добавил в драйвер ada(4) новый quirk - ADA_Q_4K. Который говорит драйверу установить geom провайдеру размер stripesize равным 4 Кбайта. На основе этой информации все консьюмеры этого провайдера могут проявлять свой "интеллект" и пытаться выполнить некоторые оптимизации при работе.

В драйвер уже "вшита" информация о некоторых диска, размер сектора которых 4 Кбайт. Для них stripesize будет установлен автоматически. Для других же дисков, которые не прописаны в драйвере, можно установить данный quirk через loader.conf. Так, для диска ada3 это будет примерно так:

# echo 'kern.cam.ada.3.quirks="1"' >> /boot/loader.conf

проверить работоспособность можно, например, так:

# geom disk list ada3
Geom name: ada3
Providers:
1. Name: ada3
   Mediasize: 80026361856 (74G)
   Sectorsize: 512
   Stripesize: 4096
   Stripeoffset: 0
   Mode: r2w2e4
   descr: SAMSUNG HD080HJ/P
   ident: S0DEJ1NL817767
   fwsectors: 63
   fwheads: 16


Теперь вернёмся к gpart(8). Я добавил туда поддержку stripesize, а так же возможность вручную задавать нужное выравнивание:

# gpart
usage: gpart add -t type [-a alignment] [-b start] [-s size] [-i index] [-l label] [-f flags] geom
 ...
       gpart resize -i index [-a alignment] [-s size] [-f flags] geom 

У двух подкоманд "add" и "resize" появилась новая опция -a alignment. Которую можно задавать как в секторах, так и в байтах. Наличие этой опции влияет на то, как gpart рассчитывает границы разделов. Например, если вы хотите, чтобы раздел был выравнен по границе в 4 Кбайт, то достаточно указать "-a 4k" дополнительно к команде "gpart add". При использовании stripesize выравнивание можно не задавать, оно будет "подхвачено" автоматически.

Для проверки, выравнен раздел или нет, можно использовать команду diskinfo(8):
# diskinfo -v ada0p3
ada0p3
        512             # sectorsize
        75731098112     # mediasize in bytes (70G)
        147912301       # mediasize in sectors
        4096            # stripesize
        1024            # stripeoffset
        146738          # Cylinders according to firmware.
        16              # Heads according to firmware.
        63              # Sectors according to firmware.
        S0DEJ1NL817767  # Disk ident.

#  echo 1024 % 4096 | bc
1024
Следующая после diskinfo(8) команда подсчитывает остаток от деления между stipeoffset и желаемым выравниванием. Если получаемое значение не ноль, значит раздел не выравнен.