3 @brief ENet protocol functions
7 #define ENET_BUILDING_LIB 1
8 #include "enet/utility.h"
10 #include "enet/enet.h"
12 static enet_uint32 timeCurrent
;
15 enet_protocol_dispatch_incoming_commands (ENetHost
* host
, ENetEvent
* event
)
17 ENetPeer
* currentPeer
= host
-> lastServicedPeer
;
18 ENetChannel
* channel
;
24 if (currentPeer
>= & host
-> peers
[host
-> peerCount
])
25 currentPeer
= host
-> peers
;
27 switch (currentPeer
-> state
)
29 case ENET_PEER_STATE_CONNECTION_PENDING
:
30 currentPeer
-> state
= ENET_PEER_STATE_CONNECTED
;
32 event
-> type
= ENET_EVENT_TYPE_CONNECT
;
33 event
-> peer
= currentPeer
;
37 case ENET_PEER_STATE_ZOMBIE
:
38 host
-> recalculateBandwidthLimits
= 1;
40 event
-> type
= ENET_EVENT_TYPE_DISCONNECT
;
41 event
-> peer
= currentPeer
;
42 event
-> data
= currentPeer
-> disconnectData
;
44 enet_peer_reset (currentPeer
);
46 host
-> lastServicedPeer
= currentPeer
;
51 if (currentPeer
-> state
!= ENET_PEER_STATE_CONNECTED
)
54 for (channel
= currentPeer
-> channels
;
55 channel
< & currentPeer
-> channels
[currentPeer
-> channelCount
];
58 if (enet_list_empty (& channel
-> incomingReliableCommands
) &&
59 enet_list_empty (& channel
-> incomingUnreliableCommands
))
62 event
-> packet
= enet_peer_receive (currentPeer
, channel
- currentPeer
-> channels
);
63 if (event
-> packet
== NULL
)
66 event
-> type
= ENET_EVENT_TYPE_RECEIVE
;
67 event
-> peer
= currentPeer
;
68 event
-> channelID
= (enet_uint8
) (channel
- currentPeer
-> channels
);
70 host
-> lastServicedPeer
= currentPeer
;
74 } while (currentPeer
!= host
-> lastServicedPeer
);
80 enet_protocol_notify_connect (ENetHost
* host
, ENetPeer
* peer
, ENetEvent
* event
)
82 host
-> recalculateBandwidthLimits
= 1;
85 peer
-> state
= ENET_PEER_STATE_CONNECTION_PENDING
;
88 peer
-> state
= ENET_PEER_STATE_CONNECTED
;
90 event
-> type
= ENET_EVENT_TYPE_CONNECT
;
96 enet_protocol_notify_disconnect (ENetHost
* host
, ENetPeer
* peer
, ENetEvent
* event
)
98 if (peer
-> state
>= ENET_PEER_STATE_CONNECTION_PENDING
)
99 host
-> recalculateBandwidthLimits
= 1;
101 if (peer
-> state
< ENET_PEER_STATE_CONNECTED
)
102 enet_peer_reset (peer
);
105 peer
-> state
= ENET_PEER_STATE_ZOMBIE
;
108 event
-> type
= ENET_EVENT_TYPE_DISCONNECT
;
109 event
-> peer
= peer
;
112 enet_peer_reset (peer
);
117 enet_protocol_remove_sent_unreliable_commands (ENetPeer
* peer
)
119 ENetOutgoingCommand
* outgoingCommand
;
121 while (enet_list_empty (& peer
-> sentUnreliableCommands
) == 0)
123 outgoingCommand
= (ENetOutgoingCommand
*) enet_list_front (& peer
-> sentUnreliableCommands
);
125 enet_list_remove (& outgoingCommand
-> outgoingCommandList
);
127 if (outgoingCommand
-> packet
!= NULL
)
129 -- outgoingCommand
-> packet
-> referenceCount
;
131 if (outgoingCommand
-> packet
-> referenceCount
== 0)
132 enet_packet_destroy (outgoingCommand
-> packet
);
135 enet_free (outgoingCommand
);
139 static ENetProtocolCommand
140 enet_protocol_remove_sent_reliable_command (ENetPeer
* peer
, enet_uint32 reliableSequenceNumber
, enet_uint8 channelID
)
142 ENetOutgoingCommand
* outgoingCommand
;
143 ENetListIterator currentCommand
;
144 ENetProtocolCommand commandNumber
;
146 for (currentCommand
= enet_list_begin (& peer
-> sentReliableCommands
);
147 currentCommand
!= enet_list_end (& peer
-> sentReliableCommands
);
148 currentCommand
= enet_list_next (currentCommand
))
150 outgoingCommand
= (ENetOutgoingCommand
*) currentCommand
;
152 if (outgoingCommand
-> reliableSequenceNumber
== reliableSequenceNumber
&&
153 outgoingCommand
-> command
.header
.channelID
== channelID
)
157 if (currentCommand
== enet_list_end (& peer
-> sentReliableCommands
))
158 return ENET_PROTOCOL_COMMAND_NONE
;
160 commandNumber
= outgoingCommand
-> command
.header
.command
;
162 enet_list_remove (& outgoingCommand
-> outgoingCommandList
);
164 if (outgoingCommand
-> packet
!= NULL
)
166 peer
-> reliableDataInTransit
-= outgoingCommand
-> fragmentLength
;
168 -- outgoingCommand
-> packet
-> referenceCount
;
170 if (outgoingCommand
-> packet
-> referenceCount
== 0)
171 enet_packet_destroy (outgoingCommand
-> packet
);
174 enet_free (outgoingCommand
);
176 if (enet_list_empty (& peer
-> sentReliableCommands
))
177 return commandNumber
;
179 outgoingCommand
= (ENetOutgoingCommand
*) enet_list_front (& peer
-> sentReliableCommands
);
181 peer
-> nextTimeout
= outgoingCommand
-> sentTime
+ outgoingCommand
-> roundTripTimeout
;
183 return commandNumber
;
187 enet_protocol_handle_connect (ENetHost
* host
, const ENetProtocolHeader
* header
, const ENetProtocol
* command
)
190 enet_uint32 windowSize
;
191 ENetChannel
* channel
;
193 ENetPeer
* currentPeer
;
194 ENetProtocol verifyCommand
;
196 if (command
-> header
.commandLength
< sizeof (ENetProtocolConnect
))
199 channelCount
= ENET_NET_TO_HOST_32 (command
-> connect
.channelCount
);
201 if (channelCount
< ENET_PROTOCOL_MINIMUM_CHANNEL_COUNT
||
202 channelCount
> ENET_PROTOCOL_MAXIMUM_CHANNEL_COUNT
)
205 for (currentPeer
= host
-> peers
;
206 currentPeer
< & host
-> peers
[host
-> peerCount
];
209 if (currentPeer
-> state
!= ENET_PEER_STATE_DISCONNECTED
&&
210 currentPeer
-> address
.host
== host
-> receivedAddress
.host
&&
211 currentPeer
-> address
.port
== host
-> receivedAddress
.port
&&
212 currentPeer
-> challenge
== header
-> challenge
)
216 for (currentPeer
= host
-> peers
;
217 currentPeer
< & host
-> peers
[host
-> peerCount
];
220 if (currentPeer
-> state
== ENET_PEER_STATE_DISCONNECTED
)
224 if (currentPeer
>= & host
-> peers
[host
-> peerCount
])
227 currentPeer
-> state
= ENET_PEER_STATE_ACKNOWLEDGING_CONNECT
;
228 currentPeer
-> challenge
= header
-> challenge
;
229 currentPeer
-> address
= host
-> receivedAddress
;
230 currentPeer
-> outgoingPeerID
= ENET_NET_TO_HOST_16 (command
-> connect
.outgoingPeerID
);
231 currentPeer
-> incomingBandwidth
= ENET_NET_TO_HOST_32 (command
-> connect
.incomingBandwidth
);
232 currentPeer
-> outgoingBandwidth
= ENET_NET_TO_HOST_32 (command
-> connect
.outgoingBandwidth
);
233 currentPeer
-> packetThrottleInterval
= ENET_NET_TO_HOST_32 (command
-> connect
.packetThrottleInterval
);
234 currentPeer
-> packetThrottleAcceleration
= ENET_NET_TO_HOST_32 (command
-> connect
.packetThrottleAcceleration
);
235 currentPeer
-> packetThrottleDeceleration
= ENET_NET_TO_HOST_32 (command
-> connect
.packetThrottleDeceleration
);
236 currentPeer
-> channels
= (ENetChannel
*) enet_malloc (channelCount
* sizeof (ENetChannel
));
237 currentPeer
-> channelCount
= channelCount
;
239 for (channel
= currentPeer
-> channels
;
240 channel
< & currentPeer
-> channels
[channelCount
];
243 channel
-> outgoingReliableSequenceNumber
= 0;
244 channel
-> outgoingUnreliableSequenceNumber
= 0;
245 channel
-> incomingReliableSequenceNumber
= 0;
246 channel
-> incomingUnreliableSequenceNumber
= 0;
248 enet_list_clear (& channel
-> incomingReliableCommands
);
249 enet_list_clear (& channel
-> incomingUnreliableCommands
);
252 mtu
= ENET_NET_TO_HOST_16 (command
-> connect
.mtu
);
254 if (mtu
< ENET_PROTOCOL_MINIMUM_MTU
)
255 mtu
= ENET_PROTOCOL_MINIMUM_MTU
;
257 if (mtu
> ENET_PROTOCOL_MAXIMUM_MTU
)
258 mtu
= ENET_PROTOCOL_MAXIMUM_MTU
;
260 currentPeer
-> mtu
= mtu
;
262 if (host
-> outgoingBandwidth
== 0 &&
263 currentPeer
-> incomingBandwidth
== 0)
264 currentPeer
-> windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
266 currentPeer
-> windowSize
= (ENET_MIN (host
-> outgoingBandwidth
, currentPeer
-> incomingBandwidth
) /
267 ENET_PEER_WINDOW_SIZE_SCALE
) *
268 ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
270 if (currentPeer
-> windowSize
< ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
)
271 currentPeer
-> windowSize
= ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
273 if (currentPeer
-> windowSize
> ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
)
274 currentPeer
-> windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
276 if (host
-> incomingBandwidth
== 0)
277 windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
279 windowSize
= (host
-> incomingBandwidth
/ ENET_PEER_WINDOW_SIZE_SCALE
) *
280 ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
282 if (windowSize
> ENET_NET_TO_HOST_32 (command
-> connect
.windowSize
))
283 windowSize
= ENET_NET_TO_HOST_32 (command
-> connect
.windowSize
);
285 if (windowSize
< ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
)
286 windowSize
= ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
288 if (windowSize
> ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
)
289 windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
291 verifyCommand
.header
.command
= ENET_PROTOCOL_COMMAND_VERIFY_CONNECT
;
292 verifyCommand
.header
.channelID
= 0xFF;
293 verifyCommand
.header
.flags
= ENET_PROTOCOL_FLAG_ACKNOWLEDGE
;
294 verifyCommand
.header
.commandLength
= sizeof (ENetProtocolVerifyConnect
);
295 verifyCommand
.verifyConnect
.outgoingPeerID
= ENET_HOST_TO_NET_16 (currentPeer
-> incomingPeerID
);
296 verifyCommand
.verifyConnect
.mtu
= ENET_HOST_TO_NET_16 (currentPeer
-> mtu
);
297 verifyCommand
.verifyConnect
.windowSize
= ENET_HOST_TO_NET_32 (windowSize
);
298 verifyCommand
.verifyConnect
.channelCount
= ENET_HOST_TO_NET_32 (channelCount
);
299 verifyCommand
.verifyConnect
.incomingBandwidth
= ENET_HOST_TO_NET_32 (host
-> incomingBandwidth
);
300 verifyCommand
.verifyConnect
.outgoingBandwidth
= ENET_HOST_TO_NET_32 (host
-> outgoingBandwidth
);
301 verifyCommand
.verifyConnect
.packetThrottleInterval
= ENET_HOST_TO_NET_32 (currentPeer
-> packetThrottleInterval
);
302 verifyCommand
.verifyConnect
.packetThrottleAcceleration
= ENET_HOST_TO_NET_32 (currentPeer
-> packetThrottleAcceleration
);
303 verifyCommand
.verifyConnect
.packetThrottleDeceleration
= ENET_HOST_TO_NET_32 (currentPeer
-> packetThrottleDeceleration
);
305 enet_peer_queue_outgoing_command (currentPeer
, & verifyCommand
, NULL
, 0, 0);
311 enet_protocol_handle_send_reliable (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
315 if (command
-> header
.commandLength
<= sizeof (ENetProtocolSendReliable
) ||
316 command
-> header
.channelID
>= peer
-> channelCount
||
317 peer
-> state
!= ENET_PEER_STATE_CONNECTED
)
320 packet
= enet_packet_create ((const enet_uint8
*) command
+ sizeof (ENetProtocolSendReliable
),
321 command
-> header
.commandLength
- sizeof (ENetProtocolSendReliable
),
322 ENET_PACKET_FLAG_RELIABLE
);
324 enet_peer_queue_incoming_command (peer
, command
, packet
, 0);
328 enet_protocol_handle_send_unsequenced (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
331 enet_uint32 unsequencedGroup
, index
;
333 if (command
-> header
.commandLength
<= sizeof (ENetProtocolSendUnsequenced
) ||
334 command
-> header
.channelID
>= peer
-> channelCount
||
335 peer
-> state
!= ENET_PEER_STATE_CONNECTED
)
338 unsequencedGroup
= ENET_NET_TO_HOST_32 (command
-> sendUnsequenced
.unsequencedGroup
);
339 index
= unsequencedGroup
% ENET_PEER_UNSEQUENCED_WINDOW_SIZE
;
341 if (unsequencedGroup
>= peer
-> incomingUnsequencedGroup
+ ENET_PEER_UNSEQUENCED_WINDOW_SIZE
)
343 peer
-> incomingUnsequencedGroup
= unsequencedGroup
- index
;
345 memset (peer
-> unsequencedWindow
, 0, sizeof (peer
-> unsequencedWindow
));
348 if (unsequencedGroup
< peer
-> incomingUnsequencedGroup
||
349 peer
-> unsequencedWindow
[index
/ 32] & (1 << (index
% 32)))
352 peer
-> unsequencedWindow
[index
/ 32] |= 1 << (index
% 32);
355 packet
= enet_packet_create ((const enet_uint8
*) command
+ sizeof (ENetProtocolSendUnsequenced
),
356 command
-> header
.commandLength
- sizeof (ENetProtocolSendUnsequenced
),
357 ENET_PACKET_FLAG_UNSEQUENCED
);
359 enet_peer_queue_incoming_command (peer
, command
, packet
, 0);
363 enet_protocol_handle_send_unreliable (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
367 if (command
-> header
.commandLength
<= sizeof (ENetProtocolSendUnreliable
) ||
368 command
-> header
.channelID
>= peer
-> channelCount
||
369 peer
-> state
!= ENET_PEER_STATE_CONNECTED
)
372 packet
= enet_packet_create ((const enet_uint8
*) command
+ sizeof (ENetProtocolSendUnreliable
),
373 command
-> header
.commandLength
- sizeof (ENetProtocolSendUnreliable
),
376 enet_peer_queue_incoming_command (peer
, command
, packet
, 0);
380 enet_protocol_handle_send_fragment (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
382 enet_uint32 fragmentNumber
,
388 ENetChannel
* channel
;
389 ENetListIterator currentCommand
;
390 ENetIncomingCommand
* startCommand
;
392 if (command
-> header
.commandLength
<= sizeof (ENetProtocolSendFragment
) ||
393 command
-> header
.channelID
>= peer
-> channelCount
||
394 peer
-> state
!= ENET_PEER_STATE_CONNECTED
)
397 startSequenceNumber
= ENET_NET_TO_HOST_32 (command
-> sendFragment
.startSequenceNumber
);
398 fragmentNumber
= ENET_NET_TO_HOST_32 (command
-> sendFragment
.fragmentNumber
);
399 fragmentCount
= ENET_NET_TO_HOST_32 (command
-> sendFragment
.fragmentCount
);
400 fragmentOffset
= ENET_NET_TO_HOST_32 (command
-> sendFragment
.fragmentOffset
);
401 totalLength
= ENET_NET_TO_HOST_32 (command
-> sendFragment
.totalLength
);
402 fragmentLength
= command
-> header
.commandLength
- sizeof (ENetProtocolSendFragment
);
404 if (fragmentOffset
>= totalLength
||
405 fragmentOffset
+ fragmentLength
> totalLength
||
406 fragmentNumber
>= fragmentCount
)
409 channel
= & peer
-> channels
[command
-> header
.channelID
];
411 if (startSequenceNumber
<= channel
-> incomingReliableSequenceNumber
)
414 for (currentCommand
= enet_list_previous (enet_list_end (& channel
-> incomingReliableCommands
));
415 currentCommand
!= enet_list_end (& channel
-> incomingReliableCommands
);
416 currentCommand
= enet_list_previous (currentCommand
))
418 startCommand
= (ENetIncomingCommand
*) currentCommand
;
420 if (startCommand
-> command
.header
.command
== ENET_PROTOCOL_COMMAND_SEND_FRAGMENT
&&
421 startCommand
-> command
.sendFragment
.startSequenceNumber
== startSequenceNumber
)
425 if (currentCommand
== enet_list_end (& channel
-> incomingReliableCommands
))
427 ENetProtocol hostCommand
= * command
;
429 hostCommand
.header
.reliableSequenceNumber
= startSequenceNumber
;
430 hostCommand
.sendFragment
.startSequenceNumber
= startSequenceNumber
;
431 hostCommand
.sendFragment
.fragmentNumber
= fragmentNumber
;
432 hostCommand
.sendFragment
.fragmentCount
= fragmentCount
;
433 hostCommand
.sendFragment
.fragmentOffset
= fragmentOffset
;
434 hostCommand
.sendFragment
.totalLength
= totalLength
;
436 startCommand
= enet_peer_queue_incoming_command (peer
,
438 enet_packet_create (NULL
, totalLength
, ENET_PACKET_FLAG_RELIABLE
),
442 if (totalLength
!= startCommand
-> packet
-> dataLength
||
443 fragmentCount
!= startCommand
-> fragmentCount
)
446 if ((startCommand
-> fragments
[fragmentNumber
/ 32] & (1 << (fragmentNumber
% 32))) == 0)
448 -- startCommand
-> fragmentsRemaining
;
450 startCommand
-> fragments
[fragmentNumber
/ 32] |= (1 << (fragmentNumber
% 32));
452 if (fragmentOffset
+ fragmentLength
> startCommand
-> packet
-> dataLength
)
453 fragmentLength
= startCommand
-> packet
-> dataLength
- fragmentOffset
;
455 memcpy (startCommand
-> packet
-> data
+ fragmentOffset
,
456 (enet_uint8
*) command
+ sizeof (ENetProtocolSendFragment
),
462 enet_protocol_handle_ping (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
464 if (command
-> header
.commandLength
< sizeof (ENetProtocolPing
))
469 enet_protocol_handle_bandwidth_limit (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
471 if (command
-> header
.commandLength
< sizeof (ENetProtocolBandwidthLimit
))
474 peer
-> incomingBandwidth
= ENET_NET_TO_HOST_32 (command
-> bandwidthLimit
.incomingBandwidth
);
475 peer
-> outgoingBandwidth
= ENET_NET_TO_HOST_32 (command
-> bandwidthLimit
.outgoingBandwidth
);
477 if (peer
-> incomingBandwidth
== 0 &&
478 host
-> outgoingBandwidth
== 0)
479 peer
-> windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
481 peer
-> windowSize
= (ENET_MIN (peer
-> incomingBandwidth
, host
-> outgoingBandwidth
) /
482 ENET_PEER_WINDOW_SIZE_SCALE
) * ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
484 if (peer
-> windowSize
< ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
)
485 peer
-> windowSize
= ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
487 if (peer
-> windowSize
> ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
)
488 peer
-> windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
492 enet_protocol_handle_throttle_configure (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
494 if (command
-> header
.commandLength
< sizeof (ENetProtocolThrottleConfigure
))
497 peer
-> packetThrottleInterval
= ENET_NET_TO_HOST_32 (command
-> throttleConfigure
.packetThrottleInterval
);
498 peer
-> packetThrottleAcceleration
= ENET_NET_TO_HOST_32 (command
-> throttleConfigure
.packetThrottleAcceleration
);
499 peer
-> packetThrottleDeceleration
= ENET_NET_TO_HOST_32 (command
-> throttleConfigure
.packetThrottleDeceleration
);
503 enet_protocol_handle_disconnect (ENetHost
* host
, ENetPeer
* peer
, const ENetProtocol
* command
)
505 if (command
-> header
.commandLength
< sizeof (ENetProtocolDisconnect
))
508 enet_peer_reset_queues (peer
);
510 if (peer
-> state
!= ENET_PEER_STATE_CONNECTED
)
512 if (peer
-> state
== ENET_PEER_STATE_CONNECTION_PENDING
) host
-> recalculateBandwidthLimits
= 1;
514 enet_peer_reset (peer
);
517 if (command
-> header
.flags
& ENET_PROTOCOL_FLAG_ACKNOWLEDGE
)
518 peer
-> state
= ENET_PEER_STATE_ACKNOWLEDGING_DISCONNECT
;
520 peer
-> state
= ENET_PEER_STATE_ZOMBIE
;
522 peer
-> disconnectData
= command
-> disconnect
.data
;
526 enet_protocol_handle_acknowledge (ENetHost
* host
, ENetEvent
* event
, ENetPeer
* peer
, const ENetProtocol
* command
)
528 enet_uint32 roundTripTime
,
530 receivedReliableSequenceNumber
;
531 ENetProtocolCommand commandNumber
;
533 if (command
-> header
.commandLength
< sizeof (ENetProtocolAcknowledge
))
536 receivedSentTime
= ENET_NET_TO_HOST_32 (command
-> acknowledge
.receivedSentTime
);
538 if (ENET_TIME_LESS (timeCurrent
, receivedSentTime
))
541 peer
-> lastReceiveTime
= timeCurrent
;
542 peer
-> earliestTimeout
= 0;
544 roundTripTime
= ENET_TIME_DIFFERENCE (timeCurrent
, receivedSentTime
);
546 enet_peer_throttle (peer
, roundTripTime
);
548 peer
-> roundTripTimeVariance
-= peer
-> roundTripTimeVariance
/ 4;
550 if (roundTripTime
>= peer
-> roundTripTime
)
552 peer
-> roundTripTime
+= (roundTripTime
- peer
-> roundTripTime
) / 8;
553 peer
-> roundTripTimeVariance
+= (roundTripTime
- peer
-> roundTripTime
) / 4;
557 peer
-> roundTripTime
-= (peer
-> roundTripTime
- roundTripTime
) / 8;
558 peer
-> roundTripTimeVariance
+= (peer
-> roundTripTime
- roundTripTime
) / 4;
561 if (peer
-> roundTripTime
< peer
-> lowestRoundTripTime
)
562 peer
-> lowestRoundTripTime
= peer
-> roundTripTime
;
564 if (peer
-> roundTripTimeVariance
> peer
-> highestRoundTripTimeVariance
)
565 peer
-> highestRoundTripTimeVariance
= peer
-> roundTripTimeVariance
;
567 if (peer
-> packetThrottleEpoch
== 0 ||
568 ENET_TIME_DIFFERENCE(timeCurrent
, peer
-> packetThrottleEpoch
) >= peer
-> packetThrottleInterval
)
570 peer
-> lastRoundTripTime
= peer
-> lowestRoundTripTime
;
571 peer
-> lastRoundTripTimeVariance
= peer
-> highestRoundTripTimeVariance
;
572 peer
-> lowestRoundTripTime
= peer
-> roundTripTime
;
573 peer
-> highestRoundTripTimeVariance
= peer
-> roundTripTimeVariance
;
574 peer
-> packetThrottleEpoch
= timeCurrent
;
577 receivedReliableSequenceNumber
= ENET_NET_TO_HOST_32 (command
-> acknowledge
.receivedReliableSequenceNumber
);
579 commandNumber
= enet_protocol_remove_sent_reliable_command (peer
, receivedReliableSequenceNumber
, command
-> header
.channelID
);
581 switch (peer
-> state
)
583 case ENET_PEER_STATE_ACKNOWLEDGING_CONNECT
:
584 if (commandNumber
!= ENET_PROTOCOL_COMMAND_VERIFY_CONNECT
)
587 enet_protocol_notify_connect (host
, peer
, event
);
591 case ENET_PEER_STATE_DISCONNECTING
:
592 if (commandNumber
!= ENET_PROTOCOL_COMMAND_DISCONNECT
)
595 enet_protocol_notify_disconnect (host
, peer
, event
);
604 enet_protocol_handle_verify_connect (ENetHost
* host
, ENetEvent
* event
, ENetPeer
* peer
, const ENetProtocol
* command
)
607 enet_uint32 windowSize
;
610 command
-> header
.commandLength
< sizeof (ENetProtocolVerifyConnect
) ||
611 peer
-> state
!= ENET_PEER_STATE_CONNECTING
)
614 if (ENET_NET_TO_HOST_32 (command
-> verifyConnect
.channelCount
) != peer
-> channelCount
||
615 ENET_NET_TO_HOST_32 (command
-> verifyConnect
.packetThrottleInterval
) != peer
-> packetThrottleInterval
||
616 ENET_NET_TO_HOST_32 (command
-> verifyConnect
.packetThrottleAcceleration
) != peer
-> packetThrottleAcceleration
||
617 ENET_NET_TO_HOST_32 (command
-> verifyConnect
.packetThrottleDeceleration
) != peer
-> packetThrottleDeceleration
)
619 peer
-> state
= ENET_PEER_STATE_ZOMBIE
;
624 peer
-> outgoingPeerID
= ENET_NET_TO_HOST_16 (command
-> verifyConnect
.outgoingPeerID
);
626 mtu
= ENET_NET_TO_HOST_16 (command
-> verifyConnect
.mtu
);
628 if (mtu
< ENET_PROTOCOL_MINIMUM_MTU
)
629 mtu
= ENET_PROTOCOL_MINIMUM_MTU
;
631 if (mtu
> ENET_PROTOCOL_MAXIMUM_MTU
)
632 mtu
= ENET_PROTOCOL_MAXIMUM_MTU
;
634 if (mtu
< peer
-> mtu
)
637 windowSize
= ENET_NET_TO_HOST_32 (command
-> verifyConnect
.windowSize
);
639 if (windowSize
< ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
)
640 windowSize
= ENET_PROTOCOL_MINIMUM_WINDOW_SIZE
;
642 if (windowSize
> ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
)
643 windowSize
= ENET_PROTOCOL_MAXIMUM_WINDOW_SIZE
;
645 if (windowSize
< peer
-> windowSize
)
646 peer
-> windowSize
= windowSize
;
648 peer
-> incomingBandwidth
= ENET_NET_TO_HOST_32 (command
-> verifyConnect
.incomingBandwidth
);
649 peer
-> outgoingBandwidth
= ENET_NET_TO_HOST_32 (command
-> verifyConnect
.outgoingBandwidth
);
651 enet_protocol_notify_connect (host
, peer
, event
);
655 enet_protocol_handle_incoming_commands (ENetHost
* host
, ENetEvent
* event
)
657 ENetProtocolHeader
* header
;
658 ENetProtocol
* command
;
660 enet_uint8
* currentData
;
663 if (host
-> receivedDataLength
< sizeof (ENetProtocolHeader
))
666 header
= (ENetProtocolHeader
*) host
-> receivedData
;
668 header
-> peerID
= ENET_NET_TO_HOST_16 (header
-> peerID
);
669 header
-> sentTime
= ENET_NET_TO_HOST_32 (header
-> sentTime
);
671 if (header
-> peerID
== 0xFFFF)
674 if (header
-> peerID
>= host
-> peerCount
)
678 peer
= & host
-> peers
[header
-> peerID
];
680 if (peer
-> state
== ENET_PEER_STATE_DISCONNECTED
||
681 peer
-> state
== ENET_PEER_STATE_ZOMBIE
||
682 (host
-> receivedAddress
.host
!= peer
-> address
.host
&&
683 peer
-> address
.host
!= ENET_HOST_BROADCAST
) ||
684 header
-> challenge
!= peer
-> challenge
)
688 peer
-> address
.host
= host
-> receivedAddress
.host
;
689 peer
-> address
.port
= host
-> receivedAddress
.port
;
694 peer
-> incomingDataTotal
+= host
-> receivedDataLength
;
696 commandCount
= header
-> commandCount
;
697 currentData
= host
-> receivedData
+ sizeof (ENetProtocolHeader
);
699 while (commandCount
> 0 &&
700 currentData
< & host
-> receivedData
[host
-> receivedDataLength
])
702 command
= (ENetProtocol
*) currentData
;
704 if (currentData
+ sizeof (ENetProtocolCommandHeader
) > & host
-> receivedData
[host
-> receivedDataLength
])
707 command
-> header
.commandLength
= ENET_NET_TO_HOST_32 (command
-> header
.commandLength
);
709 if (command
-> header
.commandLength
<= 0 ||
710 command
-> header
.commandLength
> & host
-> receivedData
[host
-> receivedDataLength
] - currentData
)
714 currentData
+= command
-> header
.commandLength
;
716 if (peer
== NULL
&& command
-> header
.command
!= ENET_PROTOCOL_COMMAND_CONNECT
)
719 command
-> header
.reliableSequenceNumber
= ENET_NET_TO_HOST_32 (command
-> header
.reliableSequenceNumber
);
721 switch (command
-> header
.command
)
723 case ENET_PROTOCOL_COMMAND_ACKNOWLEDGE
:
724 enet_protocol_handle_acknowledge (host
, event
, peer
, command
);
728 case ENET_PROTOCOL_COMMAND_CONNECT
:
729 peer
= enet_protocol_handle_connect (host
, header
, command
);
733 case ENET_PROTOCOL_COMMAND_VERIFY_CONNECT
:
734 enet_protocol_handle_verify_connect (host
, event
, peer
, command
);
738 case ENET_PROTOCOL_COMMAND_DISCONNECT
:
739 enet_protocol_handle_disconnect (host
, peer
, command
);
743 case ENET_PROTOCOL_COMMAND_PING
:
744 enet_protocol_handle_ping (host
, peer
, command
);
748 case ENET_PROTOCOL_COMMAND_SEND_RELIABLE
:
749 enet_protocol_handle_send_reliable (host
, peer
, command
);
753 case ENET_PROTOCOL_COMMAND_SEND_UNRELIABLE
:
754 enet_protocol_handle_send_unreliable (host
, peer
, command
);
758 case ENET_PROTOCOL_COMMAND_SEND_UNSEQUENCED
:
759 enet_protocol_handle_send_unsequenced (host
, peer
, command
);
763 case ENET_PROTOCOL_COMMAND_SEND_FRAGMENT
:
764 enet_protocol_handle_send_fragment (host
, peer
, command
);
768 case ENET_PROTOCOL_COMMAND_BANDWIDTH_LIMIT
:
769 enet_protocol_handle_bandwidth_limit (host
, peer
, command
);
773 case ENET_PROTOCOL_COMMAND_THROTTLE_CONFIGURE
:
774 enet_protocol_handle_throttle_configure (host
, peer
, command
);
783 (command
-> header
.flags
& ENET_PROTOCOL_FLAG_ACKNOWLEDGE
) != 0)
785 switch (peer
-> state
)
787 case ENET_PEER_STATE_DISCONNECTING
:
790 case ENET_PEER_STATE_ACKNOWLEDGING_DISCONNECT
:
791 if (command
-> header
.command
!= ENET_PROTOCOL_COMMAND_DISCONNECT
)
795 enet_peer_queue_acknowledgement (peer
, command
, header
-> sentTime
);
802 if (event
!= NULL
&& event
-> type
!= ENET_EVENT_TYPE_NONE
)
809 enet_protocol_receive_incoming_commands (ENetHost
* host
, ENetEvent
* event
)
816 buffer
.data
= host
-> receivedData
;
817 buffer
.dataLength
= sizeof (host
-> receivedData
);
819 receivedLength
= enet_socket_receive (host
-> socket
,
820 & host
-> receivedAddress
,
824 if (receivedLength
< 0)
827 if (receivedLength
== 0)
830 host
-> receivedDataLength
= receivedLength
;
832 switch (enet_protocol_handle_incoming_commands (host
, event
))
849 enet_protocol_send_acknowledgements (ENetHost
* host
, ENetPeer
* peer
)
851 ENetProtocol
* command
= & host
-> commands
[host
-> commandCount
];
852 ENetBuffer
* buffer
= & host
-> buffers
[host
-> bufferCount
];
853 ENetAcknowledgement
* acknowledgement
;
854 ENetListIterator currentAcknowledgement
;
856 currentAcknowledgement
= enet_list_begin (& peer
-> acknowledgements
);
858 while (currentAcknowledgement
!= enet_list_end (& peer
-> acknowledgements
))
860 if (command
>= & host
-> commands
[sizeof (host
-> commands
) / sizeof (ENetProtocol
)] ||
861 buffer
>= & host
-> buffers
[sizeof (host
-> buffers
) / sizeof (ENetBuffer
)] ||
862 peer
-> mtu
- host
-> packetSize
< sizeof (ENetProtocolAcknowledge
))
865 acknowledgement
= (ENetAcknowledgement
*) currentAcknowledgement
;
867 currentAcknowledgement
= enet_list_next (currentAcknowledgement
);
869 buffer
-> data
= command
;
870 buffer
-> dataLength
= sizeof (ENetProtocolAcknowledge
);
872 host
-> packetSize
+= buffer
-> dataLength
;
874 command
-> header
.command
= ENET_PROTOCOL_COMMAND_ACKNOWLEDGE
;
875 command
-> header
.channelID
= acknowledgement
-> command
.header
.channelID
;
876 command
-> header
.flags
= 0;
877 command
-> header
.commandLength
= ENET_HOST_TO_NET_32 (sizeof (ENetProtocolAcknowledge
));
878 command
-> acknowledge
.receivedReliableSequenceNumber
= ENET_HOST_TO_NET_32 (acknowledgement
-> command
.header
.reliableSequenceNumber
);
879 command
-> acknowledge
.receivedSentTime
= ENET_HOST_TO_NET_32 (acknowledgement
-> sentTime
);
881 if (acknowledgement
-> command
.header
.command
== ENET_PROTOCOL_COMMAND_DISCONNECT
)
882 peer
-> state
= ENET_PEER_STATE_ZOMBIE
;
884 enet_list_remove (& acknowledgement
-> acknowledgementList
);
885 enet_free (acknowledgement
);
891 host
-> commandCount
= command
- host
-> commands
;
892 host
-> bufferCount
= buffer
- host
-> buffers
;
896 enet_protocol_send_unreliable_outgoing_commands (ENetHost
* host
, ENetPeer
* peer
)
898 ENetProtocol
* command
= & host
-> commands
[host
-> commandCount
];
899 ENetBuffer
* buffer
= & host
-> buffers
[host
-> bufferCount
];
900 ENetOutgoingCommand
* outgoingCommand
;
901 ENetListIterator currentCommand
;
903 currentCommand
= enet_list_begin (& peer
-> outgoingUnreliableCommands
);
905 while (currentCommand
!= enet_list_end (& peer
-> outgoingUnreliableCommands
))
907 outgoingCommand
= (ENetOutgoingCommand
*) currentCommand
;
909 if (command
>= & host
-> commands
[sizeof (host
-> commands
) / sizeof (ENetProtocol
)] ||
910 buffer
+ 1 >= & host
-> buffers
[sizeof (host
-> buffers
) / sizeof (ENetBuffer
)] ||
911 peer
-> mtu
- host
-> packetSize
< outgoingCommand
-> command
.header
.commandLength
||
912 (outgoingCommand
-> packet
!= NULL
&&
913 peer
-> mtu
- host
-> packetSize
< outgoingCommand
-> command
.header
.commandLength
+
914 outgoingCommand
-> packet
-> dataLength
))
917 currentCommand
= enet_list_next (currentCommand
);
919 if (outgoingCommand
-> packet
!= NULL
)
921 peer
-> packetThrottleCounter
+= ENET_PEER_PACKET_THROTTLE_COUNTER
;
922 peer
-> packetThrottleCounter
%= ENET_PEER_PACKET_THROTTLE_SCALE
;
924 if (peer
-> packetThrottleCounter
> peer
-> packetThrottle
)
926 -- outgoingCommand
-> packet
-> referenceCount
;
928 if (outgoingCommand
-> packet
-> referenceCount
== 0)
929 enet_packet_destroy (outgoingCommand
-> packet
);
931 enet_list_remove (& outgoingCommand
-> outgoingCommandList
);
932 enet_free (outgoingCommand
);
938 buffer
-> data
= command
;
939 buffer
-> dataLength
= outgoingCommand
-> command
.header
.commandLength
;
941 host
-> packetSize
+= buffer
-> dataLength
;
943 * command
= outgoingCommand
-> command
;
945 enet_list_remove (& outgoingCommand
-> outgoingCommandList
);
947 if (outgoingCommand
-> packet
!= NULL
)
951 buffer
-> data
= outgoingCommand
-> packet
-> data
;
952 buffer
-> dataLength
= outgoingCommand
-> packet
-> dataLength
;
954 command
-> header
.commandLength
+= buffer
-> dataLength
;
956 host
-> packetSize
+= buffer
-> dataLength
;
958 enet_list_insert (enet_list_end (& peer
-> sentUnreliableCommands
), outgoingCommand
);
961 enet_free (outgoingCommand
);
963 command
-> header
.commandLength
= ENET_HOST_TO_NET_32 (command
-> header
.commandLength
);
969 host
-> commandCount
= command
- host
-> commands
;
970 host
-> bufferCount
= buffer
- host
-> buffers
;
974 enet_protocol_check_timeouts (ENetHost
* host
, ENetPeer
* peer
, ENetEvent
* event
)
976 ENetOutgoingCommand
* outgoingCommand
;
977 ENetListIterator currentCommand
;
979 currentCommand
= enet_list_begin (& peer
-> sentReliableCommands
);
981 while (currentCommand
!= enet_list_end (& peer
-> sentReliableCommands
))
983 outgoingCommand
= (ENetOutgoingCommand
*) currentCommand
;
985 currentCommand
= enet_list_next (currentCommand
);
987 if (ENET_TIME_DIFFERENCE (timeCurrent
, outgoingCommand
-> sentTime
) < outgoingCommand
-> roundTripTimeout
)
990 if(peer
-> earliestTimeout
== 0 ||
991 ENET_TIME_LESS(outgoingCommand
-> sentTime
, peer
-> earliestTimeout
))
992 peer
-> earliestTimeout
= outgoingCommand
-> sentTime
;
994 if (peer
-> earliestTimeout
!= 0 &&
995 (ENET_TIME_DIFFERENCE(timeCurrent
, peer
-> earliestTimeout
) >= ENET_PEER_TIMEOUT_MAXIMUM
||
996 (outgoingCommand
-> roundTripTimeout
>= outgoingCommand
-> roundTripTimeoutLimit
&&
997 ENET_TIME_DIFFERENCE(timeCurrent
, peer
-> earliestTimeout
) >= ENET_PEER_TIMEOUT_MINIMUM
)))
999 enet_protocol_notify_disconnect (host
, peer
, event
);
1004 if (outgoingCommand
-> packet
!= NULL
)
1005 peer
-> reliableDataInTransit
-= outgoingCommand
-> fragmentLength
;
1007 ++ peer
-> packetsLost
;
1009 outgoingCommand
-> roundTripTimeout
*= 2;
1011 enet_list_insert (enet_list_begin (& peer
-> outgoingReliableCommands
),
1012 enet_list_remove (& outgoingCommand
-> outgoingCommandList
));
1014 if (currentCommand
== enet_list_begin (& peer
-> sentReliableCommands
) &&
1015 enet_list_empty (& peer
-> sentReliableCommands
) == 0)
1017 outgoingCommand
= (ENetOutgoingCommand
*) currentCommand
;
1019 peer
-> nextTimeout
= outgoingCommand
-> sentTime
+ outgoingCommand
-> roundTripTimeout
;
1027 enet_protocol_send_reliable_outgoing_commands (ENetHost
* host
, ENetPeer
* peer
)
1029 ENetProtocol
* command
= & host
-> commands
[host
-> commandCount
];
1030 ENetBuffer
* buffer
= & host
-> buffers
[host
-> bufferCount
];
1031 ENetOutgoingCommand
* outgoingCommand
;
1032 ENetListIterator currentCommand
;
1034 currentCommand
= enet_list_begin (& peer
-> outgoingReliableCommands
);
1036 while (currentCommand
!= enet_list_end (& peer
-> outgoingReliableCommands
))
1038 outgoingCommand
= (ENetOutgoingCommand
*) currentCommand
;
1040 if (command
>= & host
-> commands
[sizeof (host
-> commands
) / sizeof (ENetProtocol
)] ||
1041 buffer
+ 1 >= & host
-> buffers
[sizeof (host
-> buffers
) / sizeof (ENetBuffer
)] ||
1042 peer
-> mtu
- host
-> packetSize
< outgoingCommand
-> command
.header
.commandLength
)
1045 currentCommand
= enet_list_next (currentCommand
);
1047 if (outgoingCommand
-> packet
!= NULL
)
1049 if ((enet_uint16
) (peer
-> mtu
- host
-> packetSize
) <
1050 (enet_uint16
) (outgoingCommand
-> command
.header
.commandLength
+
1051 outgoingCommand
-> fragmentLength
) ||
1052 peer
-> reliableDataInTransit
+ outgoingCommand
-> fragmentLength
> peer
-> windowSize
)
1056 if (outgoingCommand
-> roundTripTimeout
== 0)
1058 outgoingCommand
-> roundTripTimeout
= peer
-> roundTripTime
+ 4 * peer
-> roundTripTimeVariance
;
1059 outgoingCommand
-> roundTripTimeoutLimit
= ENET_PEER_TIMEOUT_LIMIT
* outgoingCommand
-> roundTripTimeout
;
1062 if (enet_list_empty (& peer
-> sentReliableCommands
))
1063 peer
-> nextTimeout
= timeCurrent
+ outgoingCommand
-> roundTripTimeout
;
1065 enet_list_insert (enet_list_end (& peer
-> sentReliableCommands
),
1066 enet_list_remove (& outgoingCommand
-> outgoingCommandList
));
1068 outgoingCommand
-> sentTime
= timeCurrent
;
1070 buffer
-> data
= command
;
1071 buffer
-> dataLength
= outgoingCommand
-> command
.header
.commandLength
;
1073 host
-> packetSize
+= buffer
-> dataLength
;
1075 * command
= outgoingCommand
-> command
;
1077 if (outgoingCommand
-> packet
!= NULL
)
1081 buffer
-> data
= outgoingCommand
-> packet
-> data
+ outgoingCommand
-> fragmentOffset
;
1082 buffer
-> dataLength
= outgoingCommand
-> fragmentLength
;
1084 command
-> header
.commandLength
+= outgoingCommand
-> fragmentLength
;
1086 host
-> packetSize
+= outgoingCommand
-> fragmentLength
;
1088 peer
-> reliableDataInTransit
+= outgoingCommand
-> fragmentLength
;
1091 command
-> header
.commandLength
= ENET_HOST_TO_NET_32 (command
-> header
.commandLength
);
1093 ++ peer
-> packetsSent
;
1099 host
-> commandCount
= command
- host
-> commands
;
1100 host
-> bufferCount
= buffer
- host
-> buffers
;
1104 enet_protocol_send_outgoing_commands (ENetHost
* host
, ENetEvent
* event
, int checkForTimeouts
)
1106 size_t packetsSent
= 1;
1107 ENetProtocolHeader header
;
1108 ENetPeer
* currentPeer
;
1111 while (packetsSent
> 0)
1112 for (currentPeer
= host
-> peers
,
1114 currentPeer
< & host
-> peers
[host
-> peerCount
];
1117 if (currentPeer
-> state
== ENET_PEER_STATE_DISCONNECTED
||
1118 currentPeer
-> state
== ENET_PEER_STATE_ZOMBIE
)
1121 host
-> commandCount
= 0;
1122 host
-> bufferCount
= 1;
1123 host
-> packetSize
= sizeof (ENetProtocolHeader
);
1125 if (enet_list_empty (& currentPeer
-> acknowledgements
) == 0)
1126 enet_protocol_send_acknowledgements (host
, currentPeer
);
1128 if (host
-> commandCount
< sizeof (host
-> commands
) / sizeof (ENetProtocol
))
1130 if (checkForTimeouts
!= 0 &&
1131 enet_list_empty (& currentPeer
-> sentReliableCommands
) == 0 &&
1132 ENET_TIME_GREATER_EQUAL (timeCurrent
, currentPeer
-> nextTimeout
) &&
1133 enet_protocol_check_timeouts (host
, currentPeer
, event
) == 1)
1136 if (enet_list_empty (& currentPeer
-> outgoingReliableCommands
) == 0)
1137 enet_protocol_send_reliable_outgoing_commands (host
, currentPeer
);
1139 if (enet_list_empty (& currentPeer
-> sentReliableCommands
) &&
1140 ENET_TIME_DIFFERENCE (timeCurrent
, currentPeer
-> lastReceiveTime
) >= ENET_PEER_PING_INTERVAL
&&
1141 currentPeer
-> mtu
- host
-> packetSize
>= sizeof (ENetProtocolPing
))
1143 enet_peer_ping (currentPeer
);
1144 enet_protocol_send_reliable_outgoing_commands (host
, currentPeer
);
1147 if (host
-> commandCount
< sizeof (host
-> commands
) / sizeof (ENetProtocol
) &&
1148 enet_list_empty (& currentPeer
-> outgoingUnreliableCommands
) == 0)
1149 enet_protocol_send_unreliable_outgoing_commands (host
, currentPeer
);
1151 if (host
-> commandCount
== 0)
1154 if (currentPeer
-> packetLossEpoch
== 0)
1155 currentPeer
-> packetLossEpoch
= timeCurrent
;
1157 if (ENET_TIME_DIFFERENCE (timeCurrent
, currentPeer
-> packetLossEpoch
) >= ENET_PEER_PACKET_LOSS_INTERVAL
&&
1158 currentPeer
-> packetsSent
> 0)
1160 enet_uint32 packetLoss
= currentPeer
-> packetsLost
* ENET_PEER_PACKET_LOSS_SCALE
/ currentPeer
-> packetsSent
;
1168 "peer %u: %f%%+-%f%% packet loss, %u+-%u ms round trip time, %f%% throttle, %u/%u outgoing, %u/%u incoming\n", currentPeer
-> incomingPeerID
, currentPeer
-> packetLoss
/ (float) ENET_PEER_PACKET_LOSS_SCALE
, currentPeer
-> packetLossVariance
/ (float) ENET_PEER_PACKET_LOSS_SCALE
, currentPeer
-> roundTripTime
, currentPeer
-> roundTripTimeVariance
, currentPeer
-> packetThrottle
/ (float) ENET_PEER_PACKET_THROTTLE_SCALE
, enet_list_size (& currentPeer
-> outgoingReliableCommands
), enet_list_size (& currentPeer
-> outgoingUnreliableCommands
), currentPeer
-> channels
!= NULL
? enet_list_size (& currentPeer
-> channels
-> incomingReliableCommands
) : 0, enet_list_size (& currentPeer
-> channels
-> incomingUnreliableCommands
));
1171 currentPeer
-> packetLossVariance
-= currentPeer
-> packetLossVariance
/ 4;
1173 if (packetLoss
>= currentPeer
-> packetLoss
)
1175 currentPeer
-> packetLoss
+= (packetLoss
- currentPeer
-> packetLoss
) / 8;
1176 currentPeer
-> packetLossVariance
+= (packetLoss
- currentPeer
-> packetLoss
) / 4;
1180 currentPeer
-> packetLoss
-= (currentPeer
-> packetLoss
- packetLoss
) / 8;
1181 currentPeer
-> packetLossVariance
+= (currentPeer
-> packetLoss
- packetLoss
) / 4;
1184 currentPeer
-> packetLossEpoch
= timeCurrent
;
1185 currentPeer
-> packetsSent
= 0;
1186 currentPeer
-> packetsLost
= 0;
1189 header
.peerID
= ENET_HOST_TO_NET_16 (currentPeer
-> outgoingPeerID
);
1191 header
.commandCount
= host
-> commandCount
;
1192 header
.sentTime
= ENET_HOST_TO_NET_32 (timeCurrent
);
1193 header
.challenge
= currentPeer
-> challenge
;
1195 host
-> buffers
-> data
= & header
;
1196 host
-> buffers
-> dataLength
= sizeof (ENetProtocolHeader
);
1198 currentPeer
-> lastSendTime
= timeCurrent
;
1202 sentLength
= enet_socket_send (host
-> socket
, & currentPeer
-> address
, host
-> buffers
, host
-> bufferCount
);
1204 enet_protocol_remove_sent_unreliable_commands (currentPeer
);
1213 /** Sends any queued packets on the host specified to its designated peers.
1215 @param host host to flush
1216 @remarks this function need only be used in circumstances where one wishes to send queued packets earlier than in a call to enet_host_service().
1220 enet_host_flush (ENetHost
* host
)
1222 timeCurrent
= enet_time_get ();
1224 enet_protocol_send_outgoing_commands (host
, NULL
, 0);
1227 /** Waits for events on the host specified and shuttles packets between
1228 the host and its peers.
1230 @param host host to service
1231 @param event an event structure where event details will be placed if one occurs
1232 if event == NULL then no events will be delivered
1233 @param timeout number of milliseconds that ENet should wait for events
1234 @retval > 0 if an event occurred within the specified time limit
1235 @retval 0 if no event occurred
1236 @retval < 0 on failure
1237 @remarks enet_host_service should be called fairly regularly for adequate performance
1241 enet_host_service (ENetHost
* host
, ENetEvent
* event
, enet_uint32 timeout
)
1243 enet_uint32 waitCondition
;
1247 event
-> type
= ENET_EVENT_TYPE_NONE
;
1248 event
-> peer
= NULL
;
1249 event
-> packet
= NULL
;
1251 switch (enet_protocol_dispatch_incoming_commands (host
, event
))
1257 perror ("Error dispatching incoming packets");
1266 timeCurrent
= enet_time_get ();
1268 timeout
+= timeCurrent
;
1272 if (ENET_TIME_DIFFERENCE (timeCurrent
, host
-> bandwidthThrottleEpoch
) >= ENET_HOST_BANDWIDTH_THROTTLE_INTERVAL
)
1273 enet_host_bandwidth_throttle (host
);
1275 switch (enet_protocol_send_outgoing_commands (host
, event
, 1))
1281 perror ("Error sending outgoing packets");
1289 switch (enet_protocol_receive_incoming_commands (host
, event
))
1295 perror ("Error receiving incoming packets");
1303 switch (enet_protocol_send_outgoing_commands (host
, event
, 1))
1309 perror ("Error sending outgoing packets");
1319 switch (enet_protocol_dispatch_incoming_commands (host
, event
))
1325 perror ("Error dispatching incoming packets");
1334 timeCurrent
= enet_time_get ();
1336 if (ENET_TIME_GREATER_EQUAL (timeCurrent
, timeout
))
1339 waitCondition
= ENET_SOCKET_WAIT_RECEIVE
;
1341 if (enet_socket_wait (host
-> socket
, & waitCondition
, ENET_TIME_DIFFERENCE (timeout
, timeCurrent
)) != 0)
1344 timeCurrent
= enet_time_get ();
1345 } while (waitCondition
== ENET_SOCKET_WAIT_RECEIVE
);