Wie kann ich das iptables Modul "connlimit" installieren?

Status
Für weitere Antworten geschlossen.

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
Mein Cloud-Anbieter erlaubt "nur" 10 parallele Verbindungen. Da ich möglichst schnell den aktuellen Datenbestand in die Cloud laden möchte, habe ich drei NAS an drei Standorten positioniert und Cloud Sync hinterlegt. Leider erlaubt Cloud Sync aber nicht weniger als 3 parallele Uploads:
2019-12-11 10_29_20.jpg

Dadurch habe ich automatisch 3x3 Uploads, also 9 Verbindungen bereits verbraucht.

Zuerst habe ich versucht per Browser Developer Tools den Wert im HTML Quelltext zu verändern und dann das Formular abzusenden. Aber so lässt sich das NAS leider nicht austricksen ^^

Dann habe ich ein wenig recherchiert und bin über iptables und das Modul connlimit gestoßen. Damit kann ich wohl gezielt die Domain meiner Cloud auf eine Verbindung limitieren:
https://serverfault.com/a/547317/44086
Rich (BBCode):
iptables -A OUTPUT -p tcp --syn -m connlimit --connlimit-above 1 --connlimit-mask 0 -j DROP -d cloud.example.org

Leider fehlt aber dieses Modul:
Rich (BBCode):
iptables v1.6.0: Couldn't load match `connlimit':No such file or directory

Komisch ist dabei noch, dass ein NAS über "conntrack" verfügt, aber andere Modelle wiederum nicht. Ich vermute die sind Teil von irgendeinem nachinstallierten Paket. Ich habe schon überlegt ob ich einfach mal alle Pakete installiere. Vielleicht habe ich ja Glück und irgendwo ist das dabei ^^

Oder ihr sagt mir wie ich das draufbekomme. :p
 

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
Ich habe mal mit dem Firefox Netzwerkmonitor (F12) verfolgt was beim Ändern der Einstellung übertragen wird. Ich habe dann über "Bearbeiten und erneut senden" den Wert auf 1 geändert und dann erneut abgesendet:
2019-12-11 12_21_38.jpg

Öffne ich nun die Cloud Sync Einstellungen sehe ich, dass der Wert erfolgreich übernommen wurde, doch leider greift er nicht. Ich habe auch "0" und "2" getestet. Es gehen aber immer 3 Uploads auf. Die 3 sind also sogar im Programmcode als Mindestwert hinterlegt :(
2019-12-11 12_18_41.jpg
 

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
Ok, ich nähere mich dem Ergebnis:
Rich (BBCode):
#!/bin/sh
# #####################################
# limitCloudSync v0.1
# 
# Notes:
# This adds a new rule to iptables that limits OUTGOING traffic to a specific domain
# 
# Changelog:
# 0.1
# - first release
# 
# Todo:
# #####################################
destination="owncube.com"
# remove existing rules
iptables -D OUTPUT --match state --state NEW --jump DROP -d $destination
iptables -D OUTPUT -p TCP --match state --state NEW --match limit --limit 1/h --limit-burst 2 --jump ACCEPT -d $destination
# add new rules
iptables -A OUTPUT -p TCP --match state --state NEW --match limit --limit 1/h --limit-burst 2 --jump ACCEPT -d $destination
iptables -A OUTPUT --match state --state NEW --jump DROP -d $destination

Das führt dazu, dass Cloud Sync innerhalb einer 2 Stunde zwei neue Verbindungen aufbauen kann. Also nach Starten des Scriptes sieht es so aus:
2019-12-12 12_54_38.jpg

Das Problem daran ist jetzt aber, dass wenn ein Upload länger als 1 Stunde dauert, dass dann wieder zwei neue Verbindungen erlaubt sind. Am Ende sind es also wieder 3. Und andersherum, wenn nur zwei kleine Dateien hochgeladen wurden, dauert es 1 Stunde bis die nächsten zwei kleinen Dateien hochgeladen werden können.

Bei einem NAS läuft zB gerade ein Upload (keine Ahnung warum keine 2 ^^) und die restlichen Verbindungen haben den Status "SYN_SENT" (wird also gerade blockiert):
Rich (BBCode):
ash-4.3# netstat -a | grep owncub
tcp        0      1 DiskStation.fritz:52304 occloud.owncub:https SYN_SENT
tcp        0 195840 DiskStation.fritz:51688 occloud.owncub:https ESTABLISHED
tcp        0      1 DiskStation.fritz:52306 occloud.owncub:https SYN_SENT

Daraus schließe ich, dass ich ja hingehen könnte und die bestehende Regel während dem Betrieb so überschreibe, dass er eine Verbindung mehr freigibt. Quasi den "limit-burst"-Bucket manuell "nachfülle". Andersherum könnte man den Bucket "nullen", wenn zwei ESTABLISHED gefunden wurden. Mal sehen ob ich das hinbekomme.
 

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
Es hat eine ganze Weile gedauert, aber ich habe es geschafft connlimit mit limit-burst "nachzubauen". Dieses Script erlaubt nur einen Up- bzw Download:

Rich (BBCode):
#!/bin/sh
# #####################################
# LimitCloudSync v0.2
# 
# Notes:
# This adds a new rule to iptables that limits OUTGOING traffic to a specific domain
# 
# Changelog:
# 0.2
# - working script
# 0.1
# - first release
# 
# Todo:
# #####################################
destination="<deineCloud>.owncube.com"
dest_domain="owncube.com"
# check running tcp connections
tcp_stats="$(netstat --tcp --wide | grep $dest_domain)"
established=0
while read line; do
    # echo $line
    if [[ "$line" =~ "ESTABLISHED" ]]; then
        established=$((established+1))
    fi
done <<< "$tcp_stats"
echo $established
if [[ $established == 0 ]]; then
    # check if this rule was set before (this means an up- / download has been finished)
    iptables -C OUTPUT -p TCP --match state --state NEW --match limit --limit 1/d --limit-burst 1 --jump ACCEPT -d $destination
    iptables_return=$?
    if [[ $iptables_return -eq 0 ]]; then
        # add general drop rule (to avoid new connections while resetting the rules)
        iptables -A OUTPUT --jump DROP -d $destination
        # delete old burst limit
        iptables -D OUTPUT -p TCP --match state --state NEW --match limit --limit 1/d --limit-burst 1 --jump ACCEPT -d $destination
        # delete old DROP rule
        iptables -D OUTPUT --match state --state NEW --jump DROP -d $destination
        # now it will re-add the burst limit and by that it will reset the bucket to 1 new connection
    fi
    # add new burst limit
    iptables -A OUTPUT -p TCP --match state --state NEW --match limit --limit 1/d --limit-burst 1 --jump ACCEPT -d $destination
    # add new drop rule at the bottom
    iptables -A OUTPUT --match state --state NEW --jump DROP -d $destination
    # delete general drop rule
    iptables -D OUTPUT --jump DROP -d $destination
elif [[ $established != 1 ]]; then
    # check if the global rule exists (this means its still trying to kill existing connections)
    iptables -C OUTPUT --jump DROP -d $destination
    iptables_return=$?
    if [[ $iptables_return != 0 ]]; then
        # add general drop rule (this will slowly kill existing connections)
        iptables -A OUTPUT --jump DROP -d $destination
        # check if a burst rule is set (if not, this is the very first request of the script and we do nothing)
        iptables -C OUTPUT -p TCP --match state --state NEW --match limit --limit 1/d --limit-burst 1 --jump ACCEPT -d $destination
        iptables_return=$?
        if [[ $iptables_return -eq 0 ]]; then
            # delete old burst limit
            iptables -D OUTPUT -p TCP --match state --state NEW --match limit --limit 1/d --limit-burst 1 --jump ACCEPT -d $destination
            # delete the old DROP rule
            iptables -D OUTPUT --match state --state NEW --jump DROP -d $destination
        fi
    fi
fi

Zur Erklärung:
Man hinterlegt das Script im Aufgabenplaner und stellt die Ausführung auf minütlich:
2019-12-12 23_54_40.jpg
2019-12-12 23_54_51.jpg

Beim Neustart des NAS wird Cloud Sync so viele Verbindungen aufbauen wie eingestellt sind. Also in der Regel starten dann 3 Up-/Downloads. Nachdem das Script dann ausgeführt wird, greift der letzte Block ($established != 1). Dieser blockiert alle TCP Pakete in Richtung der Cloud bis keine Verbindung mehr besteht. Beim nächsten Aufruf des Scriptes greift dann der erste Block ($established == 0). Dieser erlaubt pro Tag eine Verbindung. Sobald nun der Up- / Download fertig ist, wird diese Verbindung wieder verschwinden und sobald danach das Script wieder aufgerufen wird, wird wieder eine Verbindung pro Tag erlaubt.

In Screenshots sieht das dann aus wie folgt:

Das NAS wurde neu gestartet (wie man sieht respektiert Cloud Sync nicht mal die eigenen Einstellung von 3 Verbindungen):
2019-12-12 23_36_24.jpg

Es dauert ein paar Minuten, aber dann sind alle Verbindungen gekillt:
2019-12-12 23_39_10.jpg
2019-12-12 23_40_06.jpg

Danach öffnet das Script eine Verbindung zur Cloud, die dann natürlich die maximale Bandbreite nutzen kann:
2019-12-13 00_10_32.jpg

Hinweise:
1.) Meine Cloud ist bei owncube.com gehostet. Ich habe dort eine subdomain.owncube.com. Trotzdem braucht das Script die Domain, denn subdomain.owncube.com ist nur ein Alias von occloudXXX.owncube.com und unser Script sucht in den TCP-Verbindungen gezielt nach dieser Zieladresse. Man muss also destination und dest_domain korrekt einstellen.
2.) Die einzige Möglichkeit, dass nun mehr als eine Verbindung aufgebaut wird ist, dass der Up- / Download einer Datei länger als 24 Stunden benötigt. In diesem Fall würde limit-burst eine weitere Verbindung erlauben. Das Script wiederum würde dann wieder anfangen alle Verbindungen zu killen. Das muss man wissen, sofern man so große Einzeldateien in die Cloud lädt bzw der Upload sehr langsam ist. Die würde dann logischerweise nie hochgeladen werden. Kommt bei mir nicht vor, sollte man aber einfach wissen.
3.) Ich empfehle jedem Cloud Sync über die allgemeine Datenflusssteuerung zu limitieren, gerade wenn das NAS an einem anderen Standort steht und per Fernwartung erreichbar bleiben soll. Wenn der Upload komplett bei DSL Anschlüssen genutzt wird, kann sich das nämlich negativ auf den Ping bzw den Download auswirken. Bei einem billigen Router kann es sogar passieren das gar nichts mehr geht (fehlendes QoS). Ich konnte zB bei einem Standort nicht mal mehr per Teamviewer auf einen lokalen PC zugreifen um von dort aufs NAS zu kommen und vor Ort gab es massive Probleme schon beim Laden von Internetseiten (weil eine Anfrage an eine Website ja auch nichts anderes als ein Upload ist). Wenn das Ziel von Cloud Sync wie bei mir ein WebDAV Server ist, dann müsste man in dem Fall die Ports 80 und 443 limitieren (bei diesem Anschluss habe ich den Upload auf 3 MB/s von 4 MB/s begrenzt):
2019-12-12 23_42_21.jpg
 
Zuletzt bearbeitet:

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
So, heute morgen habe ich noch mal alle NAS geprüft. Während auf einem ein Upload lief, waren bei den anderen mehr Verbindungen gestartet worden, aber alle gesperrt. Das dürfte im laufenden Betrieb eigentlich gar nicht passieren, sondern nur beim Neustart. Irgendwo ist also noch der Wurm drin. Weiß jemand ob iptables-Regeln einen Neustart überleben? Weil es kann sein, dass meine vorherigen Versuche noch "Rückstände" hinterlassen haben. Das würde das dann erklären. Muss ich gerade mal auslesen. Moment.

EDIT: Ne, ich habe mir über den Aufgabenplaner das Ergebnis per E-Mail zusenden lassen und es sieht sauber aus:
Rich (BBCode):
iptables -nL -v --line-numbers

Die Ergebnisse aller drei NAS sind identisch:

Standort A
Code:
Chain DEFAULT_OUTPUT (1 references)
num   pkts bytes target     prot opt in     out     source               destination         
1        1    60 ACCEPT     tcp  --  any    any     anywhere             occloud416.owncube.com  state NEW limit: avg 1/day burst 1
2       86  5160 DROP       all  --  any    any     anywhere             occloud416.owncube.com  state NEW

Lokal:
Code:
Chain DEFAULT_OUTPUT (1 references)
num   pkts bytes target     prot opt in     out     source               destination         
1        1    60 ACCEPT     tcp  --  any    any     anywhere             xxx.owncube.com  state NEW limit: avg 1/day burst 1
2       28  1680 DROP       all  --  any    any     anywhere             xxx.owncube.com  state NEW

Standort V:
Code:
Chain DEFAULT_OUTPUT (1 references)
num   pkts bytes target     prot opt in     out     source               destination         
1        1    60 ACCEPT     tcp  --  any    any     anywhere             occloud416.owncube.com  state NEW limit: avg 1/day burst 1
2       90  5400 DROP       all  --  any    any     anywhere             occloud416.owncube.com  state NEW

Daraus schließe ich, dass irgendwas passiert, sobald ein Up-/Download beendet wurde.

Bei Standort V fällt auf, dass der letzte Upload um 5:10 war:
2019-12-13 10_19_35.jpg

Bei Standort A sieht eigentlich alles gut aus:
2019-12-13 10_20_20.jpg

Lokal auch:
2019-12-13 10_20_51.jpg

Ich denke wenn etwas falsch im Script läuft, dann sobald ein Up-/Download fertig ist. Denn nachdem alle Verbindungen wieder erfolgreich gekillt wurden, läuft wieder alles ganz normal. Überall ist nur eine Verbindung offen.

Auch muss ich mal darüber nachdenken was passiert, wenn die Internetverbindung wegfällt. Bei Standort V kommt das nämlich häufiger vor (Unitymedia ^^).

Ich lasse bei Standort V jetzt mal den Netzwerkmonitor offen. Mal sehen was passiert, wenn der nächste Upload fertig ist.
 

mgutt

Benutzer
Mitglied seit
14. Nov 2012
Beiträge
429
Punkte für Reaktionen
18
Punkte
18
Ich habe jetzt beobachtet wie auf beiden NAS mehrere Uploads auf 100% gegangen sind. Danach startete dann der nächste. Mehrere Verbindungen traten nicht auf. Keine Ahnung was heute morgen war.

Es gibt allerdings einen Fehler, aber mit dem kann ich leben. Und zwar hat er gerade eine Datei hochgeladen. In der Cloud ist sie angekommen. Aber im Verlauf von Cloud Sync wurde kein neuer Eintrag generiert:
2019-12-13 13_20_19.jpg

Komischerweise nicht mal eine Fehlermeldung. Jetzt läuft der nächste Upload. Ich beobachte jetzt mal ob er die selbe Datei noch mal versucht hochzuladen. Aktuell lädt er eine andere hoch.
 
Status
Für weitere Antworten geschlossen.
 

Kaffeautomat

Wenn du das Forum hilfreich findest oder uns unterstützen möchtest, dann gib uns doch einfach einen Kaffee aus.

Als Dankeschön schalten wir deinen Account werbefrei.

:coffee:

Hier gehts zum Kaffeeautomat