X-Git-Url: http://de.git.xonotic.org/?p=xonotic%2Fdarkplaces.git;a=blobdiff_plain;f=sv_main.c;h=e6ce99427d03c790e71ed34a86d703bc1895b13e;hp=8e68234bdffa27eebfd714d601cfb4193530fade;hb=69a9f6bb4ea7d2a62b22238da58fe99d0ebd41d8;hpb=cbb6c7c5b3dadfa4bf3bf06285722a69e4f93f51 diff --git a/sv_main.c b/sv_main.c index 8e68234b..e6ce9942 100644 --- a/sv_main.c +++ b/sv_main.c @@ -372,7 +372,6 @@ void SV_SendServerinfo (client_t *client) MSG_WriteByte (&client->netconnection->message, svc_signonnum); MSG_WriteByte (&client->netconnection->message, 1); - client->sendsignon = true; client->spawned = false; // need prespawn, spawn, etc } @@ -408,7 +407,8 @@ void SV_ConnectClient (int clientnum, netconn_t *netconnection) strcpy(client->old_name, "unconnected"); client->spawned = false; client->edict = PRVM_EDICT_NUM(clientnum+1); - client->netconnection->message.allowoverflow = true; // we can catch it + if (client->netconnection) + client->netconnection->message.allowoverflow = true; // we can catch it // updated by receiving "rate" command from client client->rate = NET_MINRATE; // no limits for local player @@ -426,10 +426,10 @@ void SV_ConnectClient (int clientnum, netconn_t *netconnection) PRVM_ExecuteProgram (prog->globals.server->SetNewParms, "QC function SetNewParms is missing"); for (i=0 ; ispawn_parms[i] = (&prog->globals.server->parm1)[i]; - } - // set up the entity for this client (including .colormap, .team, etc) - PRVM_ED_ClearEdict(client->edict); + // set up the entity for this client (including .colormap, .team, etc) + PRVM_ED_ClearEdict(client->edict); + } // don't call SendServerinfo for a fresh botclient because its fields have // not been set up by the qc yet @@ -1179,7 +1179,7 @@ SV_SendClientDatagram ======================= */ static unsigned char sv_sendclientdatagram_buf[NET_MAXMESSAGE]; // FIXME? -qboolean SV_SendClientDatagram (client_t *client) +void SV_SendClientDatagram (client_t *client) { int rate, maxrate, maxsize, maxsize2; sizebuf_t msg; @@ -1206,6 +1206,8 @@ qboolean SV_SendClientDatagram (client_t *client) if (sv_maxrate.integer != maxrate) Cvar_SetValueQuick(&sv_maxrate, maxrate); + // this rate limiting does not understand sys_ticrate 0 + // (but no one should be running that on a server!) rate = bound(NET_MINRATE, client->rate, maxrate); rate = (int)(client->rate * sys_ticrate.value); maxsize = bound(100, rate, 1400); @@ -1216,31 +1218,35 @@ qboolean SV_SendClientDatagram (client_t *client) msg.maxsize = maxsize; msg.cursize = 0; - MSG_WriteByte (&msg, svc_time); - MSG_WriteFloat (&msg, sv.time); - - // add the client specific data to the datagram - SV_WriteClientdataToMessage (client, client->edict, &msg, stats); - VM_SV_WriteAutoSentStats (client, client->edict, &msg, stats); - SV_WriteEntitiesToClient (client, client->edict, &msg, stats); - - // expand packet size to allow effects to go over the rate limit - // (dropping them is FAR too ugly) - msg.maxsize = maxsize2; - - // copy the server datagram if there is space - // FIXME: put in delayed queue of effects to send - if (sv.datagram.cursize > 0 && msg.cursize + sv.datagram.cursize <= msg.maxsize) - SZ_Write (&msg, sv.datagram.data, sv.datagram.cursize); - -// send the datagram - if (NetConn_SendUnreliableMessage (client->netconnection, &msg) == -1) + if (host_client->spawned) + { + MSG_WriteByte (&msg, svc_time); + MSG_WriteFloat (&msg, sv.time); + + // add the client specific data to the datagram + SV_WriteClientdataToMessage (client, client->edict, &msg, stats); + VM_SV_WriteAutoSentStats (client, client->edict, &msg, stats); + SV_WriteEntitiesToClient (client, client->edict, &msg, stats); + + // expand packet size to allow effects to go over the rate limit + // (dropping them is FAR too ugly) + msg.maxsize = maxsize2; + + // copy the server datagram if there is space + // FIXME: put in delayed queue of effects to send + if (sv.datagram.cursize > 0 && msg.cursize + sv.datagram.cursize <= msg.maxsize) + SZ_Write (&msg, sv.datagram.data, sv.datagram.cursize); + } + else if (realtime > client->keepalivetime) { - SV_DropClient (true);// if the message couldn't send, kick off - return false; + // the player isn't totally in the game yet + // send small keepalive messages if too much time has passed + client->keepalivetime = realtime + 5; + MSG_WriteChar (&msg, svc_nop); } - return true; +// send the datagram + NetConn_SendUnreliableMessage (client->netconnection, &msg, sv.protocol); } /* @@ -1334,30 +1340,6 @@ void SV_UpdateToReliableMessages (void) } -/* -======================= -SV_SendNop - -Send a nop message without trashing or sending the accumulated client -message buffer -======================= -*/ -void SV_SendNop (client_t *client) -{ - sizebuf_t msg; - unsigned char buf[4]; - - msg.data = buf; - msg.maxsize = sizeof(buf); - msg.cursize = 0; - - MSG_WriteChar (&msg, svc_nop); - - if (NetConn_SendUnreliableMessage (client->netconnection, &msg) == -1) - SV_DropClient (true); // if the message couldn't send, kick off - client->last_message = realtime; -} - /* ======================= SV_SendClientMessages @@ -1367,6 +1349,9 @@ void SV_SendClientMessages (void) { int i, prepared = false; + if (sv.protocol == PROTOCOL_QUAKEWORLD) + Sys_Error("SV_SendClientMessages: no quakeworld support\n"); + // update frags, names, etc SV_UpdateToReliableMessages(); @@ -1384,43 +1369,13 @@ void SV_SendClientMessages (void) continue; } - if (host_client->spawned) - { - if (!prepared) - { - prepared = true; - // only prepare entities once per frame - SV_PrepareEntitiesForSending(); - } - if (!SV_SendClientDatagram (host_client)) - continue; - } - else - { - // the player isn't totally in the game yet - // send small keepalive messages if too much time has passed - // send a full message when the next signon stage has been requested - // some other message data (name changes, etc) may accumulate - // between signon stages - if (!host_client->sendsignon) - { - if (realtime - host_client->last_message > 5) - SV_SendNop (host_client); - continue; // don't send out non-signon messages - } - } - - if (host_client->netconnection->message.cursize) + if (!prepared) { - if (!NetConn_CanSendMessage (host_client->netconnection)) - continue; - - if (NetConn_SendReliableMessage (host_client->netconnection, &host_client->netconnection->message) == -1) - SV_DropClient (true); // if the message couldn't send, kick off - SZ_Clear (&host_client->netconnection->message); - host_client->last_message = realtime; - host_client->sendsignon = false; + prepared = true; + // only prepare entities once per frame + SV_PrepareEntitiesForSending(); } + SV_SendClientDatagram (host_client); } // clear muzzle flashes @@ -1718,11 +1673,15 @@ void SV_SpawnServer (const char *server) // if (sv.active) { - // Tell all the clients that the server is changing levels - SV_VM_Begin(); - MSG_WriteByte(&sv.reliable_datagram, svc_stufftext); - MSG_WriteString(&sv.reliable_datagram, "reconnect\n"); - SV_VM_End(); + client_t *client; + for (i = 0, client = svs.clients;i < svs.maxclients;i++, client++) + { + if (client->netconnection) + { + MSG_WriteByte(&client->netconnection->message, svc_stufftext); + MSG_WriteString(&client->netconnection->message, "reconnect\n"); + } + } } else { @@ -1743,8 +1702,6 @@ void SV_SpawnServer (const char *server) // // set up the new server // - Host_ClearMemory (); - memset (&sv, 0, sizeof(sv)); SV_VM_Setup(); @@ -1869,10 +1826,7 @@ void SV_SpawnServer (const char *server) } // load replacement entity file if found - entities = NULL; - if (sv_entpatch.integer) - entities = (char *)FS_LoadFile(va("maps/%s.ent", sv.name), tempmempool, true, NULL); - if (entities) + if (sv_entpatch.integer && (entities = (char *)FS_LoadFile(va("maps/%s.ent", sv.name), tempmempool, true, NULL))) { Con_Printf("Loaded maps/%s.ent\n", sv.name); PRVM_ED_LoadFromFile (entities); @@ -1974,6 +1928,8 @@ void SV_VM_CB_InitEdict(prvm_edict_t *e) // LordHavoc: for consistency set these here int num = PRVM_NUM_FOR_EDICT(e) - 1; + e->priv.server->move = false; // don't move on first frame + if (num >= 0 && num < svs.maxclients) { prvm_eval_t *val;