Пример #1
0
        public PyPacket CreateEmptySessionChange()
        {
            // Fill all the packet data, except the dest/source
            SessionChangeNotification scn = new SessionChangeNotification();
            scn.changes = session.EncodeChanges();

            if (scn.changes.Dictionary.Count == 0)
            {
                // Nothing to do
                return null;
            }

            // Add all the nodeIDs
            foreach (int node in NodeManager.nodes.Keys)
            {
                if (node == 0)
                    continue;

                scn.nodesOfInterest.Items.Add(new PyInt(node));
            }

            PyPacket p = new PyPacket();

            p.type_string = "macho.SessionChangeNotification";
            p.type = Macho.MachoNetMsg_Type.SESSIONCHANGENOTIFICATION;

            p.userID = (uint)ClientManager.GetClientID(this);

            p.payload = scn.Encode().As<PyTuple>();

            p.named_payload = new PyDict();
            p.named_payload.Set("channel", new PyString("sessionchange"));

            return p;
        }
Пример #2
0
        public void UpdateSession(PyPacket from)
        {
            Log.Debug("Client", "Updating session for client");

            // We should add a Decode method to SessionChangeNotification...
            PyTuple payload = from.payload;

            PyDict changes = payload[0].As<PyTuple>()[1].As<PyTuple>()[0].As<PyDict>();

            // Update our local session
            foreach(PyString key in changes.Dictionary.Keys)
            {
                session.Set(key.Value, changes[key.Value].As<PyTuple>()[1]);
            }
        }
Пример #3
0
        public void Run()
        {
            while (true)
            {
                Thread.Sleep(1);

                try
                {
                    byte[] data = new byte[socket.Available];
                    int bytes = socket.Recv(data);

                    if (bytes == -1)
                    {
                        throw new DisconnectException();
                    }
                    else if (bytes > 0)
                    {
                        packetizer.QueuePackets(data, bytes);
                        int p = packetizer.ProcessPackets();

                        for (int i = 0; i < p; i++)
                        {
                            byte[] packet = packetizer.PopItem();
                            PyObject obj = Unmarshal.Process<PyObject>(packet);

                            if (obj.Type == PyObjectType.ObjectData)
                            {
                                Log.Warning("Node", PrettyPrinter.Print(obj));
                                PyObjectData item = obj as PyObjectData;

                                if (item.Name == "macho.CallRsp")
                                {
                                    PyPacket final = new PyPacket();

                                    if (final.Decode(item) == true)
                                    {
                                        if (final.dest.type == PyAddress.AddrType.Client)
                                        {
                                            try
                                            {
                                                ClientManager.NotifyClient((int)final.userID, obj);
                                            }
                                            catch (Exception)
                                            {
                                                Log.Error("Node", "Trying to send a packet to a non-existing client");
                                            }
                                        }
                                        else if (final.dest.type == PyAddress.AddrType.Node)
                                        {
                                            NodeManager.NotifyNode((int)final.dest.typeID, obj);
                                        }
                                        else if (final.dest.type == PyAddress.AddrType.Broadcast)
                                        {
                                            // This should not be coded like this here, but will do the trick for now
                                            // TODO: Add a ClientManager
                                            ClientManager.NotifyClients(obj);
                                        }
                                    }
                                }
                            }
                            else
                            {
                                Log.Error("Node", "Unknown type");
                            }

                        }
                    }
                }
                catch (SocketException ex)
                {
                    if (ex.ErrorCode != 10035)
                        break;
                }
                catch (DisconnectException)
                {
                    Log.Error("Node", "Node " + NodeManager.GetNodeID(this) + " disconnected");
                    break;
                }
                catch (Exception)
                {

                }
            }
        }
Пример #4
0
 private void Send(PyPacket packet)
 {
     Send(packet.Encode());
 }
 private void SendServer(PyPacket data)
 {
     SendServer(data.Encode());
 }
 private void SendClient(PyPacket data)
 {
     SendClient(data.Encode());
 }
        private PyObject OldHandle(PyObject packet)
        {
            // Check for login packets and just forward them
            if (packet is PyTuple)
            {
                // Those are the first packets, sent by both client and server
                return packet;
            }
            else if (packet is PyInt)
            {
                // This is only sent by the server
                return packet;
            }
            else if (packet is PyString)
            {
                // This is only sent by the server
                return packet;
            }
            else if (packet is PyDict)
            {
                // Packet sent by the client(HandshakeAck)
                // We need to modify it in order to put our own client address, as it isnt the same as the address that the server sends
                PyDict handshake = packet as PyDict;

                PyDict session = handshake.Get("session_init") as PyDict;

                session.Set("address", new PyString(socket.GetAddress()));

                handshake.Set("session_init", session);

                return handshake;
            }
            else if (packet is PyObjectEx) // Exceptions... just check the type and decide what to do
            {
                PyException exception = new PyException();

                if (exception.Decode(packet) == true) // Ignore the error
                {
                    Log.Debug("Exceptions", "Got exception of type " + exception.exception_type);
                }

                return packet;
            }
            else // Normal packets
            {
                PyPacket p = new PyPacket();
                if (p.Decode(packet) == false)
                {
                    // Big problem here, we dont know who to send this
                    Log.Error("Client", "Cannot decode PyPacket");
                }
                else
                {
                    return HandlePyPacket(p);
                }

                return packet;
            }
        }
        private PyObject HandlePyPacket(PyPacket data)
        {
            // Just forward it if we dont want to look for a specific one
            if (data.dest.type == PyAddress.AddrType.Client)
            {
                // Look for SessionChangeNotifications
                if (data.type == Macho.MachoNetMsg_Type.SESSIONCHANGENOTIFICATION)
                {
                    // Search for address change in session
                    PyTuple payload = data.payload;
                    PyDict session = payload.Items[0].As<PyTuple>().Items[1].As<PyDict>();

                    if (session.Contains("address") == true)
                    {
                        PyTuple address = session.Get("address").As<PyTuple>();

                        address[0] = new PyString(socket.GetAddress());
                        address[1] = new PyString(socket.GetAddress());
                        session.Set("address", address);
                    }

                    payload.Items[0].As<PyTuple>().Items[1] = session;

                    data.payload = payload;
                }

                // SendClient(data);
            }
            else if (data.dest.type == PyAddress.AddrType.Node)
            {
                // SendServer(data);
            }
            else if (data.dest.type == PyAddress.AddrType.Broadcast)
            {
                // What to do now ?
                Log.Error("Client", "Broadcast packets not supported yet");
                // throw new NotImplementedException("Broadcast packets are not supported yet");
            }

            return data.Encode();
        }
Пример #9
0
        public void ReceiveClientAsync(IAsyncResult ar)
        {
            try
            {
                AsyncState state = (AsyncState)(ar.AsyncState);

                int bytes = Socket.Socket.EndReceive(ar);

                packetizer.QueuePackets(state.buffer, bytes);
                int p = packetizer.ProcessPackets();

                for (int i = 0; i < p; i++)
                {
                    byte[] actual = packetizer.PopItem();
                    PyObject obj = Unmarshal.Process<PyObject>(actual);

                    if (obj == null)
                    {
                        continue;
                    }

                    if (obj is PyObjectEx)
                    {
                        // PyException
                        Log.Error("Client", "Got exception from client");
                    }
                    else
                    {

                        PyPacket packet = new PyPacket();

                        if (packet.Decode(obj) == false)
                        {
                            Log.Error("Client", "Error decoding PyPacket");
                        }
                        else
                        {
                            if (packet.dest.type == PyAddress.AddrType.Node)
                            {
                                if (packet.source.type != PyAddress.AddrType.Client)
                                {
                                    Log.Error("Client", string.Format("Wrong source data, expected client but got {0}", packet.source.type));
                                }

                                // Notify the node, be careful here, the client will be able to send packets to game clients
                                if (packet.dest.typeID == 0xFFAA)
                                {
                                    Log.Warning("Client", "Sending packet to proxy");
                                    ConnectionManager.NotifyNode((int)(packet.dest.typeID), obj);
                                }
                                else
                                {
                                    ConnectionManager.NotifyNode((int)(packet.dest.typeID), obj);
                                }

                            }
                        }
                    }
                }

                Socket.Socket.BeginReceive(state.buffer, 0, 8192, SocketFlags.None, recvAsync, state);
            }
            catch (ObjectDisposedException)
            {
                Log.Debug("Client", "Disconnected");
                ConnectionManager.RemoveConnection(this);
            }
            catch (SocketException)
            {
                Log.Debug("Client", "Disconnected");
                ConnectionManager.RemoveConnection(this);
            }
            catch (Exception ex)
            {
                Log.Error("Client", "Caught unhandled exception: " + ex.ToString());
            }
        }
Пример #10
0
        private void Run()
        {
            try
            {
                while (true)
                {
                    Thread.Sleep(1);

                    byte[] data = new byte[socket.Available];
                    int bytes = 0;

                    try
                    {
                        bytes = socket.Recv(data);
                    }
                    catch (SocketException ex)
                    {
                        if (ex.ErrorCode != 10035)
                            throw new DisconnectException();
                    }
                    catch (Exception)
                    {
                        throw new DisconnectException();
                    }

                    if (bytes == -1) // Client disconnected
                    {
                        throw new DisconnectException();
                    }
                    else if (bytes > 0)
                    {
                        packetizer.QueuePackets(data, bytes);
                        int p = packetizer.ProcessPackets();

                        byte[] actual = null;

                        for (int i = 0; i < p; i++)
                        {
                            actual = packetizer.PopItem();
                            PyObject obj = Unmarshal.Process<PyObject>(actual);

                            if (obj is PyObjectEx)
                            {
                                // PyException
                                Log.Error("Client", "Got exception from client");
                            }
                            else
                            {

                                PyPacket packet = new PyPacket();
                                if (packet.Decode(obj) == false)
                                {
                                    Log.Error("Client", "Error decoding PyPacket");
                                }
                                else
                                {
                                    // Get the node ID to send
                                    if (packet.dest.type == PyAddress.AddrType.Node)
                                    {
                                        if (packet.dest.typeID == 1)
                                        {
                                            packet.dest.typeID = (ulong)nodeID; // We dont want to receive packets in the proxy
                                        }

                                        if (packet.source.type != PyAddress.AddrType.Client)
                                        {
                                            Log.Error("Client", string.Format("Wrong source data, expected client but got {0}", packet.source.type));
                                        }

                                        Log.Warning("Client", PrettyPrinter.Print(packet.Encode()));

                                        if (NodeManager.NotifyNode((int)packet.dest.typeID, obj) == false)
                                        {
                                            // We cant send the data to the node, what to do?
                                            Log.Error("Client", "Trying to send a packet to a non-existing node");
                                            throw new DisconnectException();
                                        }
                                    }
                                }
                            }

                        }
                    }
                }
            }
            catch (ThreadAbortException)
            {

            }
            catch (DisconnectException)
            {

            }
            catch (Exception ex)
            {
                Log.Error("Client", "Unhandled exception... " + ex.Message);
                Log.Error("ExceptionHandler", "Stack trace: " + ex.StackTrace);
            }

            // We should notify our node about this
            Log.Error("Client", "Client disconnected");
            socket.Close();
            ClientManager.RemoveClient(this);
        }
Пример #11
0
        public PyObject SetSessionChangeDestination(PyPacket p, int node)
        {
            // The session change info should never come from the client
            p.source.type = PyAddress.AddrType.Node;
            p.source.typeID = (ulong)1;
            p.source.callID = 0;

            p.dest.type = PyAddress.AddrType.Node;
            p.dest.typeID = (ulong)node;
            p.dest.callID = 0;

            return p.Encode();
        }
Пример #12
0
        public PyObject SetSessionChangeDestination(PyPacket p)
        {
            p.source.type = PyAddress.AddrType.Node;
            p.source.typeID = (ulong)nodeID;
            p.source.callID = 0;

            p.dest.type = PyAddress.AddrType.Client;
            p.dest.typeID = (ulong)ClientManager.GetClientID(this);
            p.dest.callID = 0;

            return p.Encode();
        }
Пример #13
0
        public static void HandlePacket(object input)
        {
            PyPacket packet = (PyPacket)input;
            PyPacket res = new PyPacket();

            if (packet.type == Macho.MachoNetMsg_Type.CALL_REQ)
            {
                PyTuple callInfo = packet.payload.As<PyTuple>().Items[0].As<PyTuple>()[1].As<PySubStream>().Data.As<PyTuple>();

                string call = callInfo.Items[1].As<PyString>().Value;
                PyTuple args = callInfo.Items[2].As<PyTuple>();
                PyDict sub = callInfo.Items[3].As<PyDict>();

                if (Program.SvcMgr.FindService(packet.dest.service) == false)
                {
                    Log.Error("Client", "Cannot find service " + packet.dest.service + " to call " + call);
                    return;
                }

                if (Program.SvcMgr.GetService(packet.dest.service).FindServiceCall(call) == false)
                {
                    Log.Error("Client", "Service " + packet.dest.service + " doesnt contains a call to " + call);
                    return;
                }

                PyObject callRes = Program.SvcMgr.Call(packet.dest.service, call, args, null);

                if (callRes == null)
                {
                    return;
                }

                if (callRes.Type == PyObjectType.Tuple)
                {
                    res.type_string = "macho.CallRsp";
                    res.type = Macho.MachoNetMsg_Type.CALL_RSP;

                    res.source = packet.dest;

                    res.dest.type = PyAddress.AddrType.Client;
                    res.dest.typeID = (ulong)clients[packet.userID].GetAccountID();
                    res.dest.callID = packet.source.callID;

                    res.userID = (uint)clients[packet.userID].GetAccountID();

                    res.payload = new PyTuple();
                    res.payload.Items.Add(new PySubStream(callRes));

                    Send(res.Encode());
                }
            }
            else if (packet.type == Macho.MachoNetMsg_Type.SESSIONCHANGENOTIFICATION)
            {
                Log.Debug("Main", "Updating session for client " + packet.userID);

                // Check if the client isnt assigned to this node yet
                if(clients.ContainsKey(packet.userID) == false)
                {
                    Client cli = new Client();
                    clients.Add(packet.userID, cli);
                }

                // Update client session
                clients[packet.userID].UpdateSession(packet);
            }
        }
Пример #14
0
        static void Main(string[] args)
        {
            Log.Init("evesharp");
            Log.Info("Main", "Starting node...");
            Log.Trace("Database", "Connecting to database...");

            if (Database.Database.Init() == false)
            {
                Log.Error("Main", "Cannot connect to database");
                while (true) ;
            }

            /*
            DBRowDescriptor descriptor = new DBRowDescriptor();

            descriptor.AddColumn("itemID", FieldType.I4);
            descriptor.AddColumn("custominfo", FieldType.Str);

            PyPackedRow packed = new PyPackedRow(descriptor);

            packed.SetValue("itemID", new PyInt(500));
            packed.SetValue("custominfo", new PyString("hello world"));

            byte[] marshaled = Marshal.Marshal.Process(packed);

            PyPackedRow unmarshaled = Unmarshal.Process<PyPackedRow>(marshaled);

            Console.WriteLine(PrettyPrinter.Print(unmarshaled));
            */

            byte[] raw = new byte[] { 1, 0, 55, 1, 22, 33, 0, 33, 25, 33, 14, 0, 0, 25, 45 };

            MemoryStream output = new MemoryStream(raw);
            BinaryReader reader = new BinaryReader(output);

            MemoryStream stream = new MemoryStream();
            BinaryWriter streamWriter = new BinaryWriter(stream);
            BinaryReader streamReader = new BinaryReader(stream);

            PyPackedRow.ZeroCompress(reader, output, streamWriter);

            byte[] compressed = stream.ToArray();
            stream.Seek(0, SeekOrigin.Begin);

            byte[] uncompress = PyPackedRow.LoadZeroCompressed(streamReader);

            while (true) Thread.Sleep(1);
            /*
            SHA1 sha1 = SHA1.Create();
            byte[] hash = sha1.ComputeHash(Encoding.ASCII.GetBytes("password"));
            char[] strHash = new char[20];

            for (int i = 0; i < 20; i++)
            {
                strHash[i] = (char)hash[i];
            }

            string str = new string(strHash);

            Database.Database.Query("INSERT INTO account(accountID, accountName, password, role, online, banned)VALUES(NULL, 'Username', '" + str + "', 2, 0, 0);");
            */

            Log.Info("Main", "Connection to the DB sucessfull");

            Log.Trace("Main", "Registering services...");

            SvcMgr.AddService(new Services.Network.machoNet());
            SvcMgr.AddService(new Services.Network.alert());
            SvcMgr.AddService(new Services.CacheSvc.objectCaching());

            Log.Info("Main", "Done");
            Log.Info("Main", "Connecting to proxy...");

            proxyConnection = new TCPSocket(ushort.Parse(proxy[0, 1]), false);
            if (proxyConnection.Connect(proxy[0, 0]) == false)
            {
                Log.Error("Main", "Cannot connect to proxy. Halting");
                Database.Database.Stop();
                while (true) ;
            }

            Log.Trace("Main", "Server started");

            while (true)
            {
                Thread.Sleep(1);
                try
                {
                    byte[] data = new byte[proxyConnection.Available];
                    int bytes = proxyConnection.Recv(data);

                    if (bytes == -1)
                    {
                        // Proxy is closing, shutdown the node
                        break;
                    }
                    else if (bytes > 0)
                    {
                        packetizer.QueuePackets(data, bytes);
                        int p = packetizer.ProcessPackets();

                        for (int i = 0; i < p; i++)
                        {
                            byte[] packet = packetizer.PopItem();
                            PyObject obj = Unmarshal.Process<PyObject>(packet);

                            if (obj is PyObjectData)
                            {
                                PyObjectData info = obj as PyObjectData;

                                if (info.Name == "machoNet.nodeInfo")
                                {
                                    // Update our local info
                                    NodeInfo nodeinfo = new NodeInfo();

                                    if (nodeinfo.Decode(info) == true)
                                    {
                                        nodeID = nodeinfo.nodeID;

                                        SystemManager.LoadSolarSystems(nodeinfo.solarSystems);
                                    }
                                }
                                else
                                {
                                    // Client packet
                                    PyPacket clientpacket = new PyPacket();

                                    if (clientpacket.Decode(info) == false)
                                    {
                                        Log.Error("Main", "Unknown packet");
                                    }
                                    else
                                    {
                                        // Something similar to Async calls
                                        new Thread(new ParameterizedThreadStart(HandlePacket)).Start(clientpacket);
                                    }
                                }
                            }
                            else if (obj is PyChecksumedStream) // Checksumed packets
                            {
                                PyPacket clientpacket = new PyPacket();

                                if (clientpacket.Decode(obj) == false)
                                {
                                    Log.Error("Main", "Cannot decode packet");
                                }
                                else
                                {
                                    new Thread(new ParameterizedThreadStart(HandlePacket)).Start(clientpacket);
                                }
                            }
                            else if (obj is PyTuple)
                            {
                                // The only tuple packet is the LowLevelVersionExchange
                                LowLevelVersionExchange ex = new LowLevelVersionExchange();

                                if (ex.Decode(obj) == false)
                                {
                                    Log.Error("Main", "LowLevelVersionExchange error");
                                }

                                // Reply with the node LowLevelVersionExchange
                                LowLevelVersionExchange reply = new LowLevelVersionExchange();

                                reply.codename = Common.Constants.Game.codename;
                                reply.birthday = Common.Constants.Game.birthday;
                                reply.build = Common.Constants.Game.build;
                                reply.machoVersion = Common.Constants.Game.machoVersion;
                                reply.version = Common.Constants.Game.version;
                                reply.region = Common.Constants.Game.region;

                                Send(reply.Encode(true));
                            }
                            else if (obj is PyObjectEx)
                            {
                                Log.Error("PyObjectEx", PrettyPrinter.Print(obj));
                            }
                            else
                            {
                                Log.Error("Main", PrettyPrinter.Print(obj));
                                Log.Error("Main", "Unhandled packet type");
                            }
                        }
                    }

                }
                catch (Exception)
                {

                }
            }

            /* Code to ADD an account:
            SHA1 sha1 = SHA1.Create();
            byte[] hash = sha1.ComputeHash(Encoding.ASCII.GetBytes("password"));
            char[] strHash = new char[20];

            for (int i = 0; i < 20; i++)
            {
                strHash[i] = (char)hash[i];
            }

            string str = new string(strHash);

            Database.Database.Query("INSERT INTO account(accountID, accountName, password, role, online, banned)VALUES(NULL, 'Username', '" + str + "', 2, 0, 0);");
            */
        }
Пример #15
0
        public void ReceiveNodeAsync(IAsyncResult ar)
        {
            try
            {
                AsyncState state = (AsyncState)(ar.AsyncState);

                int bytes = Socket.Socket.EndReceive(ar);

                packetizer.QueuePackets(state.buffer, bytes);
                int p = packetizer.ProcessPackets();

                for (int i = 0; i < p; i++)
                {
                    byte[] packet = packetizer.PopItem();

                    PyObject obj = Unmarshal.Process<PyObject>(packet);

                    if (obj == null)
                    {
                        Log.Debug("Node", "Null packet received");
                        continue;
                    }

                    if ((obj is PyObjectData) == false)
                    {
                        Log.Debug("Node", "Non-valid node packet. Dropping");
                        continue;
                    }

                    PyObjectData item = obj as PyObjectData;

                    if (item.Name == "macho.CallRsp")
                    {
                        PyPacket final = new PyPacket();

                        if (final.Decode(item) == false)
                        {
                            Log.Error("Node", "Cannot decode packet");
                            continue;
                        }

                        if (final.dest.type == PyAddress.AddrType.Client)
                        {
                            ConnectionManager.NotifyClient((int)(final.userID), obj);
                        }
                        else if (final.dest.type == PyAddress.AddrType.Node)
                        {
                            ConnectionManager.NotifyNode((int)(final.dest.typeID), obj);
                        }
                        else if (final.dest.type == PyAddress.AddrType.Broadcast)
                        {
                            Log.Error("Node", "Broadcast packets not supported yet");
                        }
                        // TODO: Handle Broadcast packets
                    }
                    else
                    {
                        Log.Error("Node", string.Format("Wrong packet name: {0}", item.Name));
                    }
                }

                Socket.Socket.BeginReceive(state.buffer, 0, 8192, SocketFlags.None, recvAsync, state);
            }
            catch (ObjectDisposedException)
            {
                Log.Debug("Node", "Disconnected");
                ConnectionManager.RemoveConnection(this);
            }
            catch (SocketException)
            {
                Log.Debug("Node", "Disconnected");
                ConnectionManager.RemoveConnection(this);
            }
            catch (Exception ex)
            {
                Log.Error("Node", "Caught unhandled exception: " + ex.ToString());
            }
        }
Пример #16
0
        static void Main(string[] args)
        {
            Log.Init("evesharp");
            Log.Info("Main", "Starting node...");
            Log.Trace("Database", "Connecting to database...");

            if (Database.Database.Init() == false)
            {
                Log.Error("Main", "Cannot connect to database");
                while (true) ;
            }

            /*
            SHA1 sha1 = SHA1.Create();
            byte[] hash = sha1.ComputeHash(Encoding.ASCII.GetBytes("password"));
            char[] strHash = new char[20];

            for (int i = 0; i < 20; i++)
            {
                strHash[i] = (char)hash[i];
            }

            string str = new string(strHash);

            Database.Database.Query("INSERT INTO account(accountID, accountName, password, role, online, banned)VALUES(NULL, 'Username', '" + str + "', 2, 0, 0);");
            */

            Log.Info("Main", "Connection to the DB sucessfull");

            Log.Info("Main", "Generating default cache data");
            Cache.GenerateCache();
            Log.Debug("Main", "Done");

            Log.Info("Main", "Connecting to proxy...");

            proxyConnection = new TCPSocket(ushort.Parse(proxy[0, 1]), false);
            if (proxyConnection.Connect(proxy[0, 0]) == false)
            {
                Log.Error("Main", "Cannot connect to proxy. Halting");
                Database.Database.Stop();
                while (true) ;
            }

            Log.Trace("Main", "Server started");

            while (true)
            {
                Thread.Sleep(1);
                try
                {
                    byte[] data = new byte[proxyConnection.Available];
                    int bytes = proxyConnection.Recv(data);

                    if (bytes == -1)
                    {
                        // Proxy is closing, shutdown the node
                        break;
                    }
                    else if (bytes > 0)
                    {
                        packetizer.QueuePackets(data, bytes);
                        int p = packetizer.ProcessPackets();

                        for (int i = 0; i < p; i++)
                        {
                            byte[] packet = packetizer.PopItem();
                            PyObject obj = Unmarshal.Process<PyObject>(packet);

                            if (obj is PyObjectData)
                            {
                                PyObjectData info = obj as PyObjectData;

                                if (info.Name == "machoNet.nodeInfo")
                                {
                                    // Update our local info
                                    NodeInfo nodeinfo = new NodeInfo();

                                    if (nodeinfo.Decode(info) == true)
                                    {
                                        nodeID = nodeinfo.nodeID;

                                        Log.Debug("Main", "Found machoNet.nodeInfo, our new node id is " + nodeID.ToString("X4"));
                                        SystemManager.LoadSolarSystems(nodeinfo.solarSystems);
                                    }
                                }
                                else
                                {
                                    // Client packet
                                    PyPacket clientpacket = new PyPacket();

                                    if (clientpacket.Decode(info) == false)
                                    {
                                        Log.Error("Main", "Unknown packet");
                                    }
                                    else
                                    {
                                        // Something similar to Async calls
                                        new Thread(new ParameterizedThreadStart(HandlePacket)).Start(clientpacket);
                                    }
                                }
                            }
                            else if (obj is PyChecksumedStream) // Checksumed packets
                            {
                                PyPacket clientpacket = new PyPacket();

                                if (clientpacket.Decode(obj) == false)
                                {
                                    Log.Error("Main", "Cannot decode packet");
                                }
                                else
                                {
                                    new Thread(new ParameterizedThreadStart(HandlePacket)).Start(clientpacket);
                                }
                            }
                            else if (obj is PyTuple)
                            {
                                // The only tuple packet is the LowLevelVersionExchange
                                LowLevelVersionExchange ex = new LowLevelVersionExchange();

                                if (ex.Decode(obj) == false)
                                {
                                    Log.Error("Main", "LowLevelVersionExchange error");
                                }

                                // Reply with the node LowLevelVersionExchange
                                LowLevelVersionExchange reply = new LowLevelVersionExchange();

                                reply.codename = Common.Constants.Game.codename;
                                reply.birthday = Common.Constants.Game.birthday;
                                reply.build = Common.Constants.Game.build;
                                reply.machoVersion = Common.Constants.Game.machoVersion;
                                reply.version = Common.Constants.Game.version;
                                reply.region = Common.Constants.Game.region;

                                Send(reply.Encode(true));
                            }
                            else if (obj is PyObjectEx)
                            {
                                Log.Error("PyObjectEx", PrettyPrinter.Print(obj));
                            }
                            else
                            {
                                Log.Error("Main", PrettyPrinter.Print(obj));
                                Log.Error("Main", "Unhandled packet type");
                            }
                        }
                    }

                }
                catch (Exception)
                {

                }
            }

            /* Code to ADD an account:
            SHA1 sha1 = SHA1.Create();
            byte[] hash = sha1.ComputeHash(Encoding.ASCII.GetBytes("password"));
            char[] strHash = new char[20];

            for (int i = 0; i < 20; i++)
            {
                strHash[i] = (char)hash[i];
            }

            string str = new string(strHash);

            Database.Database.Query("INSERT INTO account(accountID, accountName, password, role, online, banned)VALUES(NULL, 'Username', '" + str + "', 2, 0, 0);");
            */
        }
Пример #17
0
        public static void HandlePacket(object input)
        {
            PyPacket packet = (PyPacket)input;
            PyPacket res = new PyPacket();

            if (packet.type == Macho.MachoNetMsg_Type.CALL_REQ)
            {
                PyTuple callInfo = packet.payload.As<PyTuple>().Items[0].As<PyTuple>()[1].As<PySubStream>().Data.As<PyTuple>();

                string call = callInfo.Items[1].As<PyString>().Value;
                PyTuple args = callInfo.Items[2].As<PyTuple>();
                PyDict sub = callInfo.Items[3].As<PyDict>();

                PyObject callRes = null;

                try
                {
                    callRes = Program.SvcMgr.ServiceCall(packet.dest.service, call, args, null);
                }
                catch (ServiceDoesNotContainCallException)
                {
                    Log.Error("HandlePacket", "The service " + packet.dest.service + " does not contain a definition for " + call);
                }
                catch (ServiceDoesNotExistsException)
                {
                    Log.Error("HandlePacket", "The requested service(" + packet.dest.service + ")does not exists");
                }
                catch (Exception ex)
                {
                    Log.Error("HandlePacket", "Unhadled exception: " + ex.ToString());
                }

                if (callRes == null)
                {
                    return;
                }

                if (callRes.Type == PyObjectType.Tuple)
                {
                    res.type_string = "macho.CallRsp";
                    res.type = Macho.MachoNetMsg_Type.CALL_RSP;

                    res.source = packet.dest;

                    res.dest = packet.source;
                    /*
                    res.dest.type = PyAddress.AddrType.Client;
                    res.dest.typeID = (ulong)clients[packet.userID].AccountID;
                    res.dest.callID = packet.source.callID;
                    */

                    res.userID = packet.userID;

                    res.payload = new PyTuple();
                    res.payload.Items.Add(new PySubStream(callRes));

                    Send(res.Encode());
                }
            }
            else if (packet.type == Macho.MachoNetMsg_Type.SESSIONCHANGENOTIFICATION)
            {
                Log.Debug("Main", "Updating session for client " + packet.userID);

                // Check if the client isnt assigned to this node yet
                if(clients.ContainsKey(packet.userID) == false)
                {
                    Client cli = new Client();
                    clients.Add(packet.userID, cli);
                }

                // Update client session
                clients[packet.userID].UpdateSession(packet);
            }
        }
Пример #18
0
        public PyPacket CreateEmptySessionChange()
        {
            // Fill all the packet data, except the dest/source
            SessionChangeNotification scn = new SessionChangeNotification();
            scn.changes = Session.EncodeChanges();

            if (scn.changes.Dictionary.Count == 0)
            {
                // Nothing to do
                return null;
            }

            Dictionary<int, Connection> nodes = ConnectionManager.Nodes;

            // Add all the nodeIDs
            foreach (KeyValuePair<int, Connection> node in nodes)
            {
                scn.nodesOfInterest.Items.Add(new PyInt(node.Key));
            }

            PyPacket p = new PyPacket();

            p.type_string = "macho.SessionChangeNotification";
            p.type = Macho.MachoNetMsg_Type.SESSIONCHANGENOTIFICATION;

            p.userID = (uint)AccountID;

            p.payload = scn.Encode().As<PyTuple>();

            p.named_payload = new PyDict();
            p.named_payload.Set("channel", new PyString("sessionchange"));

            return p;
        }