Link to home
Start Free TrialLog in
Avatar of zoukker
zoukker

asked on

Socket Problem in Mutli-threaded Application *URGENT*

Hi guys,

I have a problem working with CSocket in a mutli-threaded application. Basically, I created my sockets in the main application, then passed the SOCKET handles to the my worker thread via my dialog class object (since CSocket objects asserts when they're passed directly to another thread).

After using the sockets in my worker thread, I want to be able to transfer the control of the sockets back to my main user interface (UI) thread. My problem lies in that after the worker thread ends and transfers the sockets back to my original UI thread, they're unable to work. ie: my sockets don't work on an OnReceive() notification anymore.


//------------- code begins --------
// defined elsewhere
HANDLE m_hSocket, m_hTCPSocket;
CSocket m_pSocket, m_pTCPSocket;


CClientDialogDlg::StartThread()
{
:
:
// my sockets are detached at this point
m_hSocket = m_pSocket->Detach();
m_hTCPSocket = m_pTCPSocket->Detach();
AfxBeginThread(WorkerThread, this);
}

UINT WorkerThread( LPVOID pParam )
{
// The follow code is a workaround the VC++ 6.0 bug (see article Q193101)
#ifndef _AFXDLL
#define _AFX_SOCK_THREAD_STATE AFX_MODULE_THREAD_STATE
#define _afxSockThreadState AfxGetModuleThreadState()

_AFX_SOCK_THREAD_STATE* pState = _afxSockThreadState;
if (pState->m_pmapSocketHandle == NULL)
pState->m_pmapSocketHandle = new CMapPtrToPtr;
if (pState->m_pmapDeadSockets == NULL)
      pState->m_pmapDeadSockets = new CMapPtrToPtr;
if (pState->m_plistSocketNotifications == NULL)
      pState->m_plistSocketNotifications = new CPtrList;
#endif
// end workaround

CClientDialogDlg* dlg = (CClientDialogDlg*) pParam;
CSocket Socket;
CSocket TCPSocket;
Socket.Attach(dlg->m_hSocket);
TCPSocket.Attach(dlg->m_hTCPSocket);
:
// Socket, TCPSocket operations
:
// WM_ATTACH_SOCKET message mapped to CClientDialogDlg::AttachSocket()
dlg->SendMessage(WM_ATTACH_SOCKET);
return 0;
}

void CClientDialogDlg::AttachSocket()
{
m_pSocket->Attach( m_hSocket );
m_pTCPSocket->Attach( m_hMmSocket );

// after this point my sockets cannot work anymore on the UI thread
}
Avatar of manlore
manlore

You must Detach again the sockes at the end of the thread.

// Socket, TCPSocket operations
:

// Detach sockets
Socket.Detach();
TCPSocket.Detach();

// WM_ATTACH_SOCKET message mapped to CClientDialogDlg::AttachSocket()
dlg->SendMessage(WM_ATTACH_SOCKET);
return 0;
}

Avatar of zoukker

ASKER

Opps, I'm terribly sorry, especially to you, manlore! I omitted the Detach() parts from my question, but not my original code...

my thread code is as follows.. but it still fails as before...

UINT WorkerThread( LPVOID pParam )
{
// The follow code is a workaround the VC++ 6.0 bug (see article Q193101)
#ifndef _AFXDLL
#define _AFX_SOCK_THREAD_STATE AFX_MODULE_THREAD_STATE
#define _afxSockThreadState AfxGetModuleThreadState()

_AFX_SOCK_THREAD_STATE* pState = _afxSockThreadState;
if (pState->m_pmapSocketHandle == NULL)
pState->m_pmapSocketHandle = new CMapPtrToPtr;
if (pState->m_pmapDeadSockets == NULL)
pState->m_pmapDeadSockets = new CMapPtrToPtr;
if (pState->m_plistSocketNotifications == NULL)
pState->m_plistSocketNotifications = new CPtrList;
#endif
// end workaround

CClientDialogDlg* dlg = (CClientDialogDlg*) pParam;
CSocket Socket;
CSocket TCPSocket;
Socket.Attach(dlg->m_hSocket);
TCPSocket.Attach(dlg->m_hTCPSocket);
:
// Socket, TCPSocket operations
:

// detach portions
Socket.Detatch()
TCPSocket.Detatch()
// WM_ATTACH_SOCKET message mapped to
CClientDialogDlg::AttachSocket()
dlg->SendMessage(WM_ATTACH_SOCKET);
return 0;
}
It might be helpful to know what you are doing with your sockets in the workerthread and the UI-thread. Tried to reproduce your problem but the
following scenario works:
UI-thread: Listen for incoming connection, accept it, start workerthread
                 and detach
Worker:    Attach, receive, and detach.
UI-thread:Attach and receive.
ASKER CERTIFIED SOLUTION
Avatar of Janvo
Janvo

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
you should only use CSockets inside a CWinThread type thread