Игорь Олемской — практические заметки по системному администрированию Linux CentOS

Архив тега ‘Очумелые ручки’

Поздоровайтесь с хаосом (перепечатка)

Комментариев нет

cat /dev/urandom | base64 | grep -i hello

Будильник в Linux (перепечатка)

Комментариев нет

Тут надо было в два часа ночи продержаться не засыпая еще два часика до четырех. После этого следовало обработать кое какое событие и дальше спать. Но спички в глазах уже ломались и я стал нервно шарить вокруг в поисках мобильника, дабы включить будильник. Мобильника я не нашел. Задумался… «Есть ли будильник в линуксе?» – спросило само себя тухнущее сознание сисадмина. Уже автоматически стал открывать вкладку хрома, как вдруг нашло озарение. Открываю терминал, пишу…

#!/bin/bash
while /bin/true ; do
   /usr/bin/mplayer "/home/user/music/cf/Cradle Of Filth - Nymphetamine.mp3"
   sleep 5
done

Сохраняю, ставлю в крон на нужное время и спаааааать. mplayer в списке процессов я смогу покилять точно когда проснусь.

Да, за это я люблю Linux.

Отбиваем DDOS mod_evasive + firewall на CentOS (перепечатка)

Комментариев нет

Анализ DDoS можно производить конечно своими скриптами, парсить логи. Но лучше предоставить это апачевскому mod_evasive.

Ставим mod_evasive, в конфигурации пишем

DOSHashTableSize    3097
DOSPageCount        15
DOSSiteCount        15
DOSPageInterval     3
DOSSiteInterval     3
DOSBlockingPeriod   300
DOSSystemCommand    "/usr/bin/sudo /usr/bin/fwban %s"
  • DOSPageInterval – интервал для хитов определенной страницы
  • DOSSiteInterval – интервал для хитов определенного vhost
  • DOSPageCount – после этого количества хитов по определенному URI в течении интервала DOSPageInterval, айпи будет забанен
  • DOSSiteCount – после этого количества хитов по определенному vhost в течении интервала DOSSiteInterval, айпи будет забанен

Нам понадобиться скрипт для бана на уровне файрвола «/usr/bin/fwban» (вариант для Linux):

#!/bin/bash
if [ "x$1" = "x" ] ; then
    echo "USAGE: $0 IPADDR"
    exit
fi
/sbin/iptables -A BAN -s $1 -j DROP

Ему надо поставить права 755.

Так же нам понадобиться утилита sudo. Она стоит практически везде. В «visudo» закомментируем опцию:

#Defaults    requiretty

И добавим строку

apache  ALL = NOPASSWD: /usr/bin/fwban

где apache – юзер от которого работает апач.

Так же нам понадобиться цепочка BAN в iptables:

iptables -N BAN
iptables -I INPUT -j BAN

Сохраним правила файрвола

/etc/init.d/iptables save

Рестартанем апач. Теперь попробуйте уложить ваш сайт (только не со своего айпи!!!):

ab -n 1000  -c 20 http://yoursite.info/

В логах «жертвы» можно увидеть:

May  6 15:18:25 Server1 mod_evasive[26514]: Blacklisting address 1.2.3.4: possible DoS attack.

А в файрволе:

# iptables-save
---многа букав---
-A BAN -s 1.2.3.4 -j DROP
---многа букав---

Ура! No pasaran.

Да. И конечно, апач лучше бы прикрыть извне nginx’ом.

Да. И данный метод банит айпишнеги перманентно, пока не рестартанет сервер, или не будет сброшена цепочка BAN. Вот такой брутальный метод )

Nagios Plugin: check_ftp_login (перепечатка)

Комментариев нет

В общем нужно было проверять Nagios’ом не только порт фтп на удаленном хосте, но и работоспособность определенного аккаунтa FTP. Т.е. чтобы check_ftp заходил на FTP сервер и логинился под определенным юзером.

Существующая утилитка check_ftp из набора Nagios Plugins на момент написания статьи не умела делать логин. Точнее утилитки как таковой там и нет, там просто стоит симлинк check_ftp -> check_tcp.

По сему утилитка была написана на Perl с использованием Nagios::Plugin и Net::FTP.

Может так же использоваться как пример написания Nagios Plugins на Perl в виду простоты кода.

Сырец: http://www.pentarh.com/files/check_ftp_login

Пользоваться так.

1. Скопировать в диру с плагинами Nagios

2. Поставить чмод 755

3. Убедиться что стоят перловые модули Net::FTP и Nagios::Plugin (т.е. запустить утилитку и если все ок, она выдаст USAGE)

4. Прописать команду в commands.cfg:

define command{
   command_name    check_ftp_login
   command_line    $USER1$/check_ftp -H '$ARG1$' -u '$ARG2$' -p '$ARG3$'
}
5. Юзать, например так
define service{
   use             remote-service
   host_name ВАШХОСТ
   service_description FTP LOGIN
   check_command   check_ftp_login!ftp.foobar.com!FTP_LOGIN!FTP_PASSWORD
   normal_check_interval       10
}

Удаленный шифрованный бэкап MySQL при помощи LVM snapshot (перепечатка)

Комментариев нет

Имеем: высоконагруженый MySQL сервер с таблицами объёмом более 20 Гб.

Требуется: ежедневное резервное копирование на удавленный хост с шифрованием данных

Условия: процедура бекапа не должна ни коим образом сказаться на производительности MySQL во время проведения оной.

Итак, mysqldump отпадает автоматически, ибо локи таблиц там испортят нам весь аптайм. Выбор пал на технологию LVM снэпшотов, доступную в любом линуксе, утилитку шифрования gpg, а так же IO scheduler CFQ.

Итак, подготовка.

1. Подготовка LVM.

Нам нужна LVM группа с необходимым свободным местом для:

  • Баз MySQL
  • LVM снэпшота

Т.е. объема свободного пространства в группе LVM должно быть под базы + где-то 10-20% (в зависимости от тяжести IO записи работы с базами).

Создаем LVM Physical Volume на девайсе /dev/sda2 (у меня /dev/sda это RAID5 из 6 SAS дисков, sda2 можете заменить на свой девайс):

pvcreate /dev/sda2

Создаем Volume Group с именем vg0 на /dev/sda2:

vgcreate vg0 /dev/sda2

Теперь надо создать в группе vg0 логический том (Logical Volume) под партицию MySQL таблиц с именем mysql.  У меня эта партиция занимает 500 Гб. При этом важно оставить в группе vg0 10-20% свободного места, не занятого логическими томами, дабы было возможно делать снэпшоты.

lvcreate -L 500G -n mysql vg0

Теперь наш девайс будет виден в:

/dev/mapper/vg0-mysql
/dev/vg0/mysql (symlink)

2. Подготовка ФС

Это, думаю, умеют делать все. Но на всякий напишу.

Делаем FS:

mke2fs -j -L lmysql /dev/mapper/vg0-mysql
mkdir /mysql

Прописываем в fstab:

LABEL=lmysql            /mysql                  ext3    defaults,noatime 0 0

Монтируем, подготавливаем:

mount /mysql
mkdir /mysql/myisam
chown mysql:mysql /mysql/myisam

Прописываем в /etc/my.cnf:

datadir=/mysql/myisam

Стартуем MySQL:

/etc/init.d/mysqld start

Дальше любимым путем переносим на этот раздел (/mysql/myisam) свои базы.

3. Подготовка MySQL

Надо пропатчить RC-скрипт MySQL для выделения высокого приоритета IO, дабы наша мышца не сдулась в ходе интенсивного бекапа.

Так же следует заметить, что я использую IO scheduler CFQ. Если у вас не CFQ, то можно забыть про приоритеты IO. Узнать/Выставить IO scheduler на девайсе можно в файле:

/sys/block/sda/queue/scheduler
(sda заменить на ваш девайс)

Смысл патча в том, чтобы после старта MySQL отдавать ему высокий приоритет IO в CFQ. Патч на CentOS 5 RC скрипт /etc/init.d/mysqld выглядит так. Думаю, народ разберется.

4. Подготовка авторизации

Я буду делать бекап через кучу пайпов. Причин две:

  • Так проще
  • tar накидывается на дисковое IO с меньшим энтузиазмом когда пишет в пайп | gpg | ssh, чем когда пишет на диск.

Конечно, это увеличивает продолжительность бекапа. Но и уменьшает вероятность затыка MySQL на время бекапа.

А по сему, мы создаем Беспарольную авторизацию по публичному ключу с хоста MySQL (юзер root) на ваш некий бекап-хост  user@backup.remotehost.com.

5. Скрипт бэкапа

Собственно скрипт состоит из двух частей. Я их сложил оба в /root/scripts/. И в скрипте backup.sh используется этот путь.

1. backup.php

Этот скрипт делает сброс таблиц MySQL на диск с READ LOCK. После лока он создает снэпшот тома /dev/vg0/mysql и после этого отпускает лок MySQL.

Скриптик это служебный, используется он из скрипта backup.sh.

В нем нужно поменять в строке коннекта к MySQL данные для коннекта рутового юзера к локальному серверу:

$link=@mysql_connect('localhost','root','');

Так же стоит обратить внимание на строку

exec("/usr/sbin/lvcreate --size 30G --snapshot --name $lv /dev/{$vg}/$part",$out,$ret);

А именно на 30G – это размер LVM снапшота. Нам он нужен на время бекапа, и размер снапшота должен превышать тот максимальный объем данных, которые MySQL сможет записать за это время на диск. Ну и конечно, в группе LVM vg0 должно быть именно столько или больше свободного места. 30G в общем за глаза.

2. backup.sh

А это именно тот скрипт, который будет запускаться из крона.

Он запускает backup.php для снятия снапшота, монтирует снапшот в указанную директорию, тарит раздел с таблицами, кидает это все в пайп к gpg для шифрования по алгоритму AES256 с симметричным ключом и кидает дальше в пайп ssh, который уже на удаленной стороне складывает с помощью dd все это хозяйство в файл бекапа с временной меткой. Фух.

Далее он размонтирует снапшот и удаляет его.

Если кто успел заметить, используется утилита gpg для шифрования симметричным ключом, который расположен в файле $keyfile. Данный файл должен содержать около 20 случайных ASCII символов одной строкой. Стоит заметить что нужно создать этот файл раз и навсегда и сохранить где то у себя его копию, поскольку расшифровать бекап можно будет только с его помощью. А сделать это можно будет сделать командой:

gpg --passphrase-file $keyfile --cipher-algo AES256 -d file.tgz.gpg > file.tgz

Прочие переменные:

gpgpath – путь к gpg, с завершающим слешем
vgname – имя группы LVM, содержащей том с таблицами MySQL
lvname – имя тома создаваемого снапшота
partitionlvname – имя тома с таблицами MySQL в группе $vgname
mntpoint – директория для монтирования снапшота
remotehost – юзер и хост для удаленного бекапа (см. пункт 4)
f — имя файла, в который на удаленной стороне будет складываться шифрованный бекап

Собственно, все. Удачного дебага всего этого хаоса что выше ))

 

База сообщений ICQ Lite (перепечатка)

Комментариев нет

Потребовалось мне вытянуть сообщения из базы ICQ Lite. К моему удивлению это оказалось довольно просто, ибо база имеет формат SQLite3.

База лежит в C:\Documents and Settings\Username\Application Data\ICQ\UIN\Messages.qdb

Где Username – имя пользователя винды, UIN – числовой ICQ идентификатор.

Качаем бинарник sqlite3.exe и копируем его в C:\Windows

Пуск -> Выполнить: cmd.exe

Делаем CD в директорию базы, выполняем «sqlite3 Messages.qdb».  Смотрим «.schema». Все месаги содержатся в таблице Messages. Поле «fromUser» пустое если сообщение от вас и содержит идентификатор корреспондента, если сообщение шло к вам, то это поле содержит кто писал сообщение. Поле participantsHash это Foreighn Key на таблицу Participants, откуда джойном можно вытянуть к кому было направлено сообщение.

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

По этому следующий запрос вытянет все сообщения из БД

sqlite> select p.userId,m.* from Messages m inner join Participants p on m.participantsHash=p.participantsHash;

Можно вытянуть конкретную свою переписку с идентификатором 11111:

sqlite> select p.userId,m.* from Messages m inner join Participants p on m.participantsHash=p.participantsHash WHERE m.fromUser=111111 OR p.UserId=111111;

Однако база вообще в UTF-8 формате, по этому в командной строке вы увидите кучу говна. Советую экспортировать это в файл, а потом уже его читать редактором, понимающим UTF:

C:\blah> sqlite3 -html Messages.qdb «select p.userId,m.* from Messages m inner join Participants p on m.pa
rticipantsHash=p.participantsHash WHERE m.fromUser=111111 OR p.UserId=111111″ > perepiska.html

Отредактируем perepiska.html, вставим в начало:

<html><head><META http-equiv=»Content-Type» content=»text/html; charset=utf-8″></head>
<body><table>

И в конец:

</table></body></html>

Все. Читайте вашу переписку в деталях, охуевайте и сносите побыстрее ICQ Lite.

Установка X/KDE на удаленный CentOS сервер/VDS (перепечатка)

Комментариев нет

Написано по материалам HowTo VNC Server. В качестве операционной системы удаленного сервера возьмем CentOS.

Поскольку у нас отсутствует доступ к консоли сервера, установим KDE на http://www.softpedia.com/get/Internet/Remote-Utils/VNC-for-Windows.shtml.

На сервере понадобится 512М оперативы чтобы все это нормально работало.

Все нижеописанное работает на VDS/VPS на основе Virtuozzo/OpenVZ.

1. Устанавливаем иксы и KDE:

# yum -y groupinstall «X Window System»
# yum -y groupinstall «KDE (K Desktop Environment)»

2. Добавляем некоего юзера user1, под которым будут запускаться кеды:

# useradd user1
# passwd user1

3. Конфигурируем VNC Server (должен был поставиться с вышеописанными пакетами):

файл /etc/sysconfig/vncservers:
VNCSERVERS=»1:user1»
VNCSERVERARGS[1]=»-geometry 1024×768″

4. Устанавливаем пароль на VNC для нашего юзера:

# su user1
# vncpasswd

5.  Редактируем /home/user1/.vnc/xstartup:

Убираем камменты со следующих строк:

unset SESSION_MANAGER
exec /etc/X11/xinit/xinitrc

Должно получиться примерно следующее:

unset SESSION_MANAGER
exec /etc/X11/xinit/xinitrc

[ -x /etc/vnc/xstartup ] && exec /etc/vnc/xstartup
[ -r $HOME/.Xresources ] && xrdb $HOME/.Xresources
xsetroot -solid grey
vncconfig -iconic &
xterm -geometry 80×24+10+10 -ls -title «$VNCDESKTOP Desktop» &
twm &

6. Стартуем VNC Server, добавляем в автозагрузку:

# /etc/init.d/vncserver start
# chkconfig –level 3 vncserver on

7. Качаем VNC Client, например отсюда

8.  Выбираем параметры коннекта, глубину цвета и т.п. Коннектимся на SERVER_IP:1, вводим пароль с шага 4

9. Опционально, yum install firefox ;)

10. Enjoy

Уменьшение потребления памяти MySQL (перепечатка)

Комментариев нет

В основном это касается Virtual Dedicated Server (VDS/VPS), т.к. дефолтная установка MySQL на CeontOS/Fedora/RHEL с дефолтным my.cnf делает malloc на сотню с лишним мегабайт.

Конечно на потребляемую память MySQL влияют такие параметры как key_buffer, query_cache_size и т.п. Но они по дефолту идут минимальные, а кеш запросов вообще по моему отключен по дефолту.

Так вот все очень просто. Добавляем в my.cnf:

skip-innodb
skip-bdb

Это выключит хандлеры InnoDB и BerkeleyDB и всю потребляемую ими память. Ну конечно делать это нужно если вы не используете вышеприведенные типы таблиц.

Далее рестартуем мускуль и видим в топе что он занимает десяток-другой мегабайт.

PS: в большинстве случаев не помешает опция и skip-networking. А вот thread_cache_size я советую поставить в значение 5-15 (в зависимости от нагрузки) :)