Beispiel #1
0
        /// <summary>
        /// SV_ReadClientMove
        /// </summary>
        static void ReadClientMove(ref usercmd_t move)
        {
            client_t client = Host.HostClient;

            // read ping time
            client.ping_times[client.num_pings % NUM_PING_TIMES] = (float)(sv.time - Net.Reader.ReadFloat());
            client.num_pings++;

            // read current angles
            Vector3 angles = Net.Reader.ReadAngles();

            Mathlib.Copy(ref angles, out client.edict.v.v_angle);

            // read movement
            move.forwardmove = Net.Reader.ReadShort();
            move.sidemove    = Net.Reader.ReadShort();
            move.upmove      = Net.Reader.ReadShort();

            // read buttons
            int bits = Net.Reader.ReadByte();

            client.edict.v.button0 = bits & 1;
            client.edict.v.button2 = (bits & 2) >> 1;

            int i = Net.Reader.ReadByte();

            if (i != 0)
            {
                client.edict.v.impulse = i;
            }
        }
Beispiel #2
0
        /*
         * ===============
         * PF_lightstyle
         *
         * void(float style, string value) lightstyle
         * ===============
         */
        static void PF_lightstyle()
        {
            int    style = (int)GetFloat(OFS.OFS_PARM0); // Uze: ???
            string val   = GetString(OFS.OFS_PARM1);

            // change the string in sv
            Server.sv.lightstyles[style] = val;

            // send message to all clients on this server
            if (!Server.IsActive)
            {
                return;
            }

            for (int j = 0; j < Server.svs.maxclients; j++)
            {
                client_t client = Server.svs.clients[j];
                if (client.active || client.spawned)
                {
                    client.message.WriteChar(Protocol.svc_lightstyle);
                    client.message.WriteChar(style);
                    client.message.WriteString(val);
                }
            }
        }
Beispiel #3
0
        /// <summary>
        /// Host_Ping_f
        /// </summary>
        private static void Ping_f()
        {
            if (Cmd.Source == cmd_source_t.src_command)
            {
                Cmd.ForwardToServer();
                return;
            }

            Server.ClientPrint("Client ping times:\n");
            for (int i = 0; i < Server.svs.maxclients; i++)
            {
                client_t client = Server.svs.clients[i];
                if (!client.active)
                {
                    continue;
                }
                float total = 0;
                for (int j = 0; j < Server.NUM_PING_TIMES; j++)
                {
                    total += client.ping_times[j];
                }
                total /= Server.NUM_PING_TIMES;
                Server.ClientPrint("{0,4} {1}\n", (int)(total * 1000), client.name);
            }
        }
Beispiel #4
0
        /// <summary>
        /// SV_SendClientDatagram
        /// </summary>
        private static bool SendClientDatagram(client_t client)
        {
            MsgWriter msg = new MsgWriter(QDef.MAX_DATAGRAM);   // Uze todo: make static?

            msg.WriteByte(protocol.svc_time);
            msg.WriteFloat((float)sv.time);

            // add the client specific data to the datagram
            WriteClientDataToMessage(client.edict, msg);

            WriteEntitiesToClient(client.edict, msg);

            // copy the server datagram if there is space
            if (msg.Length + sv.datagram.Length < msg.Capacity)
            {
                msg.Write(sv.datagram.Data, 0, sv.datagram.Length);
            }

            // send the datagram
            if (net.SendUnreliableMessage(client.netconnection, msg) == -1)
            {
                DropClient(true);  // if the message couldn't send, kick off
                return(false);
            }

            return(true);
        }
Beispiel #5
0
        /// <summary>
        /// SV_DropClient
        /// Called when the player is getting totally kicked off the host
        /// if (crash = true), don't bother sending signofs
        /// </summary>
        public static void DropClient(bool crash)
        {
            client_t client = host.HostClient;

            if (!crash)
            {
                // send any final messages (don't check for errors)
                if (net.CanSendMessage(client.netconnection))
                {
                    MsgWriter msg = client.message;
                    msg.WriteByte(protocol.svc_disconnect);
                    net.SendMessage(client.netconnection, msg);
                }

                if (client.edict != null && client.spawned)
                {
                    // call the prog function for removing a client
                    // this will set the body to a dead frame, among other things
                    int saveSelf = progs.GlobalStruct.self;
                    progs.GlobalStruct.self = EdictToProg(client.edict);
                    progs.Execute(progs.GlobalStruct.ClientDisconnect);
                    progs.GlobalStruct.self = saveSelf;
                }

                Con.DPrint("Client {0} removed\n", client.name);
            }

            // break the net connection
            net.Close(client.netconnection);
            client.netconnection = null;

            // free the client (the body stays around)
            client.active    = false;
            client.name      = null;
            client.old_frags = -999999;
            net.ActiveConnections--;

            // send notification to all clients
            for (int i = 0; i < SharpQuake.server.svs.maxclients; i++)
            {
                client_t cl = SharpQuake.server.svs.clients[i];
                if (!cl.active)
                {
                    continue;
                }

                cl.message.WriteByte(protocol.svc_updatename);
                cl.message.WriteByte(host.ClientNum);
                cl.message.WriteString("");
                cl.message.WriteByte(protocol.svc_updatefrags);
                cl.message.WriteByte(host.ClientNum);
                cl.message.WriteShort(0);
                cl.message.WriteByte(protocol.svc_updatecolors);
                cl.message.WriteByte(host.ClientNum);
                cl.message.WriteByte(0);
            }
        }
Beispiel #6
0
        /// <summary>
        /// SV_SendNop
        /// Send a nop message without trashing or sending the accumulated client
        /// message buffer
        /// </summary>
        private void SendNop(client_t client)
        {
            var msg = new MessageWriter(4);

            msg.WriteChar(ProtocolDef.svc_nop);

            if (Host.Network.SendUnreliableMessage(client.netconnection, msg) == -1)
            {
                DropClient(true);                   // if the message couldn't send, kick off
            }
            client.last_message = Host.RealTime;
        }
Beispiel #7
0
        /// <summary>
        /// SV_SendNop
        /// Send a nop message without trashing or sending the accumulated client
        /// message buffer
        /// </summary>
        private static void SendNop(client_t client)
        {
            MsgWriter msg = new MsgWriter(4);

            msg.WriteChar(protocol.svc_nop);

            if (net.SendUnreliableMessage(client.netconnection, msg) == -1)
            {
                DropClient(true);       // if the message couldn't send, kick off
            }
            client.last_message = host.RealTime;
        }
Beispiel #8
0
        /*
         * ==============
         * PF_setspawnparms
         * ==============
         */
        static void PF_setspawnparms()
        {
            edict_t ent = GetEdict(OFS.OFS_PARM0);
            int     i   = Server.NumForEdict(ent);

            if (i < 1 || i > Server.svs.maxclients)
            {
                Progs.RunError("Entity is not a client");
            }

            // copy spawn parms out of the client_t
            client_t client = Server.svs.clients[i - 1];

            Progs.GlobalStruct.SetParams(client.spawn_parms);
        }
Beispiel #9
0
        /*
         * =================
         * PF_centerprint
         *
         * single print to a specific client
         *
         * centerprint(clientent, value)
         * =================
         */
        static void PF_centerprint()
        {
            int    entnum = Server.NumForEdict(GetEdict(OFS.OFS_PARM0));
            string s      = PF_VarString(1);

            if (entnum < 1 || entnum > Server.svs.maxclients)
            {
                Con.Print("tried to centerprint to a non-client\n");
                return;
            }

            client_t client = Server.svs.clients[entnum - 1];

            client.message.WriteChar(Protocol.svc_centerprint);
            client.message.WriteString(s);
        }
Beispiel #10
0
        //============================================================================


        /// <summary>
        /// PF_stuffcmd
        /// Sends text over to the client's execution buffer
        /// stuffcmd (clientent, value)
        /// </summary>
        static void PF_stuffcmd()
        {
            int entnum = Server.NumForEdict(GetEdict(OFS.OFS_PARM0));

            if (entnum < 1 || entnum > Server.svs.maxclients)
            {
                Progs.RunError("Parm 0 not a client");
            }
            string str = GetString(OFS.OFS_PARM1);

            client_t old = Host.HostClient;

            Host.HostClient = Server.svs.clients[entnum - 1];
            Host.ClientCommands("{0}", str);
            Host.HostClient = old;
        }
Beispiel #11
0
        // Host_Tell_f
        static void Tell_f()
        {
            if (Cmd.Source == cmd_source_t.src_command)
            {
                Cmd.ForwardToServer();
                return;
            }

            if (Cmd.Argc < 3)
            {
                return;
            }

            string text = Host.HostClient.name + ": ";
            string p    = Cmd.Args;

            // remove quotes if present
            if (p.StartsWith("\""))
            {
                p = p.Substring(1, p.Length - 2);
            }

            text += p + "\n";

            client_t save = Host.HostClient;

            for (int j = 0; j < Server.svs.maxclients; j++)
            {
                client_t client = Server.svs.clients[j];
                if (!client.active || !client.spawned)
                {
                    continue;
                }

                if (client.name == Cmd.Argv(1))
                {
                    continue;
                }

                Host.HostClient = client;
                Server.ClientPrint(text);
                break;
            }
            Host.HostClient = save;
        }
Beispiel #12
0
        private qsocket_t ProcessRequestPlayerInfo(Socket acceptsock, EndPoint clientaddr)
        {
            var      playerNumber = Host.Network.Reader.ReadByte();
            Int32    clientNumber, activeNumber = -1;
            client_t client = null;

            for (clientNumber = 0; clientNumber < Host.Server.svs.maxclients; clientNumber++)
            {
                client = Host.Server.svs.clients[clientNumber];
                if (client.active)
                {
                    activeNumber++;

                    if (activeNumber == playerNumber)
                    {
                        break;
                    }
                }
            }

            if (clientNumber == Host.Server.svs.maxclients)
            {
                return(null);
            }

            Host.Network.Message.Clear();
            // save space for the header, filled in later
            Host.Network.Message.WriteLong(0);
            Host.Network.Message.WriteByte(CCRep.CCREP_PLAYER_INFO);
            Host.Network.Message.WriteByte(playerNumber);
            Host.Network.Message.WriteString(client.name);
            Host.Network.Message.WriteLong(client.colors);
            Host.Network.Message.WriteLong(( Int32 )client.edict.v.frags);
            Host.Network.Message.WriteLong(( Int32 )(Host.Network.Time - client.netconnection.connecttime));
            Host.Network.Message.WriteString(client.netconnection.address);
            Utilities.WriteInt(Host.Network.Message.Data, 0, EndianHelper.BigLong(NetFlags.NETFLAG_CTL |
                                                                                  (Host.Network.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
            Host.Network.LanDriver.Write(acceptsock, Host.Network.Message.Data, Host.Network.Message.Length, clientaddr);
            Host.Network.Message.Clear();

            return(null);
        }
Beispiel #13
0
        /// <summary>
        /// SV_ConnectClient
        /// Initializes a client_t for a new net connection.  This will only be called
        /// once for a player each game, not once for each level change.
        /// </summary>
        private static void ConnectClient(int clientnum)
        {
            client_t client = svs.clients[clientnum];

            Con.DPrint("Client {0} connected\n", client.netconnection.address);

            int     edictnum = clientnum + 1;
            edict_t ent      = EdictNum(edictnum);

            // set up the client_t
            qsocket_t netconnection = client.netconnection;

            float[] spawn_parms = new float[NUM_SPAWN_PARMS];
            if (sv.loadgame)
            {
                Array.Copy(client.spawn_parms, spawn_parms, spawn_parms.Length);
            }

            client.Clear();
            client.netconnection         = netconnection;
            client.name                  = "unconnected";
            client.active                = true;
            client.spawned               = false;
            client.edict                 = ent;
            client.message.AllowOverflow = true; // we can catch it
            client.privileged            = false;

            if (sv.loadgame)
            {
                Array.Copy(spawn_parms, client.spawn_parms, spawn_parms.Length);
            }
            else
            {
                // call the progs to get default spawn parms for the new client
                progs.Execute(progs.GlobalStruct.SetNewParms);

                AssignGlobalSpawnparams(client);
            }

            SendServerInfo(client);
        }
Beispiel #14
0
        private static void AssignGlobalSpawnparams(client_t client)
        {
            client.spawn_parms[0] = progs.GlobalStruct.parm1;
            client.spawn_parms[1] = progs.GlobalStruct.parm2;
            client.spawn_parms[2] = progs.GlobalStruct.parm3;
            client.spawn_parms[3] = progs.GlobalStruct.parm4;

            client.spawn_parms[4] = progs.GlobalStruct.parm5;
            client.spawn_parms[5] = progs.GlobalStruct.parm6;
            client.spawn_parms[6] = progs.GlobalStruct.parm7;
            client.spawn_parms[7] = progs.GlobalStruct.parm8;

            client.spawn_parms[8]  = progs.GlobalStruct.parm9;
            client.spawn_parms[9]  = progs.GlobalStruct.parm10;
            client.spawn_parms[10] = progs.GlobalStruct.parm11;
            client.spawn_parms[11] = progs.GlobalStruct.parm12;

            client.spawn_parms[12] = progs.GlobalStruct.parm13;
            client.spawn_parms[13] = progs.GlobalStruct.parm14;
            client.spawn_parms[14] = progs.GlobalStruct.parm15;
            client.spawn_parms[15] = progs.GlobalStruct.parm16;
        }
Beispiel #15
0
        /// <summary>
        /// SV_UpdateToReliableMessages
        /// </summary>
        static void UpdateToReliableMessages()
        {
            // check for changes to be sent over the reliable streams
            for (int i = 0; i < svs.maxclients; i++)
            {
                Host.HostClient = svs.clients[i];
                if (Host.HostClient.old_frags != Host.HostClient.edict.v.frags)
                {
                    for (int j = 0; j < svs.maxclients; j++)
                    {
                        client_t client = svs.clients[j];
                        if (!client.active)
                        {
                            continue;
                        }

                        client.message.WriteByte(Protocol.svc_updatefrags);
                        client.message.WriteByte(i);
                        client.message.WriteShort((int)Host.HostClient.edict.v.frags);
                    }

                    Host.HostClient.old_frags = (int)Host.HostClient.edict.v.frags;
                }
            }

            for (int j = 0; j < svs.maxclients; j++)
            {
                client_t client = svs.clients[j];
                if (!client.active)
                {
                    continue;
                }

                client.message.Write(sv.reliable_datagram.Data, 0, sv.reliable_datagram.Length);
            }

            sv.reliable_datagram.Clear();
        }
Beispiel #16
0
        /// <summary>
        /// Host_ShutdownServer
        /// This only happens at the end of a game, not between levels
        /// </summary>
        public static void ShutdownServer(bool crash)
        {
            if (!Server.IsActive)
            {
                return;
            }

            Server.sv.active = false;

            // stop all client sounds immediately
            if (Client.cls.state == cactive_t.ca_connected)
            {
                Client.Disconnect();
            }

            // flush any pending messages - like the score!!!
            double start = Sys.GetFloatTime();
            int    count;

            do
            {
                count = 0;
                for (int i = 0; i < Server.svs.maxclients; i++)
                {
                    HostClient = Server.svs.clients[i];
                    if (HostClient.active && !HostClient.message.IsEmpty)
                    {
                        if (Net.CanSendMessage(HostClient.netconnection))
                        {
                            Net.SendMessage(HostClient.netconnection, HostClient.message);
                            HostClient.message.Clear();
                        }
                        else
                        {
                            Net.GetMessage(HostClient.netconnection);
                            count++;
                        }
                    }
                }
                if ((Sys.GetFloatTime() - start) > 3.0)
                {
                    break;
                }
            }while (count > 0);

            // make sure all the clients know we're disconnecting
            MsgWriter writer = new MsgWriter(4);

            writer.WriteByte(Protocol.svc_disconnect);
            count = Net.SendToAll(writer, 5);
            if (count != 0)
            {
                Con.Print("Host_ShutdownServer: NET_SendToAll failed for {0} clients\n", count);
            }

            for (int i = 0; i < Server.svs.maxclients; i++)
            {
                HostClient = Server.svs.clients[i];
                if (HostClient.active)
                {
                    Server.DropClient(crash);
                }
            }

            //
            // clear structures
            //
            Server.sv.Clear();
            for (int i = 0; i < Server.svs.clients.Length; i++)
            {
                Server.svs.clients[i].Clear();
            }
        }
Beispiel #17
0
        /// <summary>
        /// _Datagram_CheckNewConnections
        /// </summary>
        public qsocket_t InternalCheckNewConnections( )
        {
            var acceptsock = Host.Network.LanDriver.CheckNewConnections( );

            if (acceptsock == null)
            {
                return(null);
            }

            EndPoint clientaddr = new IPEndPoint(IPAddress.Any, 0);

            Host.Network.Message.FillFrom(Host.Network, acceptsock, ref clientaddr);

            if (Host.Network.Message.Length < sizeof(Int32))
            {
                return(null);
            }

            Host.Network.Reader.Reset( );
            var control = EndianHelper.BigLong(Host.Network.Reader.ReadLong( ));

            if (control == -1)
            {
                return(null);
            }
            if ((control & (~NetFlags.NETFLAG_LENGTH_MASK)) != NetFlags.NETFLAG_CTL)
            {
                return(null);
            }
            if ((control & NetFlags.NETFLAG_LENGTH_MASK) != Host.Network.Message.Length)
            {
                return(null);
            }

            var command = Host.Network.Reader.ReadByte( );

            if (command == CCReq.CCREQ_SERVER_INFO)
            {
                var tmp = Host.Network.Reader.ReadString( );
                if (tmp != "QUAKE")
                {
                    return(null);
                }

                Host.Network.Message.Clear( );

                // save space for the header, filled in later
                Host.Network.Message.WriteLong(0);
                Host.Network.Message.WriteByte(CCRep.CCREP_SERVER_INFO);
                var newaddr = acceptsock.LocalEndPoint;                //dfunc.GetSocketAddr(acceptsock, &newaddr);
                Host.Network.Message.WriteString(newaddr.ToString( )); // dfunc.AddrToString(&newaddr));
                Host.Network.Message.WriteString(Host.Network.HostName);
                Host.Network.Message.WriteString(Host.Server.sv.name);
                Host.Network.Message.WriteByte(Host.Network.ActiveConnections);
                Host.Network.Message.WriteByte(Host.Server.svs.maxclients);
                Host.Network.Message.WriteByte(NetworkDef.NET_PROTOCOL_VERSION);
                Utilities.WriteInt(Host.Network.Message.Data, 0, EndianHelper.BigLong(NetFlags.NETFLAG_CTL |
                                                                                      (Host.Network.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                Host.Network.LanDriver.Write(acceptsock, Host.Network.Message.Data, Host.Network.Message.Length, clientaddr);
                Host.Network.Message.Clear( );
                return(null);
            }

            if (command == CCReq.CCREQ_PLAYER_INFO)
            {
                var      playerNumber = Host.Network.Reader.ReadByte( );
                Int32    clientNumber, activeNumber = -1;
                client_t client = null;
                for (clientNumber = 0; clientNumber < Host.Server.svs.maxclients; clientNumber++)
                {
                    client = Host.Server.svs.clients[clientNumber];
                    if (client.active)
                    {
                        activeNumber++;
                        if (activeNumber == playerNumber)
                        {
                            break;
                        }
                    }
                }
                if (clientNumber == Host.Server.svs.maxclients)
                {
                    return(null);
                }

                Host.Network.Message.Clear( );
                // save space for the header, filled in later
                Host.Network.Message.WriteLong(0);
                Host.Network.Message.WriteByte(CCRep.CCREP_PLAYER_INFO);
                Host.Network.Message.WriteByte(playerNumber);
                Host.Network.Message.WriteString(client.name);
                Host.Network.Message.WriteLong(client.colors);
                Host.Network.Message.WriteLong(( Int32 )client.edict.v.frags);
                Host.Network.Message.WriteLong(( Int32 )(Host.Network.Time - client.netconnection.connecttime));
                Host.Network.Message.WriteString(client.netconnection.address);
                Utilities.WriteInt(Host.Network.Message.Data, 0, EndianHelper.BigLong(NetFlags.NETFLAG_CTL |
                                                                                      (Host.Network.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                Host.Network.LanDriver.Write(acceptsock, Host.Network.Message.Data, Host.Network.Message.Length, clientaddr);
                Host.Network.Message.Clear( );

                return(null);
            }

            if (command == CCReq.CCREQ_RULE_INFO)
            {
                // find the search start location
                var            prevCvarName = Host.Network.Reader.ReadString( );
                ClientVariable var;
                if (!String.IsNullOrEmpty(prevCvarName))
                {
                    var = Host.CVars.Get(prevCvarName);

                    if (var == null)
                    {
                        return(null);
                    }

                    var index = Host.CVars.IndexOf(var.Name);

                    var = Host.CVars.GetByIndex(index + 1);
                }
                else
                {
                    var = Host.CVars.GetByIndex(0);
                }

                // search for the next server cvar
                while (var != null)
                {
                    if (var.IsServer)
                    {
                        break;
                    }

                    var index = Host.CVars.IndexOf(var.Name);

                    var = Host.CVars.GetByIndex(index + 1);
                }

                // send the response
                Host.Network.Message.Clear( );

                // save space for the header, filled in later
                Host.Network.Message.WriteLong(0);
                Host.Network.Message.WriteByte(CCRep.CCREP_RULE_INFO);
                if (var != null)
                {
                    Host.Network.Message.WriteString(var.Name);
                    Host.Network.Message.WriteString(var.Get( ).ToString( ));
                }
                Utilities.WriteInt(Host.Network.Message.Data, 0, EndianHelper.BigLong(NetFlags.NETFLAG_CTL |
                                                                                      (Host.Network.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                Host.Network.LanDriver.Write(acceptsock, Host.Network.Message.Data, Host.Network.Message.Length, clientaddr);
                Host.Network.Message.Clear( );

                return(null);
            }

            if (command != CCReq.CCREQ_CONNECT)
            {
                return(null);
            }

            if (Host.Network.Reader.ReadString( ) != "QUAKE")
            {
                return(null);
            }

            if (Host.Network.Reader.ReadByte( ) != NetworkDef.NET_PROTOCOL_VERSION)
            {
                Host.Network.Message.Clear( );
                // save space for the header, filled in later
                Host.Network.Message.WriteLong(0);
                Host.Network.Message.WriteByte(CCRep.CCREP_REJECT);
                Host.Network.Message.WriteString("Incompatible version.\n");
                Utilities.WriteInt(Host.Network.Message.Data, 0, EndianHelper.BigLong(NetFlags.NETFLAG_CTL |
                                                                                      (Host.Network.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                Host.Network.LanDriver.Write(acceptsock, Host.Network.Message.Data, Host.Network.Message.Length, clientaddr);
                Host.Network.Message.Clear( );
                return(null);
            }

#if BAN_TEST
            // check for a ban
            if (clientaddr.sa_family == AF_INET)
            {
                unsigned long testAddr;
                testAddr = ((struct sockaddr_in *)&clientaddr)->sin_addr.s_addr;
Beispiel #18
0
        /// <summary>
        /// SV_SendServerinfo
        /// Sends the first message from the server to a connected client.
        /// This will be sent on the initial connection and upon each server load.
        /// </summary>
        private void SendServerInfo(client_t client)
        {
            var writer = client.message;

            writer.WriteByte(ProtocolDef.svc_print);
            writer.WriteString(String.Format("{0}\nVERSION {1,4:F2} SERVER ({2} CRC)", ( Char )2, QDef.VERSION, Host.Programs.Crc));

            writer.WriteByte(ProtocolDef.svc_serverinfo);
            writer.WriteLong(ProtocolDef.PROTOCOL_VERSION);
            writer.WriteByte(svs.maxclients);

            if (!Host.Cvars.Coop.Get <Boolean>() && Host.Cvars.Deathmatch.Get <Int32>() != 0)
            {
                writer.WriteByte(ProtocolDef.GAME_DEATHMATCH);
            }
            else
            {
                writer.WriteByte(ProtocolDef.GAME_COOP);
            }

            var message = Host.Programs.GetString(sv.edicts[0].v.message);

            writer.WriteString(message);

            for (var i = 1; i < sv.model_precache.Length; i++)
            {
                var tmp = sv.model_precache[i];
                if (String.IsNullOrEmpty(tmp))
                {
                    break;
                }
                writer.WriteString(tmp);
            }
            writer.WriteByte(0);

            for (var i = 1; i < sv.sound_precache.Length; i++)
            {
                var tmp = sv.sound_precache[i];
                if (tmp == null)
                {
                    break;
                }
                writer.WriteString(tmp);
            }
            writer.WriteByte(0);

            // send music
            writer.WriteByte(ProtocolDef.svc_cdtrack);
            writer.WriteByte(( Int32 )sv.edicts[0].v.sounds);
            writer.WriteByte(( Int32 )sv.edicts[0].v.sounds);

            // set view
            writer.WriteByte(ProtocolDef.svc_setview);
            writer.WriteShort(NumForEdict(client.edict));

            writer.WriteByte(ProtocolDef.svc_signonnum);
            writer.WriteByte(1);

            client.sendsignon = true;
            client.spawned    = false;              // need prespawn, spawn, etc
        }
Beispiel #19
0
        /// <summary>
        /// Host_ShutdownServer
        /// This only happens at the end of a game, not between levels
        /// </summary>
        public static void ShutdownServer(bool crash)
        {
            if (!Server.IsActive)
                return;

            Server.sv.active = false;

            // stop all client sounds immediately
            if (Client.cls.state == cactive_t.ca_connected)
                Client.Disconnect();

            // flush any pending messages - like the score!!!
            double start = Sys.GetFloatTime();
            int count;
            do
            {
                count = 0;
                for (int i = 0; i < Server.svs.maxclients; i++)
                {
                    HostClient = Server.svs.clients[i];
                    if (HostClient.active && !HostClient.message.IsEmpty)
                    {
                        if (Net.CanSendMessage(HostClient.netconnection))
                        {
                            Net.SendMessage(HostClient.netconnection, HostClient.message);
                            HostClient.message.Clear();
                        }
                        else
                        {
                            Net.GetMessage(HostClient.netconnection);
                            count++;
                        }
                    }
                }
                if ((Sys.GetFloatTime() - start) > 3.0)
                    break;
            }
            while (count > 0);

            // make sure all the clients know we're disconnecting
            MsgWriter writer = new MsgWriter(4);
            writer.WriteByte(Protocol.svc_disconnect);
            count = Net.SendToAll(writer, 5);
            if (count != 0)
                Con.Print("Host_ShutdownServer: NET_SendToAll failed for {0} clients\n", count);

            for (int i = 0; i < Server.svs.maxclients; i++)
            {
                HostClient = Server.svs.clients[i];
                if (HostClient.active)
                    Server.DropClient(crash);
            }

            //
            // clear structures
            //
            Server.sv.Clear();
            for (int i = 0; i < Server.svs.clients.Length; i++)
                Server.svs.clients[i].Clear();
        }
Beispiel #20
0
        /// <summary>
        /// SV_SendServerinfo
        /// Sends the first message from the server to a connected client.
        /// This will be sent on the initial connection and upon each server load.
        /// </summary>
        private static void SendServerInfo(client_t client)
        {
            MsgWriter writer = client.message;

            writer.WriteByte(protocol.svc_print);
            writer.WriteString(String.Format("{0}\nVERSION {1,4:F2} SERVER ({2} CRC)", (char)2, QDef.VERSION, progs.Crc));

            writer.WriteByte(protocol.svc_serverinfo);
            writer.WriteLong(protocol.PROTOCOL_VERSION);
            writer.WriteByte(svs.maxclients);

            if (!host.IsCoop && host.Deathmatch != 0)
            {
                writer.WriteByte(protocol.GAME_DEATHMATCH);
            }
            else
            {
                writer.WriteByte(protocol.GAME_COOP);
            }

            string message = progs.GetString(sv.edicts[0].v.message);

            writer.WriteString(message);

            for (int i = 1; i < sv.model_precache.Length; i++)
            {
                string tmp = sv.model_precache[i];
                if (String.IsNullOrEmpty(tmp))
                {
                    break;
                }
                writer.WriteString(tmp);
            }
            writer.WriteByte(0);

            for (int i = 1; i < sv.sound_precache.Length; i++)
            {
                string tmp = sv.sound_precache[i];
                if (tmp == null)
                {
                    break;
                }
                writer.WriteString(tmp);
            }
            writer.WriteByte(0);

            // send music
            writer.WriteByte(protocol.svc_cdtrack);
            writer.WriteByte((int)sv.edicts[0].v.sounds);
            writer.WriteByte((int)sv.edicts[0].v.sounds);

            // set view
            writer.WriteByte(protocol.svc_setview);
            writer.WriteShort(NumForEdict(client.edict));

            writer.WriteByte(protocol.svc_signonnum);
            writer.WriteByte(1);

            client.sendsignon = true;
            client.spawned    = false;          // need prespawn, spawn, etc
        }
Beispiel #21
0
        /// <summary>
        /// _Datagram_CheckNewConnections
        /// </summary>
        public qsocket_t InternalCheckNewConnections()
        {
            Socket acceptsock = net.LanDriver.CheckNewConnections();

            if (acceptsock == null)
            {
                return(null);
            }

            EndPoint clientaddr = new IPEndPoint(IPAddress.Any, 0);

            net.Message.FillFrom(acceptsock, ref clientaddr);

            if (net.Message.Length < sizeof(int))
            {
                return(null);
            }

            net.Reader.Reset();
            int control = common.BigLong(net.Reader.ReadLong());

            if (control == -1)
            {
                return(null);
            }
            if ((control & (~NetFlags.NETFLAG_LENGTH_MASK)) != NetFlags.NETFLAG_CTL)
            {
                return(null);
            }
            if ((control & NetFlags.NETFLAG_LENGTH_MASK) != net.Message.Length)
            {
                return(null);
            }

            int command = net.Reader.ReadByte();

            if (command == CCReq.CCREQ_SERVER_INFO)
            {
                string tmp = net.Reader.ReadString();
                if (tmp != "QUAKE")
                {
                    return(null);
                }

                net.Message.Clear();

                // save space for the header, filled in later
                net.Message.WriteLong(0);
                net.Message.WriteByte(CCRep.CCREP_SERVER_INFO);
                EndPoint newaddr = acceptsock.LocalEndPoint; //dfunc.GetSocketAddr(acceptsock, &newaddr);
                net.Message.WriteString(newaddr.ToString()); // dfunc.AddrToString(&newaddr));
                net.Message.WriteString(net.HostName);
                net.Message.WriteString(server.sv.name);
                net.Message.WriteByte(net.ActiveConnections);
                net.Message.WriteByte(server.svs.maxclients);
                net.Message.WriteByte(net.NET_PROTOCOL_VERSION);
                common.WriteInt(net.Message.Data, 0, common.BigLong(NetFlags.NETFLAG_CTL |
                                                                    (net.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                net.LanDriver.Write(acceptsock, net.Message.Data, net.Message.Length, clientaddr);
                net.Message.Clear();
                return(null);
            }

            if (command == CCReq.CCREQ_PLAYER_INFO)
            {
                int      playerNumber = net.Reader.ReadByte();
                int      clientNumber, activeNumber = -1;
                client_t client = null;
                for (clientNumber = 0; clientNumber < server.svs.maxclients; clientNumber++)
                {
                    client = server.svs.clients[clientNumber];
                    if (client.active)
                    {
                        activeNumber++;
                        if (activeNumber == playerNumber)
                        {
                            break;
                        }
                    }
                }
                if (clientNumber == server.svs.maxclients)
                {
                    return(null);
                }

                net.Message.Clear();
                // save space for the header, filled in later
                net.Message.WriteLong(0);
                net.Message.WriteByte(CCRep.CCREP_PLAYER_INFO);
                net.Message.WriteByte(playerNumber);
                net.Message.WriteString(client.name);
                net.Message.WriteLong(client.colors);
                net.Message.WriteLong((int)client.edict.v.frags);
                net.Message.WriteLong((int)(net.Time - client.netconnection.connecttime));
                net.Message.WriteString(client.netconnection.address);
                common.WriteInt(net.Message.Data, 0, common.BigLong(NetFlags.NETFLAG_CTL |
                                                                    (net.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                net.LanDriver.Write(acceptsock, net.Message.Data, net.Message.Length, clientaddr);
                net.Message.Clear();

                return(null);
            }

            if (command == CCReq.CCREQ_RULE_INFO)
            {
                // find the search start location
                string prevCvarName = net.Reader.ReadString();
                cvar   var;
                if (!String.IsNullOrEmpty(prevCvarName))
                {
                    var = cvar.Find(prevCvarName);
                    if (var == null)
                    {
                        return(null);
                    }
                    var = var.Next;
                }
                else
                {
                    var = cvar.First;
                }

                // search for the next server cvar
                while (var != null)
                {
                    if (var.IsServer)
                    {
                        break;
                    }
                    var = var.Next;
                }

                // send the response
                net.Message.Clear();

                // save space for the header, filled in later
                net.Message.WriteLong(0);
                net.Message.WriteByte(CCRep.CCREP_RULE_INFO);
                if (var != null)
                {
                    net.Message.WriteString(var.Name);
                    net.Message.WriteString(var.String);
                }
                common.WriteInt(net.Message.Data, 0, common.BigLong(NetFlags.NETFLAG_CTL |
                                                                    (net.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                net.LanDriver.Write(acceptsock, net.Message.Data, net.Message.Length, clientaddr);
                net.Message.Clear();

                return(null);
            }

            if (command != CCReq.CCREQ_CONNECT)
            {
                return(null);
            }

            if (net.Reader.ReadString() != "QUAKE")
            {
                return(null);
            }

            if (net.Reader.ReadByte() != net.NET_PROTOCOL_VERSION)
            {
                net.Message.Clear();
                // save space for the header, filled in later
                net.Message.WriteLong(0);
                net.Message.WriteByte(CCRep.CCREP_REJECT);
                net.Message.WriteString("Incompatible version.\n");
                common.WriteInt(net.Message.Data, 0, common.BigLong(NetFlags.NETFLAG_CTL |
                                                                    (net.Message.Length & NetFlags.NETFLAG_LENGTH_MASK)));
                net.LanDriver.Write(acceptsock, net.Message.Data, net.Message.Length, clientaddr);
                net.Message.Clear();
                return(null);
            }

#if BAN_TEST
            // check for a ban
            if (clientaddr.sa_family == AF_INET)
            {
                unsigned long testAddr;
                testAddr = ((struct sockaddr_in *)&clientaddr)->sin_addr.s_addr;
Beispiel #22
0
        /// <summary>
        /// Host_Status_f
        /// </summary>
        private static void Status_f()
        {
            bool flag = true;

            if (Cmd.Source == cmd_source_t.src_command)
            {
                if (!Server.sv.active)
                {
                    Cmd.ForwardToServer();
                    return;
                }
            }
            else
            {
                flag = false;
            }

            StringBuilder sb = new StringBuilder(256);

            sb.Append(String.Format("host:    {0}\n", Cvar.GetString("hostname")));
            sb.Append(String.Format("version: {0:F2}\n", QDef.VERSION));
            if (Net.TcpIpAvailable)
            {
                sb.Append("tcp/ip:  ");
                sb.Append(Net.MyTcpIpAddress);
                sb.Append('\n');
            }

            sb.Append("map:     ");
            sb.Append(Server.sv.name);
            sb.Append('\n');
            sb.Append(String.Format("players: {0} active ({1} max)\n\n", Net.ActiveConnections, Server.svs.maxclients));
            for (int j = 0; j < Server.svs.maxclients; j++)
            {
                client_t client = Server.svs.clients[j];
                if (!client.active)
                {
                    continue;
                }

                int seconds = (int)(Net.Time - client.netconnection.connecttime);
                int hours, minutes = seconds / 60;
                if (minutes > 0)
                {
                    seconds -= (minutes * 60);
                    hours    = minutes / 60;
                    if (hours > 0)
                    {
                        minutes -= (hours * 60);
                    }
                }
                else
                {
                    hours = 0;
                }
                sb.Append(String.Format("#{0,-2} {1,-16}  {2}  {2}:{4,2}:{5,2}",
                                        j + 1, client.name, (int)client.edict.v.frags, hours, minutes, seconds));
                sb.Append("   ");
                sb.Append(client.netconnection.address);
                sb.Append('\n');
            }

            if (flag)
            {
                Con.Print(sb.ToString());
            }
            else
            {
                Server.ClientPrint(sb.ToString());
            }
        }
Beispiel #23
0
        /// <summary>
        /// Host_Say
        /// </summary>
        private static void Say(bool teamonly)
        {
            bool fromServer = false;

            if (Cmd.Source == cmd_source_t.src_command)
            {
                if (Client.cls.state == cactive_t.ca_dedicated)
                {
                    fromServer = true;
                    teamonly   = false;
                }
                else
                {
                    Cmd.ForwardToServer();
                    return;
                }
            }

            if (Cmd.Argc < 2)
            {
                return;
            }

            client_t save = Host.HostClient;

            string p = Cmd.Args;

            // remove quotes if present
            if (p.StartsWith("\""))
            {
                p = p.Substring(1, p.Length - 2);
            }

            // turn on color set 1
            string text;

            if (!fromServer)
            {
                text = (char)1 + save.name + ": ";
            }
            else
            {
                text = (char)1 + "<" + Net.HostName + "> ";
            }

            text += p + "\n";

            for (int j = 0; j < Server.svs.maxclients; j++)
            {
                client_t client = Server.svs.clients[j];
                if (client == null || !client.active || !client.spawned)
                {
                    continue;
                }
                if (Host.TeamPlay != 0 && teamonly && client.edict.v.team != save.edict.v.team)
                {
                    continue;
                }
                Host.HostClient = client;
                Server.ClientPrint(text);
            }
            Host.HostClient = save;
        }
Beispiel #24
0
        /// <summary>
        /// Host_Spawn_f
        /// </summary>
        private static void Spawn_f()
        {
            if (Cmd.Source == cmd_source_t.src_command)
            {
                Con.Print("spawn is not valid from the console\n");
                return;
            }

            if (Host.HostClient.spawned)
            {
                Con.Print("Spawn not valid -- allready spawned\n");
                return;
            }

            edict_t ent;

            // run the entrance script
            if (Server.sv.loadgame)
            {
                // loaded games are fully inited allready
                // if this is the last client to be connected, unpause
                Server.sv.paused = false;
            }
            else
            {
                // set up the edict
                ent = Host.HostClient.edict;

                ent.Clear(); //memset(&ent.v, 0, progs.entityfields * 4);
                ent.v.colormap = Server.NumForEdict(ent);
                ent.v.team     = (Host.HostClient.colors & 15) + 1;
                ent.v.netname  = Progs.NewString(Host.HostClient.name);

                // copy spawn parms out of the client_t
                Progs.GlobalStruct.SetParams(Host.HostClient.spawn_parms);

                // call the spawn function

                Progs.GlobalStruct.time = (float)Server.sv.time;
                Progs.GlobalStruct.self = Server.EdictToProg(Server.Player);
                Progs.Execute(Progs.GlobalStruct.ClientConnect);

                if ((Sys.GetFloatTime() - Host.HostClient.netconnection.connecttime) <= Server.sv.time)
                {
                    Con.DPrint("{0} entered the game\n", Host.HostClient.name);
                }

                Progs.Execute(Progs.GlobalStruct.PutClientInServer);
            }

            // send all current names, colors, and frag counts
            MsgWriter msg = Host.HostClient.message;

            msg.Clear();

            // send time of update
            msg.WriteByte(Protocol.svc_time);
            msg.WriteFloat((float)Server.sv.time);

            for (int i = 0; i < Server.svs.maxclients; i++)
            {
                client_t client = Server.svs.clients[i];
                msg.WriteByte(Protocol.svc_updatename);
                msg.WriteByte(i);
                msg.WriteString(client.name);
                msg.WriteByte(Protocol.svc_updatefrags);
                msg.WriteByte(i);
                msg.WriteShort(client.old_frags);
                msg.WriteByte(Protocol.svc_updatecolors);
                msg.WriteByte(i);
                msg.WriteByte(client.colors);
            }

            // send all current light styles
            for (int i = 0; i < QDef.MAX_LIGHTSTYLES; i++)
            {
                msg.WriteByte(Protocol.svc_lightstyle);
                msg.WriteByte((char)i);
                msg.WriteString(Server.sv.lightstyles[i]);
            }

            //
            // send some stats
            //
            msg.WriteByte(Protocol.svc_updatestat);
            msg.WriteByte(QStats.STAT_TOTALSECRETS);
            msg.WriteLong((int)Progs.GlobalStruct.total_secrets);

            msg.WriteByte(Protocol.svc_updatestat);
            msg.WriteByte(QStats.STAT_TOTALMONSTERS);
            msg.WriteLong((int)Progs.GlobalStruct.total_monsters);

            msg.WriteByte(Protocol.svc_updatestat);
            msg.WriteByte(QStats.STAT_SECRETS);
            msg.WriteLong((int)Progs.GlobalStruct.found_secrets);

            msg.WriteByte(Protocol.svc_updatestat);
            msg.WriteByte(QStats.STAT_MONSTERS);
            msg.WriteLong((int)Progs.GlobalStruct.killed_monsters);

            //
            // send a fixangle
            // Never send a roll angle, because savegames can catch the server
            // in a state where it is expecting the client to correct the angle
            // and it won't happen if the game was just loaded, so you wind up
            // with a permanent head tilt
            ent = Server.EdictNum(1 + Host.ClientNum);
            msg.WriteByte(Protocol.svc_setangle);
            msg.WriteAngle(ent.v.angles.x);
            msg.WriteAngle(ent.v.angles.y);
            msg.WriteAngle(0);

            Server.WriteClientDataToMessage(Server.Player, Host.HostClient.message);

            msg.WriteByte(Protocol.svc_signonnum);
            msg.WriteByte(3);
            Host.HostClient.sendsignon = true;
        }
Beispiel #25
0
        /// <summary>
        /// Host_Kick_f
        /// Kicks a user off of the server
        /// </summary>
        private static void Kick_f()
        {
            if (Cmd.Source == cmd_source_t.src_command)
            {
                if (!Server.sv.active)
                {
                    Cmd.ForwardToServer();
                    return;
                }
            }
            else if (Progs.GlobalStruct.deathmatch != 0 && !Host.HostClient.privileged)
            {
                return;
            }

            client_t save     = Host.HostClient;
            bool     byNumber = false;
            int      i;

            if (Cmd.Argc > 2 && Cmd.Argv(1) == "#")
            {
                i = (int)Common.atof(Cmd.Argv(2)) - 1;
                if (i < 0 || i >= Server.svs.maxclients)
                {
                    return;
                }
                if (!Server.svs.clients[i].active)
                {
                    return;
                }

                Host.HostClient = Server.svs.clients[i];
                byNumber        = true;
            }
            else
            {
                for (i = 0; i < Server.svs.maxclients; i++)
                {
                    Host.HostClient = Server.svs.clients[i];
                    if (!Host.HostClient.active)
                    {
                        continue;
                    }
                    if (Common.SameText(Host.HostClient.name, Cmd.Argv(1)))
                    {
                        break;
                    }
                }
            }

            if (i < Server.svs.maxclients)
            {
                string who;
                if (Cmd.Source == cmd_source_t.src_command)
                {
                    if (Client.cls.state == cactive_t.ca_dedicated)
                    {
                        who = "Console";
                    }
                    else
                    {
                        who = Client.Name;
                    }
                }
                else
                {
                    who = save.name;
                }

                // can't kick yourself!
                if (Host.HostClient == save)
                {
                    return;
                }

                string message = null;
                if (Cmd.Argc > 2)
                {
                    message = Common.Parse(Cmd.Args);
                    if (byNumber)
                    {
                        message = message.Substring(1);                  // skip the #
                        message = message.Trim();                        // skip white space
                        message = message.Substring(Cmd.Argv(2).Length); // skip the number
                    }
                    message = message.Trim();
                }
                if (!String.IsNullOrEmpty(message))
                {
                    Server.ClientPrint("Kicked by {0}: {1}\n", who, message);
                }
                else
                {
                    Server.ClientPrint("Kicked by {0}\n", who);
                }
                Server.DropClient(false);
            }

            Host.HostClient = save;
        }