static void Main(string[] args) { Log.Init("cluster", Log.LogLevel.All); Log.Info("Cluster", "Starting GameCluster"); Log.Info("Cluster", "Loading database.conf file"); string[] lines = File.ReadAllLines("database.conf"); Database.Database.Username = lines[0]; Database.Database.Password = lines[1]; Database.Database.Host = lines[2]; Database.Database.DB = lines[3]; if (Database.Database.Init() == false) { Log.Error("Cluster", "Cannot connect to database"); while (true) { Thread.Sleep(1); } } Log.Debug("Cluster", "Connected to database"); if (socket.Listen(1) == false) { Log.Error("Cluster", "Cannot listen on port 26000"); while (true) { Thread.Sleep(1); } } // set max_allowed_packet value to 1GB Database.Database.Query("SET global max_allowed_packet=1073741824"); Log.Debug("Cluster", "Listening on port 26000"); // Begin accept socket.Socket.BeginAccept(acceptAsync, socket); // Start the login queue LoginQueue.Start(); while (true) { // Timers or whatever here? Or maybe async calls with timers? Pretty much that will help Thread.Sleep(1); } }
private static PyObject HandleTuple(PyTuple tup, Connection connection) { int items = tup.Items.Count; if (items == 6) { // Only LowLeverVersionExchange if (connection.CheckLowLevelVersionExchange(tup) == false) { connection.EndConnection(); } if (connection.Type == ConnectionType.Node) { // Update the list in ConnectionManager ConnectionManager.UpdateConnection(connection); // Send the node info connection.SendNodeChangeNotification(); // Flag the connection as fully handled to start the correct listener connection.StageEnded = true; } else if (connection.Type == ConnectionType.Client) { // Update the list in ConnectionManager(we should do this later) // ConnectionManager.UpdateConnection(connection); } return(null); } else if (items == 3) { if (tup.Items[0].Type == PyObjectType.None) { // VipKey VipKeyCommand vk = new VipKeyCommand(); if (vk.Decode(tup) == false) { Log.Error("Client", "Wrong vipKey command"); connection.EndConnection(); return(null); } return(null); } else { // Handshake sent when we are mostly in HandshakeAck ack = new HandshakeAck(); ack.live_updates = new PyList(); ack.jit = connection.LanguageID; ack.userid = (int)connection.AccountID; ack.maxSessionTime = new PyNone(); ack.userType = Common.Constants.AccountType.User; ack.role = (int)connection.Role; ack.address = connection.Address; ack.inDetention = new PyNone(); ack.client_hashes = new PyList(); ack.user_clientid = (int)connection.AccountID; // We have to send this just before the sessionchange connection.Send(ack.Encode()); // Send session change connection.SendSessionChange(); // Change the stage to ended to start the real listener connection.StageEnded = true; } } else if (items == 2) // PlaceboRequest, QueueCheck and Login packet { if (tup.Items[0].Type == PyObjectType.None) { QueueCheckCommand qc = new QueueCheckCommand(); if (qc.Decode(tup) == false) { Log.Error("Client", "Wrong QueueCheck command"); connection.EndConnection(); return(null); } // Queued logins connection.Send(new PyInt(LoginQueue.queue.Count + 1)); connection.SendLowLevelVersionExchange(); return(null); } else if (tup.Items[0].Type == PyObjectType.String) { if (tup.Items[0].As <PyString>().Value == "placebo") { // We assume it is a placebo request PlaceboRequest req = new PlaceboRequest(); if (req.Decode(tup) == false) { Log.Error("Client", "Wrong placebo request"); connection.EndConnection(); return(null); } return(new PyString("OK CC")); } else { // Check if the password is hashed or not and ask for plain password AuthenticationReq req = new AuthenticationReq(); // Send AutClusterStarting message if we do not have any node attached yet if (ConnectionManager.NodesCount <= 0) { GPSTransportClosed ex = new GPSTransportClosed("AutClusterStarting"); connection.Send(ex.Encode()); connection.EndConnection(); return(null); } if (req.Decode(tup) == false) { Log.Error("Client", "Wrong login packet"); GPSTransportClosed ex = new GPSTransportClosed("LoginAuthFailed"); connection.Send(ex.Encode()); connection.EndConnection(); return(null); } Log.Debug("Client", "Login try: " + req.user_name); // The hash is in sha1, we should handle it later if (req.user_password == null) { Log.Trace("Client", "Rejected by server; requesting plain password"); return(new PyInt(1)); // Ask for unhashed password( 1 -> Plain, 2 -> Hashed ) } // Login request, add it to the queue and wait until we are accepted or rejected LoginQueue.Enqueue(connection, req); // The login queue will call send the data to the client return(null); } } } else { Log.Error("Connection", "Unhandled Tuple packet with " + items + " items"); connection.EndConnection(); return(null); } return(null); }