You are here

TutorialLibraryTest ApplicationDownload
[Tutorial]LibraryTest ApplicationDownload

Error message

Deprecated function: The each() function is deprecated. This message will be suppressed on further calls in menu_set_active_trail() (line 2404 of /home/quantics/public_html/dp/includes/menu.inc).

Socket Tutorial

Chapter 9 - Accepting a connection request

C_SCP::Accept (int waitTime_ms, unsigned int *pIDLink)

This function waits up to waitTime_ms milliseconds to accept a new connection request. A negative value for this parameter means the function can potentially wait infinitely (blocking mode), while 0 means the function performs a query and returns immediately (non-blocking mode). In any case, the function returns immediately if a customer was already waiting. If successful, a new socket is created and the link identifier is written to the parameter pIDLink. This is not the identifier of the new socket (which is hidden), but rather a value to use with other library functions to identify the link.

Along with the local variables declaration, the time at which the user enters the function (t1) is stored.

S_Error er;
sockaddr addr;
unsigned long arg;
int r;
int newSock;
unsigned int i, t1, t2;
timeval tv;
fd_set fdset;

t1 = GetTime_tick ();

Then, the function sets the listening socket in non-blocking mode using the method that was illustrated in Chapter 3.

r = Sock_SetBlockMode (w_listenSock, false);

Structure fdset is then filled with a unique listening socket identifier. Current time (t2) is stored to calculate the time left tv. From there, function select can be called to wait for the listening socket to become available for reading. If waitTime_ms is smaller than 0, then function select is called with a zeroed timeval structure. Otherwise, the fields tv_sec and tv_usec are filled to convert the time left into a number of seconds and microseconds.

FD_ZERO (&fdset);
FD_SET (w_listenSock, &fdset);
t2 = GetTime_tick ();

if (waitTime_ms >= 0) 
{
   if ((unsigned int) waitTime_ms > (t2-t1))
   {
      tv.tv_sec = (waitTime_ms  - (t2-t1) ) / 1000;
      tv.tv_usec = ( (waitTime_ms - (t2-t1))  % 1000) * 1000;
   }
   else
   {
      tv.tv_sec = 0;
      tv.tv_usec = 0;
   }

   r = select (w_listenSock +1, &fdset, NULL, NULL, &tv);
}
else
   r = select (w_listenSock +1, &fdset, NULL, NULL, NULL);

// Timeout expired
if (r == 0) 
{

   (...)
   return er;
}

If function select returns a positive result, then it means that a customer has made ​​a connection request and it is most likely that calling accept will be successful. Otherwise, nothing happened during the allowed time frame and function must give back hand. The last step is to call accept and verify that it still does not fail.

newSock = accept (w_listenSock, &addr, &addrlen);

if (newSock == INVALID_SOCKET)
{
   (...)
   return er;
}