Click here to Skip to main content
15,888,028 members
Home / Discussions / C / C++ / MFC
   

C / C++ / MFC

 
AnswerRe: code Pin
Afzaal Ahmad Zeeshan5-Feb-15 0:15
professionalAfzaal Ahmad Zeeshan5-Feb-15 0:15 
QuestionAssiging A HANDLE to a CComPtr<IStream> somestream Pin
Member 113906504-Feb-15 19:18
Member 113906504-Feb-15 19:18 
SuggestionRe: Assiging A HANDLE to a CComPtr<IStream> somestream Pin
Richard MacCutchan4-Feb-15 21:32
mveRichard MacCutchan4-Feb-15 21:32 
SuggestionMFC background color Pin
lor754-Feb-15 9:13
lor754-Feb-15 9:13 
GeneralRe: MFC background color Pin
Richard Andrew x644-Feb-15 12:21
professionalRichard Andrew x644-Feb-15 12:21 
GeneralRe: MFC background color Pin
lor754-Feb-15 20:51
lor754-Feb-15 20:51 
GeneralRe: MFC background color Pin
Richard MacCutchan4-Feb-15 21:29
mveRichard MacCutchan4-Feb-15 21:29 
QuestionExtending named server overlapped IO Pin
venkat swaminathan3-Feb-15 8:54
venkat swaminathan3-Feb-15 8:54 
I am trying to implement a service provider to connect with a hardware device. request some suggestion on my approach and ideas to implement a robust system.

Mentioned are the raised requirements
0. Receive data from other EXE process
1. To process received Q information.
2. Asynchronously send information on some failure.

TO implement the mentioned system:

1. Selected 2 named pipe (commandRecv & commandSend)
2. CommandRecv pipe will be used as "Named Pipe Server Using Overlapped" I/O"
3. commandSend pipe will be used for sending the processed information.
4. commandSend will also need to send all the async messages from service provider to connected application.


On init system will create a thread to hold connection instance of commandSend pipe.After creating thread instance commandRecv pipe will be set to overlapped I/O mode and process recieve queue information.


This is the code which i am trying to extend:

<pre>#include &lt;windows.h&gt;
#include &lt;stdio.h&gt;
#include &lt;tchar.h&gt;
//#include &lt;strsafe.h&gt;

//#include &lt;glib.h&gt;

#define CONNECTING_STATE 0
#define READING_STATE 1
#define WRITING_STATE 2
#define INSTANCES 4
#define PIPE_TIMEOUT 5000
#define BUFSIZE 4096

typedef struct
{
   OVERLAPPED oOverlap;
   HANDLE hPipeInst;
   TCHAR chRequest[BUFSIZE];
   DWORD cbRead;
   TCHAR chReply[BUFSIZE];
   DWORD cbToWrite;
   DWORD dwState;
   BOOL fPendingIO;
   int processId;
} PIPEINST, *LPPIPEINST;


typedef struct
{
char appName[256];
int processId;
}PIPEHANDSHAKE;



VOID DisconnectAndReconnect(DWORD);
BOOL ConnectToNewClient(HANDLE, LPOVERLAPPED);
VOID GetAnswerToRequest(LPPIPEINST);

PIPEINST Pipe[INSTANCES];
HANDLE hEvents[INSTANCES];

HANDLE responsePipeHandle[INSTANCES];


DWORD WINAPI InstanceThread(LPVOID);

HANDLE hPipeHandles[10];
PULONG  s;

LPTSTR lpszPipename = TEXT("\\\\.\\pipe\\mynamedpipe");
LPTSTR lpszResponsePipe = TEXT("\\\\.\\pipe\\mynamedpipe1");


//GHashTable* hash;

int responsePipeConnectionHandler(VOID)
{
   BOOL   fConnected = FALSE;
   DWORD  dwThreadId = 0;
   HANDLE hPipe = INVALID_HANDLE_VALUE, hThread = NULL;
   int cbBytesRead;
   INT threadCount=0;
   //hash = g_hash_table_new(g_str_hash, g_str_equal);
   char bufferSize[512];
   for (;;)
   {
      _tprintf( TEXT("\nPipe Server: Main thread awaiting client connection on %s\n"), lpszResponsePipe);
      hPipe = CreateNamedPipe(
    		  lpszResponsePipe,             // pipe name
          PIPE_ACCESS_DUPLEX,       // read/write access
          PIPE_TYPE_MESSAGE |       // message type pipe
          PIPE_READMODE_MESSAGE |   // message-read mode
          PIPE_WAIT,                // blocking mode
          PIPE_UNLIMITED_INSTANCES, // max. instances
          BUFSIZE,                  // output buffer size
          BUFSIZE,                  // input buffer size
          0,                        // client time-out
          NULL);                    // default security attribute

      if (hPipe == INVALID_HANDLE_VALUE)
      {
          _tprintf(TEXT("CreateNamedPipe failed, GLE=%d.\n"), GetLastError());
          return -1;
      }

      // Wait for the client to connect; if it succeeds,
      // the function returns a nonzero value. If the function
      // returns zero, GetLastError returns ERROR_PIPE_CONNECTED.

      fConnected = ConnectNamedPipe(hPipe, NULL) ?
         TRUE : (GetLastError() == ERROR_PIPE_CONNECTED);

      if(fConnected){
    	  PIPEHANDSHAKE processData;
    	  fConnected = ReadFile(
             hPipe,        // handle to pipe
             bufferSize,    // buffer to receive data
             sizeof(PIPEHANDSHAKE), // size of buffer
             &amp;cbBytesRead, // number of bytes read
             NULL);        // not overlapped I/O
          memset(&amp;processData,0,sizeof(PIPEHANDSHAKE));
          memcpy(&amp;processData,&amp;bufferSize,sizeof(PIPEHANDSHAKE));
          printf("APP Process id: %d , app name: %s",processData.processId,processData.appName);

      }

    /*  if (fConnected)
      {
         printf("Client connected, creating a processing thread.\n");

         // Create a thread for this client.
         hThread = CreateThread(
            NULL,              // no security attribute
            0,                 // default stack size
            InstanceThread,    // thread proc
            (LPVOID) hPipe,    // thread parameter
            0,                 // not suspended
            &amp;dwThreadId);      // returns thread ID

         if (hThread == NULL)
         {
            _tprintf(TEXT("CreateThread failed, GLE=%d.\n"), GetLastError());
            return -1;
         }
         else CloseHandle(hThread);
       }
      else
        // The client could not connect, so close the pipe.
         CloseHandle(hPipe);*/
   }

   return 0;
}

DWORD WINAPI InstanceThread(LPVOID lpvParam)
{
   HANDLE hHeap      = GetProcessHeap();
   TCHAR* pchRequest = (TCHAR*)HeapAlloc(hHeap, 0, BUFSIZE*sizeof(TCHAR));
   TCHAR* pchReply   = (TCHAR*)HeapAlloc(hHeap, 0, BUFSIZE*sizeof(TCHAR));

   DWORD cbBytesRead = 0, cbReplyBytes = 0, cbWritten = 0;
   BOOL fSuccess = FALSE;
   HANDLE hPipe  = NULL;

   if (lpvParam == NULL)
   {
       printf( "\nERROR - Pipe Server Failure:\n");
       printf( "   InstanceThread got an unexpected NULL value in lpvParam.\n");
       printf( "   InstanceThread exitting.\n");
       if (pchReply != NULL) HeapFree(hHeap, 0, pchReply);
       if (pchRequest != NULL) HeapFree(hHeap, 0, pchRequest);
       return (DWORD)-1;
   }

   if (pchRequest == NULL)
   {
       printf( "\nERROR - Pipe Server Failure:\n");
       printf( "   InstanceThread got an unexpected NULL heap allocation.\n");
       printf( "   InstanceThread exitting.\n");
       if (pchReply != NULL) HeapFree(hHeap, 0, pchReply);
       return (DWORD)-1;
   }

   if (pchReply == NULL)
   {
       printf( "\nERROR - Pipe Server Failure:\n");
       printf( "   InstanceThread got an unexpected NULL heap allocation.\n");
       printf( "   InstanceThread exitting.\n");
       if (pchRequest != NULL) HeapFree(hHeap, 0, pchRequest);
       return (DWORD)-1;
   }
   printf("InstanceThread created, receiving and processing messages.\n");

   hPipe = (HANDLE) lpvParam;
   while (1)
   {
      fSuccess = ReadFile(
         hPipe,        // handle to pipe
         pchRequest,    // buffer to receive data
         BUFSIZE*sizeof(TCHAR), // size of buffer
         &amp;cbBytesRead, // number of bytes read
         NULL);        // not overlapped I/O

      if (!fSuccess || cbBytesRead == 0)
      {
          if (GetLastError() == ERROR_BROKEN_PIPE)
          {
              _tprintf(TEXT("InstanceThread: client disconnected.\n"), GetLastError());
          }
          else
          {
              _tprintf(TEXT("InstanceThread ReadFile failed, GLE=%d.\n"), GetLastError());
          }
          break;
      }
      else{
    	  printf(" Recieved data in PIPE");
      }
     cbReplyBytes = (strlen(pchRequest)+1)*sizeof(TCHAR);
      fSuccess = WriteFile(
         hPipe,        // handle to pipe
         pchRequest,     // buffer to write from
         cbReplyBytes, // number of bytes to write
         &amp;cbWritten,   // number of bytes written
         NULL);        // not overlapped I/O

      if (!fSuccess || cbReplyBytes != cbWritten)
      {
          _tprintf(TEXT("InstanceThread WriteFile failed, GLE=%d.\n"), GetLastError());
          break;
      }
  }
   FlushFileBuffers(hPipe);
   DisconnectNamedPipe(hPipe);
   CloseHandle(hPipe);

   HeapFree(hHeap, 0, pchRequest);
   HeapFree(hHeap, 0, pchReply);

   printf("InstanceThread exitting.\n");
   return 1;
}


int _tmain(VOID)
{
   DWORD i, dwWait, cbRet, dwErr,hThread;
   BOOL fSuccess;
   int dwThreadId;

// The initial loop creates several instances of a named pipe
// along with an event object for each instance.  An
// overlapped ConnectNamedPipe operation is started for
// each instance.
   // Create response pipe thread
   	 hThread = CreateThread(
      NULL,              // no security attribute
      0,                 // default stack size
      responsePipeConnectionHandler,    // thread proc
      NULL,    // thread parameter
      0,                 // not suspended
      &amp;dwThreadId);      // returns thread ID


   if (hThread == NULL)
   {
       printf("Response server creation failed with %d.\n", GetLastError());
       return 0;
   }


   for (i = 0; i &lt; INSTANCES; i++)
   {

   // Create an event object for this instance.

      hEvents[i] = CreateEvent(
         NULL,    // default security attribute
         TRUE,    // manual-reset event
         TRUE,    // initial state = signaled
         NULL);   // unnamed event object

      if (hEvents[i] == NULL)
      {
         printf("CreateEvent failed with %d.\n", GetLastError());
         return 0;
      }

      Pipe[i].oOverlap.hEvent = hEvents[i];

      Pipe[i].hPipeInst = CreateNamedPipe(
         lpszPipename,            // pipe name
         PIPE_ACCESS_DUPLEX |     // read/write access
         FILE_FLAG_OVERLAPPED,    // overlapped mode
         PIPE_TYPE_MESSAGE |      // message-type pipe
         PIPE_READMODE_MESSAGE |  // message-read mode
         PIPE_WAIT,               // blocking mode
         INSTANCES,               // number of instances
         BUFSIZE*sizeof(TCHAR),   // output buffer size
         BUFSIZE*sizeof(TCHAR),   // input buffer size
         PIPE_TIMEOUT,            // client time-out
         NULL);                   // default security attributes

      if (Pipe[i].hPipeInst == INVALID_HANDLE_VALUE)
      {
         printf("CreateNamedPipe failed with %d.\n", GetLastError());
         return 0;
      }

   // Call the subroutine to connect to the new client

      Pipe[i].fPendingIO = ConnectToNewClient(
         Pipe[i].hPipeInst,
         &amp;Pipe[i].oOverlap);

      Pipe[i].dwState = Pipe[i].fPendingIO ?
         CONNECTING_STATE : // still connecting
         READING_STATE;     // ready to read
   }

   while (1)
   {
      dwWait = WaitForMultipleObjects(
         INSTANCES,    // number of event objects
         hEvents,      // array of event objects
         FALSE,        // does not wait for all
         INFINITE);    // waits indefinitely

   // dwWait shows which pipe completed the operation.

      i = dwWait - WAIT_OBJECT_0;  // determines which pipe
      if (i &lt; 0 || i &gt; (INSTANCES - 1))
      {
         printf("Index out of range.\n");
         return 0;
      }

   // Get the result if the operation was pending.

      if (Pipe[i].fPendingIO)
      {
         fSuccess = GetOverlappedResult(
            Pipe[i].hPipeInst, // handle to pipe
            &amp;Pipe[i].oOverlap, // OVERLAPPED structure
            &amp;cbRet,            // bytes transferred
            FALSE);            // do not wait

         switch (Pipe[i].dwState)
         {
         // Pending connect operation
            case CONNECTING_STATE:
               if (! fSuccess)
               {
                   printf("Error %d.\n", GetLastError());
                   return 0;
               }
               Pipe[i].dwState = READING_STATE;
               break;

         // Pending read operation
            case READING_STATE:
               if (! fSuccess || cbRet == 0)
               {
                  DisconnectAndReconnect(i);
                  continue;
               }
               Pipe[i].cbRead = cbRet;
               Pipe[i].dwState = WRITING_STATE;
               break;

         // Pending write operation
            case WRITING_STATE:
               if (! fSuccess || cbRet != Pipe[i].cbToWrite)
               {
                  DisconnectAndReconnect(i);
                  continue;
               }
               Pipe[i].dwState = READING_STATE;
               break;

            default:
            {
               printf("Invalid pipe state.\n");
               return 0;
            }
         }
      }

   // The pipe state determines which operation to do next.

      switch (Pipe[i].dwState)
      {
         case READING_STATE:
            fSuccess = ReadFile(
               Pipe[i].hPipeInst,
               Pipe[i].chRequest,
               BUFSIZE*sizeof(TCHAR),
               &amp;Pipe[i].cbRead,
               &amp;Pipe[i].oOverlap);
            if (fSuccess &amp;&amp; Pipe[i].cbRead != 0)
            {
               Pipe[i].fPendingIO = FALSE;
               Pipe[i].dwState = WRITING_STATE;
               continue;
            }
            dwErr = GetLastError();
            if (! fSuccess &amp;&amp; (dwErr == ERROR_IO_PENDING))
            {
               Pipe[i].fPendingIO = TRUE;
               continue;
            }
            DisconnectAndReconnect(i);
            break;
         case WRITING_STATE:
            GetAnswerToRequest(&amp;Pipe[i]);
            fSuccess = WriteFile(
               Pipe[i].hPipeInst,
               Pipe[i].chReply,
               Pipe[i].cbToWrite,
               &amp;cbRet,
               &amp;Pipe[i].oOverlap);
            if (fSuccess &amp;&amp; cbRet == Pipe[i].cbToWrite)
            {
               Pipe[i].fPendingIO = FALSE;
               Pipe[i].dwState = READING_STATE;
               continue;
            }
            dwErr = GetLastError();
            if (! fSuccess &amp;&amp; (dwErr == ERROR_IO_PENDING))
            {
               Pipe[i].fPendingIO = TRUE;
               continue;
            }
            DisconnectAndReconnect(i);
            break;

         default:
         {
            printf("Invalid pipe state.\n");
            return 0;
         }
      }
  }

  return 0;
}

VOID DisconnectAndReconnect(DWORD i)
{
  if (! DisconnectNamedPipe(Pipe[i].hPipeInst) )
   {
      printf("DisconnectNamedPipe failed with %d.\n", GetLastError());
   }

   Pipe[i].fPendingIO = ConnectToNewClient(
      Pipe[i].hPipeInst,
      &amp;Pipe[i].oOverlap);

   Pipe[i].dwState = Pipe[i].fPendingIO ?
      CONNECTING_STATE : // still connecting
      READING_STATE;     // ready to read
}

BOOL ConnectToNewClient(HANDLE hPipe, LPOVERLAPPED lpo)
{
   BOOL fConnected, fPendingIO = FALSE;
   fConnected = ConnectNamedPipe(hPipe, lpo);
   if (fConnected)
   {
      printf("ConnectNamedPipe failed with %d.\n", GetLastError());
      return 0;
   }

   switch (GetLastError())
   {
   // The overlapped connection in progress.
      case ERROR_IO_PENDING:
         fPendingIO = TRUE;
         break;
      case ERROR_PIPE_CONNECTED:
         if (SetEvent(lpo-&gt;hEvent))
            break;
      default:
      {
         printf("ConnectNamedPipe failed with %d.\n", GetLastError());
         return 0;
      }
   }

   return fPendingIO;
}

VOID GetAnswerToRequest(LPPIPEINST pipe)
{
   _tprintf( TEXT("[%d] %s\n"), pipe-&gt;hPipeInst, pipe-&gt;chRequest);
  // StringCchCopy( pipe-&gt;chReply, BUFSIZE, TEXT("Default answer from server") );
   strncpy(pipe-&gt;chReply, "Default answer from server",BUFSIZE);
   pipe-&gt;cbToWrite = (lstrlen(pipe-&gt;chReply)+1)*sizeof(TCHAR);
}</pre>

Current pending activities:
1. Need to get process id of the connected process. this will be mainly used for identifying the client to send response data.
   Since the system is developed under MINGW - WIN32 - server will not be able to get the process id directly by using (GetNamedPipeClientProcessId). need to form a  message structure on getting a client connection.

AnswerRe: Extending named server overlapped IO Pin
Frankie-C8-Feb-15 3:35
Frankie-C8-Feb-15 3:35 
GeneralRe: Extending named server overlapped IO Pin
venkat swaminathan8-Feb-15 17:23
venkat swaminathan8-Feb-15 17:23 
QuestionHow I can read and write dicom image via c++? Pin
ahmed088sm3-Feb-15 8:05
ahmed088sm3-Feb-15 8:05 
AnswerRe: How I can read and write dicom image via c++? Pin
jeron13-Feb-15 8:34
jeron13-Feb-15 8:34 
QuestionKeeping track of fonts, pens, device contexts, etc. Pin
Anthony Appleyard3-Feb-15 2:32
Anthony Appleyard3-Feb-15 2:32 
AnswerRe: Keeping track of fonts, pens, device contexts, etc. Pin
Richard Andrew x643-Feb-15 4:55
professionalRichard Andrew x643-Feb-15 4:55 
GeneralRe: Keeping track of fonts, pens, device contexts, etc. Pin
Anthony Appleyard3-Feb-15 5:12
Anthony Appleyard3-Feb-15 5:12 
GeneralRe: Keeping track of fonts, pens, device contexts, etc. Pin
Richard MacCutchan3-Feb-15 6:59
mveRichard MacCutchan3-Feb-15 6:59 
QuestionHow to create floating toolbar that always active in MFC application Pin
Member 111256243-Feb-15 1:38
Member 111256243-Feb-15 1:38 
QuestionA query about Visual C/C++ 2008 edition's main menu Pin
Anthony Appleyard2-Feb-15 22:09
Anthony Appleyard2-Feb-15 22:09 
AnswerRe: A query about Visual C/C++ 2008 edition's main menu Pin
Richard MacCutchan2-Feb-15 23:18
mveRichard MacCutchan2-Feb-15 23:18 
QuestionHow can I created window console application that read these: Pin
Member 1141745231-Jan-15 12:18
Member 1141745231-Jan-15 12:18 
AnswerRe: How can I created window console application that read these: Pin
Garth J Lancaster31-Jan-15 13:47
professionalGarth J Lancaster31-Jan-15 13:47 
AnswerRe: How can I created window console application that read these: Pin
Richard MacCutchan1-Feb-15 0:47
mveRichard MacCutchan1-Feb-15 0:47 
QuestionError while compiling Pin
Member 1094400430-Jan-15 19:49
Member 1094400430-Jan-15 19:49 
AnswerRe: Error while compiling Pin
pasztorpisti30-Jan-15 23:20
pasztorpisti30-Jan-15 23:20 
GeneralRe: Error while compiling Pin
Member 109440042-Feb-15 20:05
Member 109440042-Feb-15 20:05 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.