[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"project-81776":3},{"id":4,"name":5,"fullName":6,"owner":7,"repo":5,"description":8,"homepage":8,"htmlUrl":8,"language":9,"languages":8,"totalLinesOfCode":8,"stars":10,"forks":11,"watchers":12,"openIssues":13,"contributorsCount":13,"subscribersCount":13,"size":13,"stars1d":13,"stars7d":11,"stars30d":11,"stars90d":13,"forks30d":13,"starsTrendScore":13,"compositeScore":14,"rankGlobal":8,"rankLanguage":8,"license":8,"archived":15,"fork":15,"defaultBranch":16,"hasWiki":17,"hasPages":15,"topics":18,"createdAt":8,"pushedAt":8,"updatedAt":19,"readmeContent":20,"aiSummary":21,"trendingCount":13,"starSnapshotCount":13,"syncStatus":22,"lastSyncTime":23,"discoverSource":24},81776,"vpn_over_ssh","kleimer\u002Fvpn_over_ssh","kleimer",null,"Go",22,1,21,0,35.5,false,"main",true,[],"2026-06-12 04:01:35","# VPN over SSH\n\nПроект реализует L3-туннель поверх обычного SSH с использованием `ssh -w` \u002F OpenSSH TUN. Сервер поднимает пул TUN-интерфейсов, клиенты случайно выбирают свободный `tunN`, подключаются по SSH и направляют трафик через зашифрованный SSH-канал.\n\nОсновная идея MVP: использовать стандартный OpenSSH вместо отдельного VPN-сервера. На сервере достаточно отдельного `sshd`-инстанса с `PermitTunnel point-to-point`, подготовленного пула `tun100..tun200` и NAT. На клиентах используются Linux shell-клиент или Windows Go\u002FWintun-клиент.\n\n## Схема работы\n\n```text\nUser workstation\n    |\n    | local TUN adapter\n    |\nLinux: sshtun_pool_client.sh\nWindows: sshtun_pool_client.exe + Wintun\n    |\n    | SSH TCP, tun@openssh.com \u002F ssh -w N:N\n    |\nsshtun-pool-sshd на сервере\n    |\n    | tunN -> NAT -> WAN\n    v\nInternet \u002F routed networks\n```\n\nПо умолчанию используется пул `tun100..tun200` и адресация внутри `10.250.0.0\u002F16`:\n\n```text\ntun100 -> server 10.250.0.1,   client 10.250.0.2\ntun101 -> server 10.250.0.5,   client 10.250.0.6\ntun200 -> server 10.250.1.145, client 10.250.1.146\n```\n\nАдреса выделяются парами по схеме `\u002F30`-блоков. Клиенту не нужно заранее знать свой IP: он вычисляется из номера выбранного `tunN`.\n\n## Что лежит в проекте\n\n```text\n.\n├── install_server.sh\n├── sshtun_pool_client.sh\n└── sshtun_pool_windows_client\n    ├── README.md\n    ├── build.ps1\n    ├── go.mod\n    ├── go.sum\n    ├── cmd\u002Fsshtun_pool_client\u002Fmain.go\n    └── internal\n        ├── admin\n        ├── ipcalc\n        ├── packetpump\n        ├── routes\n        ├── sshtransport\n        └── wintun\n```\n\n### `install_server.sh`\n\nСерверный установщик. Он:\n\n- устанавливает зависимости;\n- создаёт системного пользователя `sshvpn`;\n- создаёт отдельную конфигурацию SSHD в `\u002Fopt\u002Fsshtun_pool\u002Fsshd_config`;\n- создаёт отдельный systemd-сервис `sshtun-pool-sshd.service`;\n- создаёт service `sshtun-pool-network.service` для подготовки TUN-пула и NAT;\n- генерирует отдельный host key для SSH-TUN сервиса;\n- включает `net.ipv4.ip_forward=1`;\n- создаёт `tun100..tun200`;\n- добавляет минимальные правила NAT\u002Fforwarding через WAN-интерфейс.\n\nВажно: это отдельный SSHD-инстанс на отдельном порту, а не изменение основного SSH на `22\u002Ftcp`.\n\n### `sshtun_pool_client.sh`\n\nLinux-клиент. Поддерживает:\n\n- full-tunnel режим;\n- split-tunnel режим;\n- route\u002Finclude\u002Fexclude CIDR;\n- списки маршрутов из файлов;\n- DNS через `resolvectl`;\n- IPv6 blackhole для защиты от IPv6 leak;\n- lock от параллельных стартов\u002Fостановок;\n- cleanup старых управляемых `tunN`;\n- работу с passphrase-protected ключами через `ssh-agent` или `--ask-passphrase`;\n- `status`, `doctor`, `cleanup`.\n\n### `sshtun_pool_windows_client\u002F`\n\nWindows-клиент на Go. Использует Wintun и совместимую с Linux-клиентом CLI-схему. Основной бинарь: `sshtun_pool_client.exe`.\n\nПоддерживает:\n\n- background worker после `start`;\n- состояние в `C:\\ProgramData\\sshtun_pool_client\\state.json`;\n- runtime-лог в `C:\\ProgramData\\sshtun_pool_client\\sshtun.log`;\n- full-tunnel и split-tunnel;\n- include\u002Fexclude CIDR и route-файлы;\n- encrypted private keys;\n- `status`, `doctor`, `cleanup`;\n- pinning SSH host key через `--host-key-sha256`.\n\n## Требования\n\n### Сервер\n\nПоддерживаемые системы: Linux с systemd, OpenSSH server, iproute2, iptables.\n\nНужны:\n\n- root-доступ;\n- `\u002Fdev\u002Fnet\u002Ftun`;\n- доступный TCP-порт, по умолчанию `65523`;\n- разрешённый forwarding\u002FNAT;\n- внешний IPv4-адрес или домен.\n\n### Linux-клиент\n\nНужны:\n\n- root-доступ для создания TUN и маршрутов;\n- `ssh`;\n- `iproute2`;\n- `flock`;\n- `getent`;\n- желательно `resolvectl` для DNS.\n\n### Windows-клиент\n\nНужны:\n\n- Windows с правами администратора;\n- `sshtun_pool_client.exe`;\n- `wintun.dll` рядом с exe;\n- приватный SSH-ключ пользователя.\n\nДля сборки Windows-клиента нужен Go `1.22+` и PowerShell.\n\n## Быстрый старт\n\n### 1. Установка сервера\n\nНа сервере:\n\n```bash\nsudo bash install_server.sh\n```\n\nПо умолчанию будут использованы параметры:\n\n```text\nuser:        sshvpn\nport:        65523\ntun pool:    tun100..tun200\nnetwork:     10.250.0.0\u002F16\nmtu:         1400\nbase dir:    \u002Fopt\u002Fsshtun_pool\n```\n\nПроверка сервисов:\n\n```bash\nsystemctl status sshtun-pool-sshd.service --no-pager\nsystemctl status sshtun-pool-network.service --no-pager\n```\n\nПроверка listening port:\n\n```bash\nss -lntp | grep 65523\n```\n\nПроверка TUN-пула:\n\n```bash\nip addr show tun100\nip addr show tun101\n```\n\n### 2. Генерация пользовательского ключа\n\nНа админской машине или на клиенте:\n\n```bash\nssh-keygen -t ed25519 -f .\u002Fid_ed25519 -N \"\" -C \"user-device\"\n```\n\nНа сервер нужно добавить публичный ключ в:\n\n```text\n\u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys\n```\n\nРекомендуемая строка ключа:\n\n```text\nno-pty,no-agent-forwarding,no-X11-forwarding,no-port-forwarding,no-user-rc ssh-ed25519 AAAAC3... user-device\n```\n\nДля random pool mode не добавляйте `tunnel=\"N\"` в `authorized_keys`. Иначе ключ будет прибит к конкретному TUN-номеру и несколько устройств с одним ключом начнут конфликтовать.\n\nПосле изменения ключей перезапуск сервиса обычно не нужен, но права должны быть корректными:\n\n```bash\nchown root:sshvpn \u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys\nchmod 640 \u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys\n```\n\n### 3. Подключение с Linux\n\nFull-tunnel режим:\n\n```bash\nsudo bash sshtun_pool_client.sh start --host SERVER_IP --key .\u002Fid_ed25519\n```\n\nFull-tunnel, но локальные\u002Fprivate сети идут напрямую:\n\n```bash\nsudo bash sshtun_pool_client.sh start \\\n  --host SERVER_IP \\\n  --key .\u002Fid_ed25519 \\\n  --exclude 10.0.0.0\u002F8 \\\n  --exclude 172.16.0.0\u002F12 \\\n  --exclude 192.168.0.0\u002F16\n```\n\nSplit-tunnel режим:\n\n```bash\nsudo bash sshtun_pool_client.sh start \\\n  --host SERVER_IP \\\n  --key .\u002Fid_ed25519 \\\n  --no-full-tunnel \\\n  --route 10.10.0.0\u002F16 \\\n  --route 172.20.0.0\u002F16\n```\n\nМаршруты из файла:\n\n```bash\nsudo bash sshtun_pool_client.sh start \\\n  --host SERVER_IP \\\n  --key .\u002Fid_ed25519 \\\n  --exclude-file .\u002Fru-cidrs.txt\n```\n\nОстановка:\n\n```bash\nsudo bash sshtun_pool_client.sh stop\n```\n\nДиагностика:\n\n```bash\nsudo bash sshtun_pool_client.sh status\nsudo bash sshtun_pool_client.sh doctor\nsudo bash sshtun_pool_client.sh cleanup\n```\n\n### 4. Сборка Windows-клиента\n\nВ каталоге `sshtun_pool_windows_client`:\n\n```powershell\nSet-ExecutionPolicy -Scope Process Bypass -Force\n.\\build.ps1\n```\n\nСкрипт скачает `wintun.dll`, подтянет Go-модули и соберёт:\n\n```text\ndist\\sshtun_pool_client.exe\ndist\\wintun.dll\n```\n\nСборка под другую архитектуру:\n\n```powershell\n.\\build.ps1 -Arch amd64\n.\\build.ps1 -Arch arm64\n.\\build.ps1 -Arch 386\n```\n\n### 5. Подключение с Windows\n\nPowerShell нужно запустить от имени администратора.\n\nFull-tunnel режим:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe start --host SERVER_IP --key .\\id_ed25519\n```\n\nFull-tunnel с исключением private-сетей:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe start `\n  --host SERVER_IP `\n  --key .\\id_ed25519 `\n  --exclude-private\n```\n\nSplit-tunnel режим:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe start `\n  --host SERVER_IP `\n  --key .\\id_ed25519 `\n  --no-full-tunnel `\n  --route 10.10.0.0\u002F16 `\n  --route 172.20.0.0\u002F16\n```\n\nМаршруты из файла:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe start --host SERVER_IP --key .\\id_ed25519 --exclude-file .\\ru-cidrs.txt\n```\n\nОстановка и диагностика:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe status\n.\\dist\\sshtun_pool_client.exe doctor\n.\\dist\\sshtun_pool_client.exe stop\n.\\dist\\sshtun_pool_client.exe cleanup\n```\n\n## Основные режимы маршрутизации\n\n### Full tunnel\n\nВесь IPv4-трафик уходит через туннель. Для этого клиент добавляет два маршрута:\n\n```text\n0.0.0.0\u002F1\n128.0.0.0\u002F1\n```\n\nТакой подход не ломает исходный default route полностью и позволяет оставить отдельный bypass-route до реального IP сервера.\n\n### Full tunnel + excludes\n\nОсновной интернет идёт через туннель, но отдельные сети уходят напрямую через исходный default gateway.\n\nТиповой пример:\n\n```bash\n--exclude 10.0.0.0\u002F8 --exclude 172.16.0.0\u002F12 --exclude 192.168.0.0\u002F16\n```\n\nНа Windows есть сокращение:\n\n```powershell\n--exclude-private\n```\n\n### Split tunnel\n\nЧерез туннель идут только явно указанные сети:\n\n```bash\n--no-full-tunnel --route 10.10.0.0\u002F16 --route 172.20.0.0\u002F16\n```\n\nЭто удобно для корпоративных сетей, внутренних ресурсов или отдельных подсетей.\n\n## CLI-опции\n\nОбщие опции Linux\u002FWindows:\n\n```text\n--host HOST\n--key FILE\n--user USER\n--port PORT\n--tun N\n--tun-start N\n--tun-end N\n--mtu N\n--no-full-tunnel\n--route CIDR\n--route-file FILE\n--include CIDR\n--include-file FILE\n--exclude CIDR\n--exclude-file FILE\n--route-private\n--exclude-private\n--no-dns\n--dns \"1.1.1.1 8.8.8.8\"\n--no-block-ipv6\n--no-clean-orphans\n--ask-passphrase\n```\n\nLinux-дополнительно:\n\n```text\n--remote-setup\n--no-remote-setup\n--remote-wan-dev DEV\n```\n\nWindows-дополнительно:\n\n```text\n--adapter-name \"SSHTUN Pool\"\n--host-key-sha256 SHA256:...\n--route-style gateway|onlink\n--connect-timeout SECONDS\n--keepalive-seconds SECONDS\n--keepalive-misses N\n```\n\n## Безопасная модель MVP\n\nСерверный установщик создаёт отдельный `sshd`-инстанс, отдельного пользователя и отдельный `authorized_keys`:\n\n```text\n\u002Fopt\u002Fsshtun_pool\u002Fsshd_config\n\u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys\n\u002Fopt\u002Fsshtun_pool\u002Fssh_host_ed25519_key\n```\n\nОсновные ограничения в SSHD-конфигурации:\n\n```text\nPasswordAuthentication no\nPubkeyAuthentication yes\nAuthenticationMethods publickey\nPermitRootLogin no\nAllowUsers sshvpn\nPermitTunnel point-to-point\nAllowTcpForwarding no\nGatewayPorts no\nPermitTTY no\nX11Forwarding no\nAllowAgentForwarding no\nAllowStreamLocalForwarding no\nPermitUserEnvironment no\nForceCommand \u002Fbin\u002Ffalse\n```\n\nПользователь `sshvpn` создаётся с `nologin`, то есть обычный shell ему не нужен. Для `ssh -w` достаточно TUN-запроса, shell-доступ пользователю не выдаётся.\n\n## Модель пользователей и ключей\n\nДля MVP используется простая модель:\n\n```text\nодин пользователь = один SSH-ключ\n```\n\nОдин ключ может использоваться на нескольких устройствах. Так как клиент выбирает случайный `tunN` из пула, несколько устройств с одним ключом не должны конфликтовать, пока есть свободные TUN-номера.\n\nДля production желательно добавить отдельный слой учёта и ограничений:\n\n- лимит одновременных подключений на ключ;\n- отзыв ключа через удаление из `authorized_keys`;\n- перевыпуск ключа через удаление старого и добавление нового;\n- аудит подключений по SSHD-логам;\n- версионирование и checksum файла `authorized_keys` при массовой синхронизации.\n\n## Где лежит состояние и логи\n\n### Linux-клиент\n\n```text\n\u002Frun\u002Fsshtun\u002Fstate\n\u002Frun\u002Fsshtun\u002Fssh.log\n\u002Frun\u002Fsshtun\u002Fssh.last.log\n\u002Frun\u002Fsshtun\u002Fknown_hosts\n\u002Frun\u002Fsshtun\u002Flock\n```\n\nКоманды:\n\n```bash\nsudo bash sshtun_pool_client.sh status\nsudo bash sshtun_pool_client.sh doctor\n```\n\n### Windows-клиент\n\n```text\nC:\\ProgramData\\sshtun_pool_client\\state.json\nC:\\ProgramData\\sshtun_pool_client\\sshtun.log\n```\n\nКоманды:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe status\n.\\dist\\sshtun_pool_client.exe doctor\n```\n\n### Сервер\n\n```bash\njournalctl -u sshtun-pool-sshd.service -n 200 --no-pager\njournalctl -u sshtun-pool-network.service -n 200 --no-pager\nsystemctl status sshtun-pool-sshd.service --no-pager\nsystemctl status sshtun-pool-network.service --no-pager\n```\n\n## Проверка после подключения\n\nLinux:\n\n```bash\nip addr show tun100\nip route\ncurl -4 ifconfig.me\nsudo bash sshtun_pool_client.sh status\n```\n\nWindows:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe status\ncurl.exe -4 ifconfig.me\nroute print -4\nipconfig \u002Fall\n```\n\nНа сервере:\n\n```bash\nip addr show tun100\niptables -t nat -S | grep 10.250\njournalctl -u sshtun-pool-sshd.service -f\n```\n\n## Типовые проблемы\n\n### `Permission denied`\n\nПроверить:\n\n- публичный ключ добавлен в `\u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys`;\n- права на файл `authorized_keys` корректные;\n- клиент использует правильный приватный ключ;\n- подключение идёт на правильный порт `65523`, а не на основной SSH-порт;\n- для ключа с passphrase используется `ssh-agent` или `--ask-passphrase`.\n\n### `Connection refused`\n\nПроверить:\n\n```bash\nsystemctl status sshtun-pool-sshd.service --no-pager\nss -lntp | grep 65523\niptables -S\n```\n\nТакже убедиться, что порт открыт в firewall\u002Fsecurity group провайдера.\n\n### `Could not request tunnel forwarding` \u002F TUN не появляется\n\nПроверить на сервере:\n\n```bash\nls -l \u002Fdev\u002Fnet\u002Ftun\ncat \u002Fopt\u002Fsshtun_pool\u002Fsshd_config | grep PermitTunnel\nsystemctl status sshtun-pool-network.service --no-pager\n```\n\nВ конфигурации SSHD должно быть:\n\n```text\nPermitTunnel point-to-point\n```\n\n### Подключение есть, но интернет не работает\n\nПроверить серверный NAT и forwarding:\n\n```bash\nsysctl net.ipv4.ip_forward\niptables -t nat -S | grep MASQUERADE\niptables -S FORWARD | grep 10.250\nip route\n```\n\nПроверить, что WAN-интерфейс определился правильно.\n\n### DNS не работает\n\nLinux-клиент использует `resolvectl`, если он установлен. Проверить:\n\n```bash\nresolvectl status\nsudo bash sshtun_pool_client.sh doctor\n```\n\nМожно отключить изменение DNS:\n\n```bash\n--no-dns\n```\n\nИли указать свои DNS:\n\n```bash\n--dns \"1.1.1.1 8.8.8.8\"\n```\n\n### IPv6 leak\n\nПо умолчанию Linux-клиент добавляет blackhole для IPv6 default route. Отключить это поведение можно так:\n\n```bash\n--no-block-ipv6\n```\n\nДля production лучше отдельно решить, будет ли IPv6 полностью запрещён или поддержан через отдельную маршрутизацию.\n\n### Остались старые TUN-адаптеры\n\nLinux:\n\n```bash\nsudo bash sshtun_pool_client.sh cleanup\n```\n\nWindows:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe cleanup\n```\n\nCleanup удаляет только управляемые интерфейсы\u002Fадаптеры проекта, а не произвольные сетевые интерфейсы системы.\n\n## Настройка через переменные окружения\n\nСерверный установщик поддерживает переопределение параметров через env:\n\n```bash\nLISTEN_PORT=65523 \\\nTUN_NUM_START=100 \\\nTUN_POOL_SIZE=101 \\\nTUN_MTU=1400 \\\nBASE_DIR=\u002Fopt\u002Fsshtun_pool \\\nsudo -E bash install_server.sh\n```\n\nОсновные переменные:\n\n```text\nBASE_DIR\nSERVICE_NAME\nNETWORK_SERVICE_NAME\nSYSTEM_USER\nLISTEN_PORT\nTUN_NUM_START\nTUN_POOL_SIZE\nTUN_PREFIX\nTUN_MTU\nTUN_NET_A\nTUN_NET_B\nTUN_POOL_CIDR\nLIMIT_NOFILE\nTASKS_MAX\n```\n\nLinux-клиент также можно настраивать через env, но обычно удобнее использовать CLI-флаги.\n\n## Что важно для MVP\n\nМинимальный рабочий набор:\n\n```text\ninstall_server.sh\nsshtun_pool_client.sh\nsshtun_pool_windows_client\u002Fbuild.ps1\nsshtun_pool_windows_client\u002Fgo.mod\nsshtun_pool_windows_client\u002Fgo.sum\nsshtun_pool_windows_client\u002Fcmd\u002Fsshtun_pool_client\u002Fmain.go\nsshtun_pool_windows_client\u002Finternal\u002F**\n```\n\nДля сборки Windows-клиента нужны все Go-файлы внутри `cmd\u002F` и `internal\u002F`, а также `go.mod`, `go.sum`, `build.ps1`. Удалять `*_other.go` не стоит: они нужны для корректной кроссплатформенной сборки и заглушек под неподдерживаемые платформы.\n\n## Ограничения текущей версии\n\n- Это MVP\u002Fпрототип транспортного слоя, а не полный коммерческий клиент с GUI, автообновлением и подписанным installer.\n- Нет центрального control-plane для выдачи\u002Fотзыва ключей.\n- Нет встроенного лимита одновременных подключений на один ключ.\n- Нет встроенной синхронизации `authorized_keys` по флоту серверов.\n- Нет встроенного мониторинга качества канала.\n- IPv6 по умолчанию скорее блокируется, чем полноценно туннелируется.\n- Windows-сборка требует Wintun DLL рядом с exe.\n\n## Рекомендованный roadmap после MVP\n\n1. Добавить генерацию пользовательского JSON-профиля: host, port, user, private key, routing mode, DNS, route\u002Fexclude files.\n2. Добавить централизованный revoke\u002Freissue ключей.\n3. Добавить лимит одновременных подключений на ключ.\n4. Добавить безопасную синхронизацию `authorized_keys` по серверам.\n5. Добавить checksum\u002Fversion для файлов ключей.\n6. Добавить GUI\u002FTray-клиент поверх CLI-ядра.\n7. Подписать Windows\u002FmacOS binaries и installer.\n8. Добавить автообновление клиента.\n9. Вынести большие списки маршрутов, например country CIDR, в отдельный обновляемый файл\u002Fсервис.\n10. Добавить полноценный healthcheck: SSH connect, tunnel up, DNS, public IP, route test, packet pump stats.\n\n## Короткая шпаргалка\n\nСервер:\n\n```bash\nsudo bash install_server.sh\nsystemctl status sshtun-pool-sshd.service --no-pager\n```\n\nКлюч:\n\n```bash\nssh-keygen -t ed25519 -f .\u002Fid_ed25519 -N \"\" -C \"user-device\"\ncat .\u002Fid_ed25519.pub >> \u002Fopt\u002Fsshtun_pool\u002Fauthorized_keys\n```\n\nLinux connect:\n\n```bash\nsudo bash sshtun_pool_client.sh start --host SERVER_IP --key .\u002Fid_ed25519\nsudo bash sshtun_pool_client.sh stop\n```\n\nWindows build:\n\n```powershell\ncd sshtun_pool_windows_client\nSet-ExecutionPolicy -Scope Process Bypass -Force\n.\\build.ps1\n```\n\nWindows connect:\n\n```powershell\n.\\dist\\sshtun_pool_client.exe start --host SERVER_IP --key .\\id_ed25519\n.\\dist\\sshtun_pool_client.exe stop\n```\n","该项目实现了一个基于SSH的L3隧道，允许用户通过标准OpenSSH创建安全的网络连接。核心功能包括利用`ssh -w`选项和OpenSSH TUN功能，在服务器端配置一个TUN接口池，并在客户端随机选择可用的TUN接口进行连接。技术上，项目使用Go语言开发，支持Linux和Windows平台，提供全隧道和分割隧道模式，以及灵活的路由配置。适用于需要快速部署轻量级VPN解决方案的场景，如远程办公、临时访问受保护网络等，特别适合已有SSH基础设施的环境。",2,"2026-06-11 04:06:40","CREATED_QUERY"]