Basierend auf Warum ist es so schwierig, ein MMO zu entwickeln? :
Die Entwicklung vernetzter Spiele ist nicht trivial. Es gibt große Hindernisse, die nicht nur bei der Latenz, sondern auch bei der Betrugsprävention, der Statusverwaltung und dem Lastenausgleich überwunden werden müssen. Wenn Sie keine Erfahrung mit dem Schreiben eines vernetzten Spiels haben, wird dies eine schwierige Lernübung sein.
Ich kenne die Theorie über Sockets, Server, Clients, Protokolle, Verbindungen und dergleichen.
Jetzt frage ich mich, wie man lernen kann, ein Netzwerkspiel zu schreiben:
- Wie können Lastprobleme ausgeglichen werden?
- Wie verwalte ich den Spielstatus?
- Wie halte ich die Dinge synchron?
- Wie schützt man die Kommunikation und den Client vor Reverse Engineering?
- Wie kann man Latenzprobleme umgehen?
- Welche Dinge sollen lokal berechnet werden und welche Dinge auf dem Server?
- ...
Gibt es dazu gute Bücher, Tutorials, Sites, interessante Artikel oder andere Fragen?
Ich suche nach umfassenden Antworten, aber bestimmte sind auch in Ordnung, um den Unterschied zu erkennen.
quelle
Antworten:
Zusätzlich zu dem Artikel, der in anderen Antworten verlinkt ist, kann ich etwas über die Erfahrungen mit dem Arianne-Projekt erzählen .
Wie halte ich die Dinge synchron?
Wir haben das Framework „ Marauroa “ um das Konzept der Handlungen und Wahrnehmungen herum aufgebaut: Handlungen werden vom Client an den Server gesendet und tragen Benutzereingaben wie (gehe nach links, greife Monster # 47 an, sag 'Hallo'). Und vom Server werden Wahrnehmungen an die Clients gesendet, die ihnen den Zustand der Welt nahebringen. Diese Wahrnehmungen werden jede Runde gesendet. Je nach Spiel verwenden wir Rundenzeiten von 30ms bis 300ms.
Wir haben zwei Arten von Wahrnehmungen : Eine vollständige Wahrnehmung wird beim Anmelden gesendet und wenn der Spieler einen neuen Bereich (Zone) betritt. Danach werden unterschiedliche Wahrnehmungen gesendet, die nur die geänderten Attribute (z. B. Position) der geänderten Objekte und natürlich neue und entfernte Objekte enthalten.
Wie kann man Latenzprobleme umgehen?
Wir sind fest davon überzeugt, dass der Server immer richtig ist. Der Klient macht einige Vorhersagen wie reibungsloses Gehen, Kollisionsprüfungen und so weiter. Aber wenn ein Client und der Server sich nicht einig sind, gewinnt der Server. Das Teilprojekt Stendhal (ein 2D-RPG) verwendet standardmäßig eine Umdrehungszeit von 300 ms (mit viel Glättung auf Client-Seite). Dies macht Stendhal sehr widerstandsfähig gegen Verzögerungen.
Hinweis: Einige andere Spiele vertrauen dem Client in gewissem Umfang, um die Auswirkungen von Netzwerkverzögerungen zu minimieren. In WoW wurde es oft auf einem Schlachtfeld namens "Warsong Gulch" ausgenutzt. Es gibt zwei Möglichkeiten, die ein Spieler mit der Flagge wählen kann: In der Mitte durch einen Tunnel und auf der rechten Seite den Berg hinauf. Ein betrügerischer Spieler rennt in Richtung Tunnel und verursacht dann für sich selbst eine Verzögerung. Der Server und die anderen Clients sehen ihn weiterhin auf sich zu rennen. Aber nach einiger Zeit kann dieser Client dem Server mitteilen, dass er in Richtung des Hügels gegangen ist. WoW prüft, ob der Abstand zwischen den zuletzt übertragenen und den aktuellen Koordinaten zum Zeitsegment passt und akzeptiert dies.
Verwendung von UDP vs. TCP
In früheren Versionen haben wir UDP verwendet, um den Overhead von TCP zu reduzieren. Verlorene Pakete haben wir selbst gehandhabt. Dies hat zu Beginn des Projekts perfekt funktioniert. Aber als der Server vor einigen Jahren von einer DSL-Heimverbindung in ein richtiges Rechenzentrum verlegt wurde, gab es große Probleme. UDP ist (oder war vor mindestens 5 Jahren) extrem anspruchsvoll in Bezug auf die CPU-Leistung von Firewall-Hardware: Der Regelsatz muss auf jedes einzelne UDP-Paket angewendet werden. Für TCP wird der Regelsatz jedoch nur für die ersten 3 Pakete angewendet. Danach ist die Verbindung hergestellt. Alle folgenden Pakete umgehen den normalen Regelsatz, weil sie sich in der Verbindungstabelle befinden oder weil sie kein SYN-Flag haben.
Wie schützt man die Kommunikation und den Client vor Reverse Engineering?
Arianne ist komplett Open Source, dazu gehören Client, Server, Grafik, Musik. Dazu gehören natürlich auch unsere Protokolldokumentation und sogar ein Analysator, der zum Debuggen verwendet wird.
Es ist einfach, die Kommunikation mithilfe von SSL gegen unbefugtes Abhören durch Dritte zu schützen.
Ein Schutz gegen Reverse Engineering ist jedoch nicht möglich. Sicher können Sie es verschleiern und Anti-Debugging-Techniken verwenden. Letztendlich können Sie jedoch ein Reverse Engineering von Software, die Sie an Benutzer weitergeben, nicht verhindern. Es gibt eine sehr interessante Präsentation darüber, wie Skype rückgängig gemacht wurde, obwohl die Entwickler sich sehr um Anti-Debugging-Techniken bemüht haben: http://recon.cx/en/f/vskype-part1.pdf
Hinweis: In einigen Ländern ist das Reverse Engineering illegal oder es ist zulässig, einen Absatz in die Lizenz aufzunehmen oder das Reverse Engineering zu verbieten. Es gibt jedoch auch andere Länder (wie das Land, in dem ich lebe), die ausdrücklich das Reverse Engineering im Zusammenhang mit der Entwicklung kompatibler Datenspeicherformate oder Übertragungsprotokolle zulassen, Absätze in der Lizenz oder Nutzungsbedingungen, die versuchen, dies zu verbieten, sind ungültig. (Alles in diesem Abschnitt ist, soweit ich weiß, kein Anwalt.)
Welche Dinge sollen lokal berechnet werden und welche Dinge auf dem Server?
Wir berechnen alles, was mit der Spielelogik auf dem Server zusammenhängt. Der Kunde wird bestimmte Ereignisse vorhersagen, damit das Spiel reibungslos läuft. Aber am Ende hat der Server immer Recht.
Vorausgesagte Ereignisse sind beispielsweise das Anhalten der Bewegung, wenn eine Kollision auftritt. Stendhal verwendet ein Raster, um Elemente zu positionieren. Und vom Server aus gesehen befindet sich die linke obere Ecke jeder Entität auf genau einem Quadrat. Der Kunde wird sie jedoch problemlos zwischen den Kacheln hin- und herbewegen. Es wird auch den Pseudo-3D-Effekt zeichnen. Daher kann eine Entität mit einer Basis von 1x1 im Client höher sein.
Wie können Lastprobleme ausgeglichen werden?
Versuchen Sie dies so einfach wie möglich zu halten, um die Wartung zu vereinfachen.
Der Lastenausgleich statischer Inhalte ist im Bereich der HTTP-Servercluster und Inhaltsverteilungsnetzwerke bekannt.
Ein ziemlich einfaches Konzept für den Lastenausgleich von Spieldiensten besteht darin, Server über Regionen / Zonen aufzuteilen. Die Zone AC befindet sich also auf einem Server und die Zonen DF auf einem anderen. Dies ist besonders einfach, wenn Sie nicht von Zonen in einem Satz zu Zonen in einem anderen Satz schauen können. Sie müssen dort einige Überprüfungen vornehmen, damit ein Client nur eine Verbindung zu einem Zonenserver herstellen kann, der für die Zone zuständig ist, in der sich der Player befindet.
Die einfachste Möglichkeit, Spieler von einem Server auf den anderen zu übertragen, besteht darin, sie in die Datenbank zu schreiben, den Client anzuweisen, eine Verbindung zum anderen Zonenserver herzustellen und sie vom aktuellen Server zu trennen. Der Client stellt dann eine Verbindung zum neuen Zonenserver her, der ihn aus der Datenbank lädt. (Da Sie ohnehin das Laden von / Speichern in den Datenbankcode benötigen, kann die direkte Kommunikation zwischen den Servern für die Übergabe später implementiert werden.)
Einige zusätzliche globale Dienste werden benötigt durch: Beim Anmelden müssen die Clients angewiesen werden, sich mit dem richtigen Zonenserver zu verbinden. Und vielleicht möchten Sie ein weltweites Chat-System.
Ich habe dieses Thema ausführlich unter Wie wird in MMOs ein Lastenausgleich erreicht?
quelle
http://gafferongames.com/networking-for-game-programmers/
Ist eine großartige Sammlung von Artikeln zu verschiedenen Problemen und Lösungen, die sich mit dem Networking von Spielen befassen.
quelle
Abhängig von der Art des Spiels, das Sie schreiben, können Sie möglicherweise einen Teil der Netzwerkprogrammierung auf niedriger Ebene vermeiden. Einige Arten von Spielen erfordern nicht viel Hin- und Her-Kommunikation zwischen den Clients und dem Server. In solchen Fällen könnte man sich für ein übergeordnetes Framework entscheiden. Zum Beispiel entwickle ich ein rundenbasiertes Strategiespiel in C # /. NET. Rundenbasierte Strategiespiele sind insofern einzigartig, als der Großteil der Client / Server-Kommunikation zu Beginn und am Ende einer Runde stattfindet, wobei relativ wenig dazwischen liegt. Daher entschied ich mich für die Windows Communication Foundation (WCF), ein allgemeines Kommunikationsframework, das hauptsächlich für Webdienste entwickelt wurde. Anstatt direkt mit Sockets und all dem Low-Level-Netzwerk-Gunk zu arbeiten, kann ich so etwas wie Standardmethodenaufrufe machen. und überlasse WCF mir die Protokoll- und Transportschicht. Das einzige Mal, dass ich mich mit dem Netzwerk auf niedriger Ebene befassen musste, war, als ich meine Endpunkte konfiguriert habe. Dies ist so ziemlich ein einmaliger Vorgang in einer Konfigurationsdatei. Möglicherweise muss noch eine benutzerdefinierte Serialisierungslogik implementiert werden, aber Sie müssen dies trotzdem tun.
quelle
Die Frage ist viel zu weit gefasst. Die Antworten könnten eine Website alleine füllen. Aber es gibt Bücher, die dies berühren, hauptsächlich diese beiden:
Beachten Sie, dass auch diese Bücher keine vollständige Anleitung sind, sondern eine Sammlung von Ideen und Ansätzen, die Sie verwenden können, von denen einige nicht zusammenarbeiten oder die sogar widersprüchlich sind. In der Regel setzt es einige Erfahrung in der Entwicklung von Spielen, Netzwerkanwendungen oder im Idealfall beidem voraus.
(Beachten Sie, dass ich in der ursprünglichen Frage mehr über die MMOs spreche - ein 'Netzwerkspiel' kann alle möglichen Dinge von einem PHP-basierten Textspiel bis hin zu einem MMO bedeuten, und die obigen Unterfragen sind es nicht alle gelten für jeden Typ.)
quelle
feste geografische Größe + mehrere Instanzen ist die einfachste Lösung. Die Leute, die an SWG arbeiteten, versuchten es mit dynamischer Größe und bedauerten es.
Der Server ist maßgebend.
Regelmäßige Synchronisierungsaktualisierungen vom Server. (nicht ganz sicher, was die Sorge hier ist)
Unmöglich. Stellen Sie einfach sicher, dass Sie nichts vertrauen, was Sie vom Client erhalten, und dass der Server autorisierend ist.
Dies geht kilometerweit, aber oberflächlich gesehen führen Sie auf dem Client dieselbe Simulation aus wie auf dem Server. Wenn die Synchronisierung stattfindet, können Sie die Probleme beheben. Alle Entscheidungen, die auf dem Client getroffen werden, werden auch auf dem Server simuliert. Es kann also zu Fehlentscheidungen kommen, aber die Dinge klappen im Allgemeinen.
Stellen Sie sich den Client als eine nicht autorisierende Simulation dessen vor, was auf dem Server vor sich geht. Reaktionsfreudigkeit ist der Schlüssel für das Spielerlebnis. Sie müssen also jedes Mal etwas unternehmen , wenn ein Spieler eine Entscheidung trifft, auch wenn es sich nur um den Beginn eines Taktes handelt.
Um ehrlich zu sein, viele dieser Probleme sind orthogonal und können später gelöst werden. Mach einfach das Spiel und sorge dich nicht zu sehr um diese Dinge.
quelle
Diese Frage ist sehr weit gefasst. Es ist auch ein sehr kniffliger Bereich, den man meistern muss. Netzwerk-Programmierer sind in der Branche sehr gefragt, mit einer entsprechenden Bezahlung. Gibt es da draußen Bücher? Gibt es da draußen ohne Zweifel gute Bücher? Gibt es da draußen Bücher, die deine Fragen beantworten? Ich glaube nicht. Sie haben vielleicht Lösungen, die in bestimmten Situationen funktionieren, oder Hinweise darauf, wonach Sie suchen müssen, aber fast alle Ihre Fragen sind spielabhängig. In diesem Bereich müssen Sie wirklich viel allein arbeiten trivial und es kann auf so viele (unkontrollierte) Arten schief gehen.
quelle