bug-gnulib
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Bug-gnulib] RE: GNULib Module gettime Breaks CVS Build On Windows


From: Jim.Hyslop
Subject: [Bug-gnulib] RE: GNULib Module gettime Breaks CVS Build On Windows
Date: Wed, 12 May 2004 11:22:58 -0400

I wrote:
> BTW, I'm also experimenting with the select() workaround (to 
> overcome Sleep()'s 10 ms granularity) - just in case this is 
> another function that accepts a high-resolution input but 
> makes it lower resolution under the hood. I'll post the 
> results as soon as I have finished.

Bad news. It appears that select() will still wait about 10 milliseconds
before timing out, even if you specify 1 microsecond as the delay.

I ran my test program (below) 6 times with a 100 microsecond timeout, and
the times reported were 10.0118, 10.0125, 10.0125, 10.0124, 10.0124, and
10.0124 milliseconds. Running it with a 1 microsecond timeout had no effect
on the output.

Compiled using Visual Studio 6.0 SP3. Results were similar in both Debug (no
optimizations) and Release (default IDE optimization, "Maximize Speed").
Test machine: Intel Pentium III, 851MHz, 512MB RAM, 15GB free disk space,
Windows XP, service pack 1.

The program is written in C++, but porting it to C should be trivial.

#include <winsock2.h>
#include <process.h>
#include <iostream>

using namespace std;

void __cdecl listenerThread( void * params )
{
    bool * canFinish= (bool * )params;

    SOCKET listener, accepter;
    listener = socket( AF_INET, SOCK_STREAM, IPPROTO_TCP );

    sockaddr_in sa;

    sa.sin_addr.S_un.S_addr = inet_addr( "127.0.0.1");
    sa.sin_family = AF_INET;
    sa.sin_port = 54321;
    memset( sa.sin_zero, 0, sizeof( sa.sin_zero ) );
    bind( listener, (sockaddr *)&sa, sizeof( sa ) );
    listen( listener, SOMAXCONN );
    accepter = accept( listener, NULL, NULL );
    fd_set fd;
    FD_ZERO( &fd );
    FD_SET( accepter, &fd );
    if ( select( 0, &fd, NULL, NULL, NULL ) == -1 )
    {
        int oops = GetLastError();
        cout << "Error " << oops << " selecting" << endl;
    } else {
        char buffer[ 100 ];
        int numRecvd = recv( accepter, buffer, sizeof( buffer )-1, MSG_PEEK
);
        buffer[ numRecvd ] = 0;
        cout << "Listening thread received: " << buffer << endl;
    }
}

const int numSamples = 500;
int main( int argc, char *argv[] )
{
    WSADATA data;
    WSAStartup( MAKEWORD( 2, 2 ), &data );

    bool canFinish=false;
    _beginthread( listenerThread, 0, &canFinish );
    SOCKET sender;
    sender=socket( AF_INET, SOCK_STREAM, IPPROTO_TCP );

    sockaddr_in sa;

    sa.sin_addr.S_un.S_addr = inet_addr( "127.0.0.1");
    sa.sin_family = AF_INET;
    sa.sin_port = 54321;
    memset( sa.sin_zero, 0, sizeof( sa.sin_zero ) );
    connect( sender, (sockaddr *)&sa, sizeof( sa ) );

    fd_set fd;
    FD_ZERO( &fd );

    FILETIME ft;
    LONGLONG sleepTimes[ numSamples ];
    LONGLONG totalTime=0;
    for( int count=0; count < numSamples; ++count )
    {
        timeval timeout;
        timeout.tv_sec=0;
        timeout.tv_usec=100;
        FD_SET( sender, &fd );

        LARGE_INTEGER timeStart, timeEnd;

        QueryPerformanceCounter( &timeStart );
        select(1, &fd, NULL, NULL, &timeout );
        QueryPerformanceCounter( &timeEnd );

        sleepTimes[ count ] = timeEnd.QuadPart - timeStart.QuadPart;
        totalTime += sleepTimes[ count ];
    }

    LARGE_INTEGER frequency;

    QueryPerformanceFrequency( &frequency );
    double averageMs = (double)totalTime / numSamples * 1000 /
frequency.QuadPart;

    cout << "Average time spent in select: " << averageMs << " milliseconds"
<< endl;
    send( sender, "Hello", 6, 0 ); // unblock the other thread

}



-- 
Jim Hyslop
Senior Software Designer
Leitch Technology International Inc. (http://www.leitch.com)
Columnist, C/C++ Users Journal (http://www.cuj.com/experts)





reply via email to

[Prev in Thread] Current Thread [Next in Thread]