File descriptors across threads.

I am running MSVC++ 6.0 (sp3) on WinNT 4.0ws (sp5).

I am trying to create a some basic concurrent server-client functionality. I have ported code from a unix platform and managed to get it compiled with a little giggery-pokery, but I have a painful bug.

The server side calls runBasicServer() with some params. This spawns a thread (with CreateThread()) and then starts a listener, socket(), bind(), listen(), select(). This is fine and it sees connection requests, and then spawns off another thread to handle the connection via a passed function pointer. The first thing I do, is do a read, since it is non-blocking, i expect a zero to come back from read(). Nope, I get a -1. This is an error so the server disconnects, and thats it.

On the client side, I use a runBasicClient() this connects and then spawns a thread to run the passed client function. THe first thing I do is a write, expecting the number of bytes I wrote... -1... error, client quits.

Because of the server functioning partly correctly, I am assuming the CreateThread does not allow the passing of file descriptors over the thread boundary? I can't seem to find this documented, but it does seem reminiscent somewhere.

How do I use CreateThread() or similar to allow the open file descriptors to be inherited by the child thread?

Worst case, I could spawn the client earlier not providing a status, but I really do want a concurrent server.
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

Socket descriptors cam be passed over thread boundaries (doing this a lot).

The following sample (though it's using a 3rd party library) illustrates how to do it:

ULONG   __stdcall   SockLibCommThread         (   LPVOID)
    HANDLE  hThread =   NULL;
    DWORD   dwTID;

    TSocket sSrvSock    =   SOCK_ERR;
    TSocket sClntSock   =   SOCK_ERR;

    SockLibSetService   (   _SERVICE_NAME);

    if  (   SOCK_ERR    ==  (   sSrvSock    =   SockLibListenSock ()))

            SockLibPrintErrorStack  (   stdout);

            return  (   -1);

    while   (   TRUE)
                sClntSock   =   SockLibWaitForConnectingSock    (   sSrvSock);

                if  (   SOCK_ERR    ==  sClntSock)

                if  (   hThread)
                        WaitForSingleObject (   hThread,    INFINITE);

                hThread =   CreateThread    (   NULL,
                                                ( LPVOID) sClntSock,


    SockLibCloseSock    (   sSrvSock);

    return  (   0);

ULONG   __stdcall   WorkerThread           (   LPVOID      pv)

    char*   pcBuf   =   NULL;

    TSocket sClntSock   =   ( TSocket)  pv;

    slr =   ReceiveBuffer   (   &pcBuf);

    SockLibCloseSock    (   sClntSock);

    return  (   0);

The 1st thread waits for incoming connections, and once a client connects, it spawns another thread to handle the communication.

Feel free to ask if you need more information!

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
nigel5Author Commented:
I dont doubt that you can pass objects, even CSocket type objects, but using standard integer file descriptors?

If ths is the default action, then why would a read() and write() (standard C library calls) both fail with a -1 status (this, on unix anyhow, means that the socket has been closed.), when the only thing I have done is started a new thread?
Hmm, the above 'TSocket' type is nothing but a standard integer file descriptor (no MFC, this lib is just a 'wrapper' for both Winsock and BSD).

Do both threads access the descriptor simultaneously?
Hi nigel5,

I understood your problem correctly.I faced the same problem while porting a multithreaded socket
code from Unix to NT.
Basically the problem is that read() and write() of  C Run-time on windows  should not be used for sockets.Ther are
basically meant for File IO.
You please try to change _read() and_write() to
send() and recv() and pass extra last parameter as default.
You can alternatively use ReadFile() and WriteFile() of win32 but it may introduce more code difference between Unix and Windows.

It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Microsoft Development

From novice to tech pro — start learning today.