C ++中的MSMQ示例?

时间:2020-03-06 14:35:15  来源:igfitidea点击:

有人可以给我一些可行的示例,说明如何从C ++ API创建,添加消息,读取消息并销毁专用消息队列吗?我尝试了MSDN代码段,但无法使其正常运行。

谢谢

解决方案

不太确定如何创建或者销毁消息队列。 Windows应该为每个线程创建一个。

如果使用的是MFC,则任何CWinThread和CWnd派生类都有一个消息队列,可以轻松访问(使用PostMessage或者PostThreadMessage和ON_COMMAND宏)。为了使用Windows API进行类似的操作,我认为我们需要编写自己的消息泵,例如CWinApp的run方法。

MSG msg;
BOOL bRet; 
while( (bRet = GetMessage( &msg, NULL, 0, 0 )) != 0)
{ 
    if (bRet == -1)
    {
        // handle the error and possibly exit
    }
    else
    {
        TranslateMessage(&msg); 
        DispatchMessage(&msg); 
    }
}

...是MSDN文档中的示例。这是我们正在使用的吗?什么不起作用?

实际上,这是我感兴趣的代码:

#include "windows.h"
#include "mq.h"
#include "tchar.h"

HRESULT CreateMSMQQueue(
                        LPWSTR wszPathName, 
                        PSECURITY_DESCRIPTOR pSecurityDescriptor,
                        LPWSTR wszOutFormatName,
                        DWORD *pdwOutFormatNameLength
                        )
{

  // Define the maximum number of queue properties.
  const int NUMBEROFPROPERTIES = 2;

  // Define a queue property structure and the structures needed to initialize it.
  MQQUEUEPROPS   QueueProps;
  MQPROPVARIANT  aQueuePropVar[NUMBEROFPROPERTIES];
  QUEUEPROPID    aQueuePropId[NUMBEROFPROPERTIES];
  HRESULT        aQueueStatus[NUMBEROFPROPERTIES];
  HRESULT        hr = MQ_OK;

  // Validate the input parameters.
  if (wszPathName == NULL || wszOutFormatName == NULL || pdwOutFormatNameLength == NULL)
  {
    return MQ_ERROR_INVALID_PARAMETER;
  }

  DWORD cPropId = 0;
  aQueuePropId[cPropId] = PROPID_Q_PATHNAME;
  aQueuePropVar[cPropId].vt = VT_LPWSTR;
  aQueuePropVar[cPropId].pwszVal = wszPathName;
  cPropId++;

  WCHAR wszLabel[MQ_MAX_Q_LABEL_LEN] = L"Test Queue";
  aQueuePropId[cPropId] = PROPID_Q_LABEL;
  aQueuePropVar[cPropId].vt = VT_LPWSTR;
  aQueuePropVar[cPropId].pwszVal = wszLabel;
  cPropId++;

  QueueProps.cProp = cPropId;               // Number of properties
  QueueProps.aPropID = aQueuePropId;        // IDs of the queue properties
  QueueProps.aPropVar = aQueuePropVar;      // Values of the queue properties
  QueueProps.aStatus = aQueueStatus;        // Pointer to the return status

  WCHAR wszFormatNameBuffer[256];
  DWORD dwFormatNameBufferLength = sizeof(wszFormatNameBuffer)/sizeof(wszFormatNameBuffer[0]);
  hr = MQCreateQueue(pSecurityDescriptor,         // Security descriptor
                     &QueueProps,                 // Address of queue property structure
                     wszFormatNameBuffer,         // Pointer to format name buffer
                     &dwFormatNameBufferLength);  // Pointer to receive the queue's format name length

  if (hr == MQ_OK || hr == MQ_INFORMATION_PROPERTY)
  {
    if (*pdwOutFormatNameLength >= dwFormatNameBufferLength)
    {
      wcsncpy_s(wszOutFormatName, *pdwOutFormatNameLength - 1, wszFormatNameBuffer, _TRUNCATE);

      wszOutFormatName[*pdwOutFormatNameLength - 1] = L'##代码##';
      *pdwOutFormatNameLength = dwFormatNameBufferLength;
    }
    else
    {
      wprintf(L"The queue was created, but its format name cannot be returned.\n");
    }
  }
  return hr;
}

这大概会创建一个队列...但是缺少一些使它起作用的部分,这就是为什么我需要一个简单的示例来工作的原因。