Frage zu Netzwerkprotokoll
-
Hey!
Ich hab mir mal Gedanken gemacht, wie die Netzwerkdaten von zB. einem Online-Spiel aussehen. Dabei muss ja 100%ig sichergestellt sein, dass die Daten am Server bzw. Client angekommen sind.
1. Frage: Ist das TCP 100% sicher? Damit meine ich nicht 99,9% sondern wirklich absolut sicher? Also kann ich damit ein Paket senden, ohne mir Gedanken machen zu müssen, ob es überhaupt wo angekommen ist?
Denn folgendes Szenario hab ich mir vorgestellt (MMORPG like):
Client sendet: "Möchte Gegner attackieren"
Server sendet: "Habe 'Möchte Gegner attackieren' erhalten"Nun, was aber wenn die letzte Antwort verworfen wird? Wie kann sich der Server sicher sein, dass der Client auch die Bestätigung erhalten hat? (Denn erst, wenn das passiert, soll der Client zum attackieren beginnen)
Es kann ja nicht ewig hin und her Bestätigt werden.Eine Möglichkeit wäre:
Client sendet: "Möchte Gegner attackieren"
Server sendet: "Habe .. erhalten" und beginnt mit der serverseitigen AttackeWeiters sendet der Server nun solange "Attackiere Gegner", bis eine Antwort vom Clienten kommt: "Okay, attackiere nun auch Gegner". Dann ist sichergestellt, dass Server und Client attackieren, wie es sein soll.
So wäre das mit UDP.
Aber das muss doch einfacher gehen?Wie macht man sowas am einfachsten und sichersten?
MfG
-
TCP garantiert dir einen zuverlässigen Datentransport, d.h. es ist zu 100% sicher - in der Theorie. Wenn es halt hardwareseitig Probleme gibt oder z.B. irgendeine Leitung defekt ist, dann werden natürlich auch keine Pakete ankommen. Aber wenn es dir um sicheren Pakettransport geht, dann nimm TCP. Verwenden ja auch viele andere Hersteller bei Netzwerkapplikationen.
-
ceplusplus schrieb:
Wie macht man sowas am einfachsten und sichersten?
Hm, imho ist das keine gute Idee. Wenn der Angriff vom Client abhängig wird verleitet das böse Buben schnell dazu, diesen zu hacken. Du solltest den Angriff sowieso lieber vom Server berechnen lassen, dann hat dein Problem auch keine Relevanz mehr. Beim nächsten Tick ist der ganze Spass dann wieder synchronisiert.
-
Aha ok.
Ja mein ich doch, dass die Berechnungen vom Server gemacht werden. Mit der zweiten Möglichkeit meinte ich wohl dasselbe wie du, @krabbels.
Also der Client sendet: "Möchte attackieren"
Der Server erhält dies, und beginnt mit dem serverseitigen attackieren. Dabei werden die Spielerdaten (Angriffspunkte, Lebenspunkte, ...) aus der Datenbank geholt um den Kampf durchführen zu können.
Weiters sendet der Server gleichzeitig solange an den Clienten "Attackiere", bis dieser antwortet, damit auch am Clienten attackiert wird. Dies könnte doch mit UDP geschehen? (Schneller, besser??) Oder reicht nur TCP?So in etwa hab ich das gemeint.
Und... wegen der Lebenspunkte zum Beispiel. Wäre es besser, wenn der Server ständig die verbleibenden Lebenspunkte an den Clienten sendet, oder nur den Wert, der abgezogen wird? Ist doch eigentlich egal, oder?
MfG
-
ceplusplus schrieb:
Weiters sendet der Server gleichzeitig solange an den Clienten "Attackiere", bis dieser antwortet, damit auch am Clienten attackiert wird.
Wenn der Client an den Server "Möchte attackieren" sendet, kann er doch das Ereignis senden und sofort mit dem Attackieren beginnen. Warum willst du da noch mal eine Rückbestätigung vom Server senden lassen? Immerhin wird das vermutlich zu einem enormen Mehraufwand beim Server führen, was, gerade bei einem MMORPG nicht wirklich wünschenswert ist.
- Client sendet an Server, "Möchte attackieren" - Client spielt "Möchte attackieren"-Musik/Animation was auch immer ab - Server erhält Nachricht und berechnet den Kampf - Nebenbei schickt der Server immer mal wieder die Daten, die beim Client zum synchronisieren des Spiels mit dem Server notwendig sind, z.B. die verbleibenden Lebenspunkte(optimal wäre es natürlich, wenn diese nur bei einer tatsächlich stattgefundenen Veränderung geschickt werden(Spieler nimmt Heiltrank))
-
Mhm, aber was, wenn eine enorme Verbindungsverzögerung existiert, und der Client schon auf den Gegner einhaut, während der Server erst 20 Sekunden später damit beginnt? Oder MUSS man da mit timestamps arbeiten?
Und ist es nun egal, ob der Server die verbleibenden Lebenspunkte oder nur den Wert der von den Lebenspunkten abgezogen wird sendet? Letzteres würde ja wieder traffic einsparen, kommt mir aber irgendwie unsicherer vor...
MfG
-
ceplusplus schrieb:
Und ist es nun egal, ob der Server die verbleibenden Lebenspunkte oder nur den Wert der von den Lebenspunkten abgezogen wird sendet? Letzteres würde ja wieder traffic einsparen, kommt mir aber irgendwie unsicherer vor...
Warum sollte es Traffic einsparen, wenn man "12 Lebenspunkte weniger" anstatt "noch 51 Lebenspunkte übrig" sendet?
-
ceplusplus schrieb:
Mhm, aber was, wenn eine enorme Verbindungsverzögerung existiert, und der Client schon auf den Gegner einhaut, während der Server erst 20 Sekunden später damit beginnt?
Lags wirst du auch so nicht vermeiden können, im Gegenteil. Deine Variante halte ich sogar für noch gefährlicher, da auf dem Server bereits gekämpft wird während der Spieler gar nichts davon mitbekommt.
ceplusplus schrieb:
Oder MUSS man da mit timestamps arbeiten?
Nein, ist doch sinnlos. Wie gesagt, Lags kannst du nicht vermeiden.
mad_martin schrieb:
ceplusplus schrieb:
Und ist es nun egal, ob der Server die verbleibenden Lebenspunkte oder nur den Wert der von den Lebenspunkten abgezogen wird sendet? Letzteres würde ja wieder traffic einsparen, kommt mir aber irgendwie unsicherer vor...
Warum sollte es Traffic einsparen, wenn man "12 Lebenspunkte weniger" anstatt "noch 51 Lebenspunkte übrig" sendet?
Es macht keinen Unterschied. Ich würde mich für erstere Variante entscheiden, da sie weniger abstrakt und mit dem Wert auf dem Server tatsächlich synchron ist.
-
ceplusplus schrieb:
Mhm, aber was, wenn eine enorme Verbindungsverzögerung existiert, und der Client schon auf den Gegner einhaut, während der Server erst 20 Sekunden später damit beginnt?
IMHO wird die Kampflogik etc. vom Server verwaltet. Soll heissen falls so eine extrem hohe Verbindungsverzögerung existiert wird sich das nur auf der Clientseite bemerkbar machen, auf dem Server sollte alles normal ablaufen. D.h. wiederum, nicht du haust auf einen nichtreagierenden Computergegner, sondern der Computergegner haut auf deinen nicht reagierenden Avatar ein. Falls zwei menschliche Spieler gegeneinander spielen, wird wohl der gewinnen der die wenigsten Lags hat.

tt
-
Hmm, bezüglich deinem Schema, @krabbels:
Wäre es nicht besser am Clienten erst mit dem Attackieren zu beginnen, wenn die erste Antwort vom Server kommt?
Also in etwa so:
- Client sendet an Server, "Möchte attackieren" - Server erhält Nachricht und berechnet den Kampf, beginnt gleichzeitig mit dem ständigen senden von zB. "A31", "A95", .. was für ATTACK + abgezogenes Leben steht.Dabei weiß dann der Client ganz sicher, dass die Attacke stattfindet.
Mir fällt keine einfachere, gleichsichere Möglichkeit ein.Und es macht doch einen Unterschied, ob man 11592 oder 62 sendet?!
MfG
-
Am "einfachsten und sichersten" machst du das mit TCP - solange die Verbindung steht brauchst du dir da keine Sorgen machen dass irgendwas nicht angekommen ist.
Am "besten" macht man sowas aber mit UDP, da die Fehlerkorrektur-Mechanismen in TCP leider dafür sorgen dass deutliche Lags auftreten, wenn mal ein Paket nicht oder verändert angekommen ist.
-
Wobei ja Fehlerkorrektur nicht unbedingt nötig wäre. Man könnte ja Bestätigungen einbauen, und falls was nicht ankommt, einfach nochmal senden oder so.
-
ceplusplus schrieb:
Wäre es nicht besser am Clienten erst mit dem Attackieren zu beginnen, wenn die erste Antwort vom Server kommt?
Warum? Was erhoffst du dir davon?
krabbels schrieb:
Lags wirst du auch so nicht vermeiden können, im Gegenteil. Deine Variante halte ich sogar für noch gefährlicher, da auf dem Server bereits gekämpft wird während der Spieler gar nichts davon mitbekommt.
Bei Verbindungsstörungen würde der Client mit meiner Variante bereits kämpfen. Bei deiner Variante würde u.U. lediglich auf dem Server gekämpft werden. Der Spieler selber würde also gar nicht merken, dass schon lange gekämpf wird. Außerdem ist mit deiner Variante, durch die Rückbestätigungen, ein höheres Maß an Leistung bei Server und Bandbreite notwenig.
-
ceplusplus schrieb:
Und es macht doch einen Unterschied, ob man 11592 oder 62 sendet?!
MfG
Ich wage einfach mal die Behauptung, dass das nicht interessiert. Ob man jetzt ein Byte oder 2 oder 3 schickt, der Overhead durch UDP und IP ist auf jeden Fall da.
-
@krabbels:
Stimmt sorry, da hatte ich nen Denkfehler.@mad_martin:
Und bei 100.000 Spielern, die gleichzeitig auf einem Server online sind? (Lässt WinSock überhaupt so viele connects zu?)
-
ceplusplus schrieb:
Und es macht doch einen Unterschied, ob man 11592 oder 62 sendet?!
Es macht sicher einen Unterschied, wieviel Daten du am Ende sendest. Nur ist es unrealistisch, dass man zum Speichern der Lebenspunkte mehr als 1 oder 2 Byte braucht und dass Veränderungen in einem wesentlich kleineren Rahmen liegen.
-
Deinen letzten Satz verstehe ich nicht.
Naja jedenfalls wären es wohl immer 2 Byte, egal ob man nun das abzuziehende Leben oder den Lebenstand sendet. Das meintest du wohl?
-
@mad_martin:
Und bei 100.000 Spielern, die gleichzeitig auf einem Server online sind? (Lässt WinSock überhaupt so viele connects zu?)Man müsste wahrscheinlich auf ein anderes System umsteigen, wenn man mehr als 65000 Clienten bedienen müsste!
Ich hab auch schon nachgeschaut und überlegt wie man das Problem lösen könnte! Letztendlich bin ich zu der Erkenntnis gekommen, dass es garnicht zu lösen ist!
Wer Lösungen hat, bitte sofort nennen!
-Mehrere Server laufen lassen!
-
ceplusplus schrieb:
Naja jedenfalls wären es wohl immer 2 Byte, egal ob man nun das abzuziehende Leben oder den Lebenstand sendet. Das meintest du wohl?
Du kannst auch anfangen bei einer maximal möglichen Energie von 200 Punkten(mind. 1 Byte) bei einem Ereignis, was dem Spieler 25 Punkte abzieht nur 5 Bit zu schicken. Mir wäre das zu frickelig. Und ob du da nun wirklich ein Leistungszuwachs rausholst, ist fragwürdig.
-
Jo, schon klar.
Aber ich hätte halt gerne optimalste Optimalität

Also so trafficsparend und sicher wie nur möglich.