Домашний сервер «всё-в-одном» — success story
09:28Жил да был у меня роутер одной хорошей фирмы на букву «Dead». Ну, это с ним, собственно, и случилось.
Посмотрел я на цены новых, на кучу компьютерного хлама в углу, на список
подключений на домашнем компе… И понял, что не нужен мне роутер. Соберу
свой, с нормальной маршрутизацией, DNS, WINS, i2p, блекджеком и так далее.
Как это было?
После недолгих раскопок в залежах железа, на свет были извлечены:
• Процессор Intel Core 2 Duo E8400 @ 3GHz
• При нём же – материнка Asus P5Q
• 2 планки DDR2 по 2Gb
• PCI-e сетевая карта TP-Link TG-3468
• Неопознанная сетевая карта WiFi (b/g/n) на базе Ralink RT3060
• Жёсткий диск Seagate 250Gb
Вывод lshw можно посмотреть тут.
Всё это было отчищено от пыли, вмонтировано в корпус с блоком питания,
запущено и проверено в memtest и mhdd. Не обнаружив дефектов, я начал
установку всего мне необходимого.
Основы основ
За основу я взял дистрибутив Debian Testing, раскатанный через
Debootstrap. Сверху сразу были поставлены openssh-server,
firmware-ralink и pppoe/pppoeconf.
Ребутнувшись в свежепоставленную систему, я сразу перенёс SSH на
192.168.1.1 и отключил авторизацию по паролю (установив предварительно
свой ключ).
Да будет сеть!
Для начала был запущен pppoeconf. К DOCSIS-модему оказалась подключена
сетевая карта с именем eth1, в итоге был получен следующий конфиг
/etc/ppp/peers/rt:
noipdefault
defaultroute
replacedefaultroute
hide-password
noauth
persist
plugin rp-pppoe.so eth1
user "ptn"
usepeerdns
Но это не всё – необходимо ещё настроить /etc/network/interfaces следующим образом:
auto rt
iface rt inet ppp
pre-up /sbin/ifconfig eth1 up
provider rt
Превращаем роутер в WiFi-AP
Изначальная задумка была в том, что бы сделать 2 WiFi-сети: одну для
своих компьютеров и ноутбуков, с надёжным паролем и присоединением ко
всем необходимым ресурсам, а вторую – для гостей, которым захотелось
выйти в интернет, но не надо знать о том, что творится в моей сети.
В итоге на сервер был установлен hostapd с конфигом следующего вида (все названия сетей и пароли были изменены):
interface=wlan0
driver=nl80211
country_code=RU
ieee80211d=1
hw_mode=g
channel=9
ssid=Private
bridge=br0
preamble=1
ignore_broadcast_ssid=0
wpa=3
wpa_key_mgmt=WPA-PSK
wpa_pairwise=TKIP CCMP
rsn_pairwise=CCMP
wpa_passphrase=MyVeryStrongPassword
wmm_enabled=1
ieee80211n=1
ht_capab=[HT40-][SHORT-GI-20][SHORT-GI-40]
internet=1
bss=wlan0_0
ssid=Guest
preamble=1
ignore_broadcast_ssid=0
wpa=3
wpa_key_mgmt=WPA-PSK
wpa_pairwise=TKIP CCMP
rsn_pairwise=CCMP
wpa_passphrase=passw0rd
wmm_enabled=1
ieee80211n=1
ht_capab=[HT40-][SHORT-GI-20][SHORT-GI-40]
internet=1
Тут мы ставим ещё и bridge для eth0 и wlan0 – это позволит
подключившимся к нашей сети видеть её целиком, а не беспроводной
сегмент. Модифицируем networks:
auto eth0 wlan0 wlan0_0 br0
iface eth0 inet manual
allow-hotplug wlan0
allow-hotplug wlan0_0
iface wlan0 inet manual
pre-up ifconfig wlan0 hw ether f2:7d:68:6d:51:30
iface br0 inet static
bridge_ports eth0 wlan0
address 192.168.1.1
netmask 24
iface wlan0_0 inet static
address 192.168.254.1
netmask 24
Немного о магии в pre-up для wlan0: для работы с несколькими AP нам надо
использовать больше, чем один MAC-адрес. Hostapd назначает MAC для
виртуальных интерфейсов (wlan0_0 в нашем случае) автоматически, но для
этого адрес первой точки доступа должен иметь несколько «пустых» битов в
конце. Я не стал мелочиться и освободил сразу 4 штуки. Задача на дом –
посчитайте, сколько максимум AP теперь можно запустить на одной карте.
Налетай – IP всем и каждому, бесплатно!
Всем компьютерам в сети, как это ни прискорбно, надо выдать IP-адреса. Да-да, этим мы и будем заниматься.
Недолго думая, на сервере был запущен DHCP-сервер следующей конфигурации:
update-static-leases on;
authoritative;
allow unknown-clients;
use-host-decl-names on;
log-facility local7;
subnet 192.168.1.0 netmask 255.255.255.0 {
interface br0;
authoritative;
range 192.168.1.2 192.168.1.254;
option subnet-mask 255.255.255.0;
option ntp-servers 192.168.1.1;
option domain-name-servers 192.168.1.1;
option netbios-name-servers 192.168.1.1;
option routers 192.168.1.1;
option domain-name "local";
}
subnet 192.168.254.0 netmask 255.255.255.0 {
interface wlan0_0;
authoritative;
range 192.168.254.2 192.168.254.254;
option subnet-mask 255.255.255.0;
option domain-name-servers 8.8.8.8, 8.8.4.4;
option routers 192.168.254.1;
}
local-address 192.168.1.1;
Видно, что для 192.168.1.1/24 так же выдаются DNS, WINS, NTP и шлюз 192.168.1.1 – самое время их настроить.
Со шлюзом всё просто, думаю, эти команды не знает только ленивый:
sysctl net.ipv4.ip_forward=1
iptables –t nat -A POSTROUTING -o ppp0 -j MASQUERADE
Разумеется, ставим iptables-persistent для сохранения наших настроек, а
так же прописываем соответствующие параметры в /etc/sysctl.conf.
Теперь наш сервер является полноценным китайским роутером за 10$. Что? Вам кажется слабовато? Мне тоже. Едем дальше.
Как пройти в библиотеку?
Думаю, никто не забыл, что нам нужен DNS? Простейший forwarding
настраивается до нелепости просто, но ведь мы делаем полноценный сервер с
резолвингом и реверс-зонами… Ставим bind9, и настраиваем:
options {
directory "/var/cache/bind";
forwarders {
8.8.8.8;
8.8.4.4;
};
dnssec-validation auto;
auth-nxdomain no;
listen-on { 127.0.0.1; 192.168.1.1; };
allow-transfer { none; };
version none;
};
zone "local" IN {
type master;
file "/var/lib/bind/db.localnet";
};
zone "1.168.192.in-addr.arpa" IN {
type master;
file "/var/lib/bind/db.localnet-rev";
};
Теперь нам нужны файлы прямой и обратной зоны:
Просто? А теперь сделаем так, что бы каждый компьютер в сети можно было видеть не по IP, а по DNS-имени.
Для этого нам нужно настроить DDNS. Эта технология позволяет связать DHCP-сервер, выдающий адреса, и DNS-сервер.
Для начала создадим ключ для нашего DDNS:
dnssec-keygen -a HMAC-MD5 -b 128 -r /dev/urandom -n USER DDNS_UPDATE
Эта команда создаст нам 2 файлика с DDNS-ключом. Нам нужно содержимое ключа:
cat Kddns_update.+157+36693.key
DDNS_UPDATE. IN KEY 0 3 157 HEyb0FU9+aOXnYFQiXfiVA==
«HEyb0FU9+aOXnYFQiXfiVA==» и есть наш ключ.
Немного отредактируем наш конфиг DHCP, добавив в него следующие опции:
ddns-updates on;
ddns-update-style interim;
key rndc-key { algorithm HMAC-MD5; secret HEyb0FU9+aOXnYFQiXfiVA==; }
zone local. { primary 192.168.1.1; key rndc-key; }
zone 1.168.192.in-addr.arpa. { primary 192.168.1.1; key rndc-key; }
subnet 192.168.1.0 netmask 255.255.255.0 {
…
ddns-domainname "local.";
ddns-rev-domainname "in-addr.arpa.";
}
Так же поступим с DNS:
key "rndc-key" {
algorithm hmac-md5;
secret "HEyb0FU9+aOXnYFQiXfiVA==";
};
zone "local" IN {
…
allow-update { key rndc-key; };
};
zone "1.168.192.in-addr.arpa" IN {
…
allow-update { key rndc-key; };
};
Вуаля – и эта киллер-фича работает.
Будущее всё-таки здесь. Шестая версия
Так исторически сложилось ©, что мой провайдер (презрительный взгляд в сторону Ростелекома) не выдаёт IPv6 (хотя обещал).
В настоящее время на всей протяженности сети «Ростелеком» обеспечил возможность работы по протоколу IPv6, — парирует пресс-служба оператора.
Что ж, пофиксим это недоразумение. В качестве брокера я выбрал sixxs.net – у них есть туннельные серверы в России, и их туннель прост в настройке для случая с динамическим IP.
Процесс регистрации и получения настроек туннеля/подсети я опущу – там всё довольно просто. Остановлюсь на настройке.
Настройка IPv6 на самом сервере производится в 2 этапа. Во-первых,
поставим пакет aiccu – это и есть туннелирующая программа. При установке
у нас будет запрошен логин и пароль от sixxs, и некоторые другие
данные. После запуска у нас появится новый интерфейс:
sixxs Link encap:IPv6-in-IPv4
inet6 addr: 2a02:578:5002:xxx::2/64 Scope:Global
UP POINTOPOINT RUNNING NOARP MTU:1280 Metric:1
…
Сервер теперь имеет доступ в v6-сеть – почему бы не поделиться ей с другими?
Для начала, разрешим IPv6-forwarding (не забудьте прописать в /etc/sysctl.conf):
sysctl net.ipv6.conf.all.forwarding=1
Настроек с iptables производить не надо – привет, 21 век!
Далее на сайте sixxs получаем подсеть. Её адрес будет очень похож на адрес нашего туннеля – будьте внимательны, они отличаются!
После получения адреса вида 2a02:578:5002:xxxx::/64, приступим к его
настройке. Во-первых, зададим нашему серверу адрес
2a02:578:5002:xxxx::1, добавив в interfaces следующие строки:
iface br0 inet6 static
address 2a02:578:5002:xxxx::1
netmask 64
Во-вторых, разрешим выдачу IPv6 компьютерам в сети. Поставим пакет radvd, и настроим его следующим образом:
interface br0
{
AdvSendAdvert on;
prefix 2a02:578:5002:xxxx::/64
{
AdvOnLink on;
AdvAutonomous on;
AdvRouterAddr on;
};
RDNSS 2a02:578:5002:xxxx::1 { };
};
Добавим IPv6 DNS в настройки нашего bind – для полного фен-шуя:
options {
forwarders {
…
2001:4860:4860::8888;
2001:4860:4860::8844;
};
listen-on-v6 { ::1/128; 2a02:578:5002:xxxx::/64; };
…
};
Это всё – теперь мы имеем доступ, например, к ipv6.google.com, или, что гораздо ценнее – к ipv6.nnm-club.me ;)
Пингвин, смотрящий в окно
Я люблю, когда у меня в сети всё красиво. А это возможно только в случае
полной гармонии. Например, когда все компьютеры видят друг друга. Для
рабочих станций Windows справедливо вспомнить про WINS (помните, мы даже
выдавали эту настройку в DHCP).
Его настройка крайне проста: устанавливаем пакет samba. Конфиг по умолчанию надо немного изменить:
workgroup = WORKGROUP
wins support = yes
dns proxy = yes
interfaces = lo br0
bind interfaces only = yes
server role = standalone server
Проверяем результаты… О, да тут всё хорошо!
Кстати, так как у нас есть samba, можно сразу настроить файлопомойку. Но
это уже настолько избитая тема, что я оставляю её на плечах гугла. По
сути, всё и так должно работать из коробки – разве что read only для
homes выключить да smbpasswd -a user…
Который час?
Настроим раздачу времени на сервере: установим ntp. С конфигами всё до нелепости просто:
server 0.ru.pool.ntp.org
server 1.ru.pool.ntp.org
server 2.ru.pool.ntp.org
server 3.ru.pool.ntp.org
…
broadcast 192.168.1.1
Мы уже вплотную приблизились к роутерам уровня microtik за $150-$200. Но это же не всё? Конечно нет.
Killer-feature #1: I2P
А почему бы не иметь доступа в эту сеть без каких-либо настроек, без
прокси-серверов и так далее? Вот и я думаю, «почему». Для начала
установим вменяемую версию Java:
echo "deb http://ppa.launchpad.net/webupd8team/java/ubuntu precise main" >> /etc/apt/sources.list
apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys EEA14886
apt-get update
apt-get install oracle-java7-installer
И установим сам роутер:
echo "deb http://deb.i2p2.no/ unstable main" >> /etc/apt/sources.list
wget "http://www.i2p2.de/_static/debian-repo.pub" -O- -q | apt-key add -
apt-get update
apt-get install i2p i2p-keyring
Теперь создадим зону, направляющую все запросы к *.i2p на наш сервер. В конфиг bind:
zone "i2p" IN {
type master;
file "/etc/bind/db.i2p";
};
Сама зона:
$ORIGIN i2p
$TTL 7200
i2p. IN SOA ns.i2p. hostmaster.i2p. (
2010020701 ; serial
7200 ; refresh
1800 ; retry
7200 ; expire
7200 ; minimum
)
i2p. IN NS ns.i2p.
ns.i2p. IN A 192.168.1.1
*.i2p. IN A 192.168.1.1
*.i2p. IN AAAA 2a02:578:5002:xxxx::1
Отлично, но как теперь это обработать? Банально завернуть весь трафик на
порт роутера у меня не получилось – прокси ругался на то, что не может
так работать. Пришлось настраивать связку nginx+php5-fpm и писать
небольшой скрипт. Как сделать первую часть – искать долго не надо, благо
мануалов в сети полно. Вторая часть:
Сам скрипт можно увидеть тут.
Это всё! Теперь мы имеем доступ в i2p даже с телефона – никаких проблем.
Killer-feature #2: делаем рабочее место рабочей сетью
Так исторически сложилось ©, что я являюсь системным администратором по
удалёнке сразу в нескольких фирмах. И очень полезно иметь к ним доступ с
любого компьютера в сети. Настройку OpenVPN (или любого другого) для
сервера осуществляем как для любого другого клиента. Например, после
этих действий у нас появился интерфейс tap0 с IP 10.0.0.7/24. Но если мы
обратимся из локальной сети по адресу 10.0.0.1, то трафик уйдёт в
default gateway провайдера. Исправим этот недостаток:
iptables -t nat -A POSTROUTING -d 10.0.0.0/24 -o tap0 -j MASQUERADE
iptables-save > /etc/iptables/rules.v4
Аналогичным образом поступаем для всех сетей на сервере.
Вместо заключения
У нас есть полноценный сервер, который мы можем использовать по своему
усмотрению. DNS, nginx, IPv6, i2p… Можно так же установить зону для
локальной разработки, например, *.dev, и тестировать свои сайты с любого
устройства в локальной сети. Так как каждый компьютер в сети имеет свой
постоянный IPv6-адрес, можно иметь к нему доступ из любой точки мира
(Security warning! Настраивайте файрволы правильно!).
И это всё – лишь вершина айсберга. То, что будет его подводной частью – решать вам.
Буду рад услышать комментарии, предложения, здравую критику и прочее. Спасибо.