Prijatelji, zdravo!
Postoji mnogo načina da se povežete od kuće do vašeg radnog prostora u kancelariji. Jedan od njih je korištenje Microsoft Remote Desktop Gatewaya. Ovo je RDP preko HTTP-a. Ne želim se ovdje doticati postavljanja samog RDGW-a, ne želim raspravljati zašto je to dobro ili loše, hajde da ga tretiramo kao jedan od alata za daljinski pristup. Želim razgovarati o zaštiti vašeg RDGW servera od zlog Interneta. Kada sam podesio RDGW server, odmah sam se zabrinuo za sigurnost, posebno zaštitu od grube sile lozinke. Iznenadio sam se što na internetu nisam našao nijedan članak o tome kako to učiniti. Pa, moraćete to sami da uradite.
Sam RDGW nema nikakvu zaštitu. Da, može se izložiti s golim sučeljem bijeloj mreži i radit će odlično. Ali ovo će učiniti pravog administratora ili stručnjaka za sigurnost informacija nelagodnim. Osim toga, omogućit će vam da izbjegnete situaciju blokade računa, kada je nepažljivi zaposlenik zapamtio lozinku za korporativni račun na svom kućnom računaru, a zatim promijenio lozinku.
Dobar način zaštite internih resursa od vanjskog okruženja je kroz različite proxy servere, sisteme za objavljivanje i druge WAF-ove. Podsjetimo da je RDGW još uvijek http, onda samo traži da se spoji specijalizovano rješenje između internih servera i Interneta.
Znam da postoje cool F5, A10, Netscaler(ADC). Kao administrator jednog od ovih sistema, reći ću da je i na ovim sistemima moguće podesiti zaštitu od grube sile. I da, ovi sistemi će vas također zaštititi od bilo kakvog syn flooda.
Ali ne može svaka kompanija priuštiti kupovinu ovakvog rješenja (i pronaći administratora za takav sistem :), ali u isto vrijeme može se pobrinuti za sigurnost!
Potpuno je moguće instalirati besplatnu verziju HAProxy na besplatni operativni sistem. Testirao sam na Debianu 10, haproxy verziji 1.8.19 u stabilnom spremištu. Također sam ga testirao na verziji 2.0.xx iz testnog spremišta.
Ostavit ćemo samo postavljanje debiana izvan okvira ovog članka. Ukratko: na bijelom sučelju zatvorite sve osim porta 443, na sivom sučelju - prema vašoj politici, na primjer, također zatvorite sve osim porta 22. Otvorite samo ono što je potrebno za rad (VRRP na primjer, za plutajući ip).
Prije svega, konfigurirao sam haproxy u SSL modu premošćavanja (aka http mod) i uključio logovanje da vidim šta se dešava unutar RDP-a. Tako da kažem, ušao sam u sredinu. Dakle, /RDWeb putanja navedena u "svim" člancima o postavljanju RDGateway-a nedostaje. Sve što postoji su /rpc/rpcproxy.dll i /remoteDesktopGateway/. U ovom slučaju se ne koriste standardni GET/POST zahtjevi, koristi se njihov vlastiti tip zahtjeva RDG_IN_DATA, RDG_OUT_DATA.
Ne mnogo, ali barem nešto.
Hajde da testiramo.
Pokrećem mstsc, idem na server, vidim četiri 401 (neovlaštene) greške u evidenciji, zatim unesem svoje korisničko ime/lozinku i vidim odgovor 200.
Isključim ga, pokrenem ponovo i u logovima vidim iste četiri greške 401. Unesem pogrešan login/lozinku i opet vidim četiri greške 401. To je ono što mi treba. To je ono što ćemo uhvatiti.
Pošto nije bilo moguće utvrditi url za prijavu, a osim toga, ne znam kako da uhvatim grešku 401 u haproxy-u, uhvatit ću (ne zapravo uhvatiti, već brojati) sve 4xx greške. Pogodan i za rješavanje problema.
Suština zaštite će biti u tome da ćemo računati broj 4xx grešaka (na backendu) po jedinici vremena i ako pređe navedeno ograničenje, onda odbaciti (na frontendu) sve daljnje veze sa ovog ip-a za određeno vrijeme .
Tehnički, ovo neće biti zaštita od grube sile lozinke, to će biti zaštita od 4xx grešaka. Na primjer, ako često tražite nepostojeći url (404), zaštita će također raditi.
Najjednostavniji i najefikasniji način je računati na backend i prijaviti se ako se nešto dodatno pojavi:
frontend fe_rdp_tsc
bind *:443 ssl crt /etc/haproxy/cert/desktop.example.com.pem
mode http
...
default_backend be_rdp_tsc
backend be_rdp_tsc
...
mode http
...
#создать таблицу, строковую, 1000 элементов, протухает через 15 сек, записать кол-во ошибок за последние 10 сек
stick-table type string len 128 size 1k expire 15s store http_err_rate(10s)
#запомнить ip
http-request track-sc0 src
#запретить с http ошибкой 429, если за последние 10 сек больше 4 ошибок
http-request deny deny_status 429 if { sc_http_err_rate(0) gt 4 }
...
server rdgw01 192.168.1.33:443 maxconn 1000 weight 10 ssl check cookie rdgw01
server rdgw02 192.168.2.33:443 maxconn 1000 weight 10 ssl check cookie rdgw02
Nije najbolja opcija, zakomplicirajmo. Računaćemo na backend i blokirati na frontendu.
Grubo ćemo se ponašati prema napadaču i prekinuti njegovu TCP vezu.
frontend fe_rdp_tsc
bind *:443 ssl crt /etc/haproxy/cert/ertelecom_ru_2020_06_11.pem
mode http
...
#создать таблицу ip адресов, 1000 элементов, протухнет через 15 сек, сохрянять из глобального счётчика
stick-table type ip size 1k expire 15s store gpc0
#взять источник
tcp-request connection track-sc0 src
#отклонить tcp соединение, если глобальный счётчик >0
tcp-request connection reject if { sc0_get_gpc0 gt 0 }
...
default_backend be_rdp_tsc
backend be_rdp_tsc
...
mode http
...
#создать таблицу ip адресов, 1000 элементов, протухнет через 15 сек, сохранять кол-во ошибок за 10 сек
stick-table type ip size 1k expire 15s store http_err_rate(10s)
#много ошибок, если кол-во ошибок за 10 сек превысило 8
acl errors_too_fast sc1_http_err_rate gt 8
#пометить атаку в глобальном счётчике (увеличить счётчик)
acl mark_as_abuser sc0_inc_gpc0(fe_rdp_tsc) gt 0
#обнулить глобальный счётчик
acl clear_as_abuser sc0_clr_gpc0(fe_rdp_tsc) ge 0
#взять источник
tcp-request content track-sc1 src
#отклонить, пометить, что атака
tcp-request content reject if errors_too_fast mark_as_abuser
#разрешить, сбросить флажок атаки
tcp-request content accept if !errors_too_fast clear_as_abuser
...
server rdgw01 192.168.1.33:443 maxconn 1000 weight 10 ssl check cookie rdgw01
server rdgw02 192.168.2.33:443 maxconn 1000 weight 10 ssl check cookie rdgw02
ista stvar, ali ljubazno, vratit ćemo grešku http 429 (Previše zahtjeva)
frontend fe_rdp_tsc
...
stick-table type ip size 1k expire 15s store gpc0
http-request track-sc0 src
http-request deny deny_status 429 if { sc0_get_gpc0 gt 0 }
...
default_backend be_rdp_tsc
backend be_rdp_tsc
...
stick-table type ip size 1k expire 15s store http_err_rate(10s)
acl errors_too_fast sc1_http_err_rate gt 8
acl mark_as_abuser sc0_inc_gpc0(fe_rdp_tsc) gt 0
acl clear_as_abuser sc0_clr_gpc0(fe_rdp_tsc) ge 0
http-request track-sc1 src
http-request allow if !errors_too_fast clear_as_abuser
http-request deny deny_status 429 if errors_too_fast mark_as_abuser
...
Provjeravam: Pokrećem mstsc i počinjem nasumično unositi lozinke. Nakon trećeg pokušaja, u roku od 10 sekundi me vraća, a mstsc daje grešku. Kao što se može vidjeti u dnevnicima.
Objašnjenja. Daleko sam od haproxy majstora. Ne razumijem zašto, na primjer
http-request deny deny_status 429 if { sc_http_err_rate(0) gt 4 }
omogućava vam da napravite oko 10 grešaka prije nego što proradi.
Zbunjen sam oko numeracije brojača. Majstori haproksija, biće mi drago ako me upotpunite, ispravite, učinite boljim.
U komentarima možete predložiti druge načine zaštite RD Gatewaya, bit će zanimljivo proučiti.
Što se tiče Windows Remote Desktop klijenta (mstsc), vrijedi napomenuti da on ne podržava TLS1.2 (barem u Windows 7), pa sam morao napustiti TLS1; ne podržava trenutnu šifru, tako da sam morao ostaviti i stare.
Za one koji ništa ne razumiju, tek uče, a već žele da rade dobro, dat ću vam cijelu konfiguraciju.
haproxy.conf
global
log /dev/log local0
log /dev/log local1 notice
chroot /var/lib/haproxy
stats socket /run/haproxy/admin.sock mode 660 level admin expose-fd listeners
stats timeout 30s
user haproxy
group haproxy
daemon
# Default SSL material locations
ca-base /etc/ssl/certs
crt-base /etc/ssl/private
# See: https://ssl-config.mozilla.org/#server=haproxy&server-version=2.0.3&config=intermediate
#ssl-default-bind-ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE
-RSA-AES256-GCM-SHA384
ssl-default-bind-ciphers ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:RSA+AESGCM:RSA+AES:!aNULL:!MD5:!DSS
ssl-default-bind-ciphersuites TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256
#ssl-default-bind-options ssl-min-ver TLSv1.2 no-tls-tickets
ssl-default-bind-options no-sslv3
ssl-server-verify none
defaults
log global
mode http
option httplog
option dontlognull
timeout connect 5000
timeout client 15m
timeout server 15m
errorfile 400 /etc/haproxy/errors/400.http
errorfile 403 /etc/haproxy/errors/403.http
errorfile 408 /etc/haproxy/errors/408.http
errorfile 500 /etc/haproxy/errors/500.http
errorfile 502 /etc/haproxy/errors/502.http
errorfile 503 /etc/haproxy/errors/503.http
errorfile 504 /etc/haproxy/errors/504.http
frontend fe_rdp_tsc
bind *:443 ssl crt /etc/haproxy/cert/dektop.example.com.pem
mode http
capture request header Host len 32
log global
option httplog
timeout client 300s
maxconn 1000
stick-table type ip size 1k expire 15s store gpc0
tcp-request connection track-sc0 src
tcp-request connection reject if { sc0_get_gpc0 gt 0 }
acl rdweb_domain hdr(host) -i beg dektop.example.com
http-request deny deny_status 400 if !rdweb_domain
default_backend be_rdp_tsc
backend be_rdp_tsc
balance source
mode http
log global
stick-table type ip size 1k expire 15s store http_err_rate(10s)
acl errors_too_fast sc1_http_err_rate gt 8
acl mark_as_abuser sc0_inc_gpc0(fe_rdp_tsc) gt 0
acl clear_as_abuser sc0_clr_gpc0(fe_rdp_tsc) ge 0
tcp-request content track-sc1 src
tcp-request content reject if errors_too_fast mark_as_abuser
tcp-request content accept if !errors_too_fast clear_as_abuser
option forwardfor
http-request add-header X-CLIENT-IP %[src]
option httpchk GET /
cookie RDPWEB insert nocache
default-server inter 3s rise 2 fall 3
server rdgw01 192.168.1.33:443 maxconn 1000 weight 10 ssl check cookie rdgw01
server rdgw02 192.168.2.33:443 maxconn 1000 weight 10 ssl check cookie rdgw02
frontend fe_stats
mode http
bind *:8080
acl ip_allow_admin src 192.168.66.66
stats enable
stats uri /stats
stats refresh 30s
#stats admin if LOCALHOST
stats admin if ip_allow_admin
Zašto dva servera na backendu? Jer na ovaj način možete napraviti toleranciju grešaka. Haproxy takođe može napraviti dva sa plutajućim bijelim IP-om.
Računarski resursi: možete početi sa „dva koncerta, dva jezgra, računar za igre“. Prema
Reference:
izvor: www.habr.com