TCP Timers and Battery Life

Many modern processors (especially those designed specifically for mobile devices) have various power saving features. One of which is that when the processor is not being used it will go to a lower power mode. This is useful for devices with limited battery life. So it becomes important to not use processor power unnecessarily as it translates into using battery power.

As it turns out TCP/IP communications require timers for active TCP connections. This is because by spec TCP needs to calculate when to resend unacknowledged packets, figure out the RTT, and has other protocol features which need an active timer. Windows CE’s TCP/IP implementation uses several timers. The most frequently firing timer goes off every 100ms—this is the same timer that is used to resend un-ACK’ed packets, figure out when to send ACK’s, etc. To reduce power consumption Windows CE turns off the timers when there are no active TCP connections. Thus it is important for application writers to know what “active” TCP connections mean.

First, this timer is only used for the TCP protocol, UDP does not require any timers as UDP does not handle any sort of retransmissions or acknowledgements.

As for TCP “active connections” consist of connections which are connected and sending data. It does not included listening sockets. This means that servers which are listening on ports do not need timers (as there is no connection yet and no re-transmissions are required). However, once a TCP connection starts exchanging data (regardless of whether it is a server or a client) the timers will run as long as data is being exchanged—this is what I am calling an “active” connection in this context.

The 100ms timer in Windows CE’s implementation is global so having multiple “active” connections will not cause multiple timers to run. Instead as long as there is at least one “active” connection the timer will be running and shortly after the last “active” connection is closed (or becomes inactive) the timer will be stopped. It turns out that this period of time after the last “active” connection becomes inactive and the timer stopping is about 24 seconds because of implementation details of the Windows CE TCPIP stack.

So let us look at a couple of examples to illustrate the point.

Let us say a Windows CE device has a TCP server listening on a particular port (and that there are no other TCP connections on the device). At this point the 100ms timer will not be running at all.

As soon as a client connects to our server port the 100ms timer will start running. Let us say the client sends us 10 packets in quick succession and closes the connection (by sending a FIN). Once we have ACK’ed all the packets including the FIN, TCP will wait approx 24 seconds and then turn off the 100ms timer.

As another example let us say the client does the same thing once again, but after sending each packet it sleeps for 1 minute. Then the timer activity will look like the following:

When we get the SYN we’ll start the timer, it’ll continue to run and we’ll get the first packet and ACK it. At this time since we’re not sending any data (therefore we don’t need any retransmissions) and the other side is not sending any more data for another minute and we have ACK’ed the last packet sent—this connection becomes temporarily inactive. We don’t need the timer to send anything—therefore approximately 24 seconds after we have sent the ACK we will stop the timer. Once the other side sends us the 2nd packet (approx. 36 secs afterwards) we’ll restart the timer, send an ACK and turn it off approx. 24 seconds later. This will continue on until the last packet and the FIN have been ACK’ed by us.

Let us now switch the tables and give one last example. Now let us say that the server is on another machine and we have a client which is going to connect to it and send a packet sleep for one minute and do that 5 times in a row.

Assuming there are no other “active” connections, our 100ms timer will not be running. Afterwards we run our client which connected to the remote server. As soon as we send the first SYN the 100ms timer will get started. Then we’ll send our first packet and sleep. Then in a little less than 30 secs, our timers will turn off. They’ll turn on when we send our second packet and then turn off, etc until we send our last packet and FIN, and about 145 secs later the timer will turn off. You may be thinking hey where did the 145 secs come from? The answer is that since we are initiating the first FIN we eventually end up in the TIME_WAIT state for the TCP connection and have a 2 MSL timeout (2 minutes) before the connection becomes inactive. And about 24 secs later we turn off the timers. So we have 120 secs + 24 = 144 (remember these are estimate times).

A couple of things to remember is that the timings given are estimates and can vary depending on whether any packets are actually lost and retransmitted. There also you should not rely on the timers being turned off in exactly 24 seconds after the last “active” connection becomes “inactive”. It is currently implemented that way but may change—the important point is that Windows CE opportunistically turns off the TCP timers after a reasonable period of time.