I have tracked down a deadlock in some code of mine using this reproducer:
if( isClient )
{
Sender sender;
Receiver receiver;
ConnectionPtr connection = Connection::create( description );
TEST( connection->connect( ));
receiver.start();
Sleep( 100 );
sender.start();
sender.join();
}
else
{
ConnectionPtr connection = Connection::create( description );
TEST( connection->listen( ));
Sender sender;
Receiver receiver;
ConnectionPtr reader = connection->accept();
receiver.start();
Sleep( 100 );
sender.start();
receiver.join();
}
I start on the same machine a server and then a client process on 127.0.0.1:1234. Both deadlock immediately in ::recv and ::send. Sender and Receiver are separate threads executing send/recv in a loop. The sockets are blocking, BSD-style TCP sockets.
When I change the order of operations to start the Sender before the Receivers, it works.
Why?