# Практика №5. OpenVPN L3 - туннелирование
## Задание к практической работе №5
- Построить инфраструктуру в системе pnet
- Организация OpenVPN L3 тоннеля вовнутрь инфраструктуры
---
## Выполнение практической работы
### Построить инфраструктуру в системе pnetlab
В данной работе и последующих работах все пользователи и устройства были переименованы, чтобы соотвествовать требованиям преподавателя по идентификации учеников. Выбор пал на имя, которое установлено на родном ноутбуке.
При выполнении данного пункта было решено модифицировать инфраструктуру из предыдущей практики №4. На устройствах pfSense и Switch сохраняются VLAN 10 и VLAN 20 c сетями 172.16.10.0/24 и 172.16.20.0/24 соотстветсвенно. SecretDebianOlezhi с предыдущей практики является "мостовым" устройством, чужим во внутренней инфраструктуре. Так же здесь добавлено новое устройство на основе ОС Debian (OpenVPN-Olezha-Client), которое будет играть роль клиента для OpenVPN на уровне L3 в этой практике, в том числе является устройством владельца Kali-Olezha2022.

В данной лабораторной работе применяются технологии OpenVPN.
> **VPN (Virtual Private Network)** -- обобщенное название технологий позволяющих обеспечить построение логической (виртуальной) сети поверх физической, чаще всего поверх сети интернет или иных сетей с низким уровнем доверия.
>
> Для построения сетей VPN обычно используются **туннели**, **туннелирование** это процесс установления соединения между двумя точками с использованием инкапсуляции, когда данные одного протокола помещаются в "конверты" другого протокола с целью обеспечить их прохождение в неподходящей среде, обеспечения целостности и конфиденциальности, защиты с помощью шифрования и т.д. и т.п. Под VPN следует понимать виртуальную сеть, которая образуется путем установления туннельных соединений между отдельными узлами.
**OpenVPN** -- свободная реализация VPN с открытым исходным кодом. Для защиты соединения также используется SSL. Для передачи данных внутри SSL-канала OpenVPN использует собственный протокол с транспортом UDP. OpenVPN обеспечивает высокую безопасность и считается одним из самых защищенных протоколов. Также имеются дополнительные возможности в виде передачи с сервера на клиент необходимых настроек и маршрутов, что позволяет легко создавать сложные сетевые конфигурации без дополнительной настройки клиентов.
Кроме туннелей, работающих на сетевом уровне (L3) -- TUN, OpenVPN позволяет создавать соединения канального (L2) уровня -- TAP, позволяя связывать сети на уровне Ethernet. Однако следует помнить, что в этом случае в туннель будет инкапсулироваться широковещательный трафик, а это может привести к повышенной нагрузке на оборудование и снижению скорости соединения.
К недостаткам можно отнести работу в пользовательском пространстве и некоторую сложность настроек. Скорость внутри OpenVPN туннелей также может быть значительно ниже скорости канала.
:::danger
**!!ВАЖНОЕ ЗАМЕЧАНИЕ!!**
После закрытия лабаторной работы IP некоторых устройств менются, поэтому неудивительно, что на некоторых скриншотах разные IP одних и тех же устройств!
:::
### Организация OpenVPN L3 тоннеля вовнутрь инфраструктуры
Перед началом работы необходимо обновить информацию о последних пакетах, прописав:
```
sudo get update
```
Это позволит устанавливать нам утилиты последних версий.

Затем необходимо скачать с [github](https://github.com/angristan/openvpn-install) OpenVPN при помощи следующего скрипта:
```
curl -O https://raw.githubusercontent.com/angristan/openvpn-install/master/openvpn-install.sh
```
Команда, которая даст ему права на выполнение:
```
chmod +x openvpn-install.sh
```

После того, как скачали, убедимся в этом, просмотрев текущую директорию при помощи `ls`. Как видно на скришноте ниже, openvpn-install.sh установился и теперь его необходимо запустить, чтобы скачать сам OpenVPN.

Для того, чтобы запустить файл используем следующее:
```
sudo ./openvpn-install.sh
```

Для начала нужно будет установить наш внешний IP, который будет доступен для клиентов. Он автоматически вписывается в первый ввод, поэтому можно просто нажать enter. В следующем вводе просто вписываем тот же IP для удобства, что и до этого.
Затем установщик спросит хотим ли мы включить IPv6, который по умолчанию отключен. Нам он не нужен в ходе лабороторной работы - отказываемся, нажимая `n`.
Слушать будем дефолтный порт, поэтому оставляем `1`.
Протокол оставляем на UDP, оставляя `1`.

Всё остальное так же оставляем без изменений.

Когда установщик просит указать имя клиента, то просто вписываем стандартное`client` и оставляем его без пароля, выбирая `1`.

Убедимся, что конфиг клиента создался, проверив директорию при помощи `ls`. На скрине ниже видно, что всё прошло успешно.

Посмотрим на сокеты. SS -- утилита для сканирования сокетов.
```
sudo ss -tunlp
```
:::info
**Объяснения флагов:**
`-t` : отображение TCP-сокетов,
`-u` : отображение UDP-сокетов,
`-l` : отображение только прослушивающихся сокетов,
`-n` : отображение процесса, использующих сокет,
`-p` : не отображать имена служб.
:::
Пока что здесь только открытый 1194 порт от OpenVPN. В будущем, чтобы передать файл, нам необходимо будет открыть 22 порт с ssh.

Необходимо поправить конфигурационные файлы.
```
sudo nano /etc/openvpn/server.conf
```

В данной практике нам не нужен пуш DNS и не нужен дефолтный роутер, который OpenVPN нам настроил, поскольку, в данной работе мы всё же хотим проникнуть внутрь сети и использовать за роутер pfsense. Закомментируем все ненужные строки при помощи '#'.

Обязательно перезапускаем службу openvpn после изменения настроек.
```
sudo service openvpn restart
```

Дальше нужно будет изменить конфигурацию клиента client.ovpn.

Уберём explicit-exit-notify. Он нам не нужен, поскольку этот параметр отвечает за то, что сервер получает сообщение о разъединении в случае отключения клиента, нам это не обязательно. Два остальных отвечают за блок DNS, даже если они не передались, поэтому они тоже не нужны и их стоит закомментировать.

Включаем сервис ssh для того, чтобы передать файл client.ovpn клиенту.
```
systemctl enable ssh
service ssh start
```

Проверим, что всё поднялось и работает.
```
sudo ss -tunlp
```

Первым делом настроим на клиенте /etc/network/interfaces под стать тому, что отображено ниже на скриншоте:

Далее при помощи scp (scp в Linux позволяет выполнить безопасное копирование и перенос файлов) передаём файл на OpenVPN-Olezha-Client.
Воспользуемся следующим шаблоном:
`scp user@ip:/home/user/file /home/user/file` , где user - наименование пользователя машины, к которой мы будем подключаться, ip - ip этой машины, дальше идёт директория и наименование файла на сервере, а в след за ним директория и наименование файла на подключаемой машине.
```
scp olezha@192.168.192.131:/home/olezha/client.ovpn ./client.conf
```

Проверяем, что файл на месте при помощи `ls`. На скриншоте ниже показано, что файл передался.

Дальше необходимо установить OpenVPN на OpenVPN-Olezha-Client.
```
apt install openvpn
```

После установки необходимо перместить файл, который мы получили при помощи scp, в директорию /etc/openvpn/. Сделаем это:
```
mv client.conf /etc/openvpn/
```

Затем необходимо запустить данный конфиг, используя утилиту openvpn и синтаксис `openvpn file`:
```
openvpn /etc/openvpn/client.conf
```
Всё должно будет подключиться самостоятельно, как указано в настройках.

Пробуем с сервера пропинговать туннель tun0, который поднялся на скрине выше, с ip 10.8.0.2. Всё хорошо пингуется.

Попробуем прослушать интерфейс tun0 и посмотреть те самые пинги с kali linux. Для этого необходимо скачать tcpdump:
```
apt install tcpdump
```
и запустить прослушивание:
```
tcpdump -i tun0
```
, где `-i` указывает на название интерфейса.
После запуска видим, что протокол ICMP отрабатывает как надо.

Далее необходимо настроить ещё один файл, для того, чтобы наш сервер мог видеть локальную сеть. Команда iroute используется в конфигурации OpenVPN для указания маршрута на стороне сервера для сети, находящейся за клиентом. Это означает, что когда клиент подключается к серверу OpenVPN, сервер добавляет маршрут для сети, находящейся за клиентом, в свою таблицу маршрутизации.
Пропишем в файле client следующее:
```
iroute 192.168.1.0 255.255.255.0
iroute 172.16.10.0 255.255.255.0
iroute 172.16.20.0 255.255.255.0
```
Всё это сети, которые находятся во внутренней инфраструктуре, которые будут теперь автоматически добавлены в таблицу маршрутизации при подключении.

Снова необходимо перезапустит сервис openvpn.

Далее прописываем сами маршруты, чтобы наша машина знала, как добраться до той или иной сетки. Воспользуемся шаблоном:
`ip route add net/mask via gateway`, где net - адрес сети, mask - маска сети, а gateway, в нашем случае, это ip машины клиента, то есть, другой конец тоннеля tun0.
Таким образом, получим следующее:
```
sudo ip route add 192.168.1.0/24 via 10.8.0.2
sudo ip route add 172.16.10.0/24 via 10.8.0.2
sudo ip route add 172.16.20.0/24 via 10.8.0.2
```
Выведем маршруты и увидим, что всё добавилось.

Далее нам необходимо снова переподключиться на клиенте, посольку мы меняли конфиги:
```
openvpn /etc/openvpn/client.conf
```

Попробуем пропинговать фаервол, но видим, что обратно мы ответ не получаем. Хотя бы не host unreachable!

Устанавливаем прослушивание тоннеля на клиенте OpenVPN-Olezha-Client, как уже делали в данной и предыдущих практиках:
```
tcpdump -i tun0
```
Как мы можем заметить, протокол IMCP отрабатывает, но только в одну сторону, ответ просто не приходит, а вот запрос да.

Для того, чтобы всё заработало необходимо нужно разрешить роутинг и настроить наттинг.

Необходимо изменить параметр net.ipv4.ip_forward для разрешения роутинга.
> **net.ipv4.ip_forward** это параметр ядра Linux, который позволяет пересылать IP-пакеты между различными интерфейсами и сетями. Установка значения 1 для параметра net.ipv4.ip_forward позволяет настроить Linux-систему в качестве маршрутизатора и перенаправлять IP-пакеты между различными интерфейсами и сетями.

Дальше используем `sysctl - p`, чтобы применить изменения без перезагрузки системы.

Далее нам необходима следующая настройка:
```
iptables -t nat -A POSTROUTING -o ens3 -j MASQUERADE
```
Что делает эта команда, мы уже разбирали в 4 практике, но кратко она настраивает NAT на нашем клиента. Когда устройства отправляет пакеты, их IP-адрес заменяется на IP-адрес интерфейса ens3, что позволяет им выходить в интернет с общим IP-адресом маршрутизатора.

Вновь переподключаемся с помощью `openvpn /etc/openvpn/client.conf`, чтобы изменения вступили в силу.

Снова пробуем пропинговать фаервол и теперь нам даже приходят ответы.

Пробуем подключиться к нему и видим, что мы сидим от лица нашего клиента с IP 192.168.1.103.

Также попобуем пропинговать внутрь одного из VLAN и проверим, доходят ли пакеты обратно. IP-адрес OlezhaW10 172.16.20.1 (это мы узнали при помощи `ipconfig`).

Как видно на скрине ниже - пинги проходят, значит мы успешно протянули руки до всей инфраструктуры.
