Поиск по этому блогу

вторник, 24 марта 2009 г.

Остановка вращения шпинделя HDD под FreeBSD

Поднял шлюз на FreeBSD, а через пару дней он таки достал громкой работой - гул старого винчестера довольно сильно раздражает.
Загорелся я идеей остановить вращение шпинделя. Пол дня копания в нете привело к обнаружению довольно интересной команды atacontrol.
Судя по мануалке команда используется для управления ATA-устройствами, управления ими в RAID, подключении и отключении.

# atacontrol
usage: atacontrol args:
atacontrol list
atacontrol info channel
atacontrol attach channel
atacontrol detach channel
atacontrol reinit channel
atacontrol create type [interleave] disk0 ... diskN
atacontrol delete array
atacontrol addspare array disk
atacontrol rebuild array
atacontrol status array
atacontrol mode device [mode]
atacontrol cap device
atacontrol spindown device [seconds]

В данном случае нас интересует только последняя строчка

atacontrol spindown device [seconds]


К примеру

#atacontrol spindown ad0 60

должно привести к отключению вращения шпинделя устройства ad0, если к нему нет обращений в течении 60 секунд. Используеться имено имя устройства "ad0", а не путь к устройству "/dev/ad0".
Для отключения остановки HDD т.е. чтоб гудел постоянно нужно сказать

#atacontrol spindown ad0 0

А для просмотра текущего состояния говорим

#atacontrol spindown ad0

т.е. без указания вермени

Приступим к полевым испытаниям:

#atacontrol spindown ad0 60

Ждем, ждем, ждем и ничего.

Уменьшаем время до 5 секунд:

#atacontrol spindown ad0 5

ad0: Idle, spin down
ad0: drive spun down.
ad0: request while spun down, starting.

Винт издает звуки остановки и тут же запускаеться заново :( Получаеться что остановка всетаки отрабатывает но ктото постоянно делает обращение к файлам. Так вспоминаем... и смотрим ps ax... Надо бы отключить sendmail, cron и всех остальных кто юзает винт. В данном случае комп используется как роутер и юзать винт ему особо ненадо. Также прийдется пожертвовать хранением логов.

Добавляем в rc.conf чтобы полностью вырубить sendmail и cron:

sendmail_enable="NO"
sendmail_submit_enable="NO"
sendmail_outbound_enable="NO"
sendmail_msp_queue_enable="NO"
cron_enable="NO"

Перезагружаемся, пробуем

#atacontrol spindown ad0 5

ad0: Idle, spin down
ad0: drive spun down.
ad0: request while spun down, starting.

Опять тож самое, винт дернулся и запустился заново. Подозрения падают на логи, причем самый разные, включая консольные команды юзера. И тут вспоминаю про то, как ставил FreeBSD на флешку. Ведь mount умеет монтировать не только разделы, а и память, создавая нечто похожее на файловую систему в оперативной памяти. В конечном итоге /etc/fstab
принял такой вид:

# cat /etc/fstab
# Device Mountpoint FStype Options Dump Pass#
/dev/ad0s1a / ufs rw 1 1
/dev/acd0 /cdrom cd9660 ro,noauto 0 0
md /tmp mfs rw,-s16M,nosuid,noatime 0 0
md /var/tmp mfs rw,-s16M,nosuid,noatime 0 0
md /var/run mfs rw,-s4M,nosuid,noatime 0 0
md /var/log mfs rw,-s16M,nosuid,noatime 0 0
md /root mfs rw,-s4M,nosuid,noatime 0 0
md /home mfs rw,-s4M,nosuid,noatime 0 0
/proc /proc procfs rw,noauto 0 0

Тоетсь реально монтируется только корневой раздел, а папки с файлами которых происходит какая-либо работа отображаются в память и никоим образом не связаны с реальными на диске. Также следует заметить, что своп не монтируется и его использование при остановка винчестера нелогично.
Все каталоги, примонтированные в память, создаются пустыми, поэтому в каталоги, в которых хранятся какие-либо конфиги эти конфиги нужно скопировать обратно. Для этого делаем их копии в какую либо папку, а потом копируем скриптом обратно в папки, примонтированные в память(ниже в
скрипте hddstop.sh).

Перезагружаемся пробуем

#atacontrol spindown ad0 5

ad0: Idle, spin down
ad0: drive spun down.

И тишина :)

Теперь чтобы выключение HDD происходило после загрузки системы создаем скрипт с любым именем в /usr/local/etc/rc.d и не забываем сделать его исполняемым.

К примеру:

# cat /usr/local/etc/rc.d/hddstop.sh

#!/bin/sh
#echo -n ' FooBar'

case "$1" in
start)
#copy mgety config and ppp files
######
cp /usr/share/mgetty_config_copy/mgetty+sendfax/* /usr/local/etc/mgetty+sendfax/
cp /usr/share/mgetty_config_copy/ppp/* /etc/ppp/
cp -R /usr/share/mgetty_config_copy/spool/* /var/spool/
######

atacontrol spindown ad0 50

echo "Spindown after 50 seconds" >&2
;;
stop)
atacontrol spindown ad0 0
echo "Spindown disabled" >&2
;;
*)
echo "This comand just start ataconfig" >&2
exit 64
;;
esac
exit 0



Перезагружаемся, ждем, проходит минута-полторы и тишина :)

З.Ы. Все эти пляски с бубном имели место лишь потому, что железо старое и с флешки грузиться не умеет. Умей грузиться - стартовало бы с флешки.

Пускаем локальную сеть в нет при помощи FreeBSD-шлюза

Поднимал недавно интернет-шлюз для того чтобы пускать локальную сеть в мир. В качестве железа взял старенький Celeron 800, с материнкой на i815, 128 + 256 памяти. Винчестера в наличии небыло поэтому решил идти в ногу со временем и поставить свеженькую FreeBSD 7.1 на флешку как описано здесь и по подобным мануалам. Таким образом FreeBSD удалось установить даже на фотоаппарат и загрузить с него ноут :), а вот старенький комп грузится с флешки категорически отказывался. Пришлось купить б/у винчестер WD на 20Гб.
Поднятие NAT на PF и кеширующего DNS не составило особого труда.

Конфиги на память.

rc.conf

saver="fire"
sshd_enable="YES"
named_enable="YES"
inetd_enable="YES"
pf_enable="YES"
gateway_enable="YES"
apm_enable="YES"
#############################################################################
# localization
#############################################################################
keymap=ru.koi8-r
keychange="61 ^[[K"
scrnmap=koi8-r2cp866
font8x16=cp866b-8x16
font8x14=cp866-8x14
font8x8=cp866-8x8
#############################################################################

ifconfig_rl1="inet xxx.xxx.xxx.xxx netmask 255.255.255.0"

ifconfig_rl0="inet xxx.xxx.xxx.xxx netmask 255.255.255.0"
defaultrouter="yyy.yyy.yyy.yy"

pf.conf

ext_if="rl0"
int_if="rl1"

set block-policy drop

scrub in all
scrub min-ttl 64
scrub in on $ext_if all fragment reassemble

nat on $ext_if from any to any -> ($ext_if)

block all
pass quick on $int_if all
pass out quick on {$ext_if} all keep state
pass on lo0 all #может и не совсем коректно, но нужно чтобы и сама фря использовала свой кеширующий DNS

resolv.conf

nameserver 127.0.0.1

/var/named/etc/namedb/namedb.conf

Подправляем и не забываем раскоментировать секцию forwarders, должно получиться что-то похожее:

forwarders {
yyy.yyy.yyy.yyy;zzz.zzz.zzz.zzz;
};


Вообщем все просто и без извращений.

пятница, 20 марта 2009 г.

Приступим

Решил все-таки завести себе блог :) Надоело постоянно натыкатся на одни и теже грабли по нескольку раз вспоминая "А как же я тогда делал?". Надеюсь, посты будут полезны не только мне, а и многим столкнувшимся с такими вещами как программинг и админинг :)