⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sdpsearch.cpp

📁 Windows CE操作系统中适用的蓝牙驱动程序
💻 CPP
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this source code is subject to the terms of the Microsoft end-user
// license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
// If you did not accept the terms of the EULA, you are not authorized to use
// this source code. For a copy of the EULA, please see the LICENSE.RTF on your
// install media.
//
/**
THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND,
EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED 
WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A PARTICULAR PURPOSE.


Abstract:
	Windows CE Bluetooth application sample
    Demonstrates using the COM apis in SDP user to traverse an SDP service attribute
    response buffer.  

    This particular example shows parsing an RFCOMM channel ID out of a query.
**/

#include <windows.h>
#include <bthapi.h>
#include <initguid.h>
#include <bt_sdp.h>
#include "..\sdpcommon\sdpcommon.h"

// Sample of what a service attribute response looks like in raw form.
UCHAR szBuf[] = {0x35, 0x43, 0x35, 0x41, 0x09, 0x00, 0x01, 0x35, 0x03, 0x19, 0x11, 0x06, 0x09, 0x00, 0x04, 0x35, 0x11, 
                 0x35, 0x03, 0x19, 0x01, 0x00, 0x35, 0x05, 0x19, 0x00, 0x03, 0x08, 0x0A, 0x35, 0x03, 0x19, 0x00, 0x08, 
                 0x09, 0x00, 0x06, 0x35, 0x09, 0x09, 0x65, 0x6E, 0x09, 0x00, 0x6A, 0x09, 0x01, 0x00, 0x09, 0x00, 0x09, 
                 0x35, 0x08, 0x35, 0x06, 0x19, 0x11, 0x06, 0x09, 0x01, 0x00, 0x09, 0x01, 0x00, 0x25, 0x03, 0x46, 0x54, 0x50};

BOOL IsRfcommUuid(NodeData *pNode)  {
	if (pNode->type != SDP_TYPE_UUID)
		return FALSE;

	if (pNode->specificType == SDP_ST_UUID16)
		return (pNode->u.uuid16 == RFCOMM_PROTOCOL_UUID16);
	else if (pNode->specificType == SDP_ST_UUID32)
		return (pNode->u.uuid32 == RFCOMM_PROTOCOL_UUID16);
	else if (pNode->specificType == SDP_ST_UUID128)
		return (0 == memcmp(&RFCOMM_PROTOCOL_UUID,&pNode->u.uuid128,sizeof(GUID)));

	return FALSE;
}

BOOL GetChannel (NodeData *pChannelNode, ULONG *pulChannel) {
	if (pChannelNode->specificType == SDP_ST_UINT8)
		*pulChannel = pChannelNode->u.uint8;
	else if (pChannelNode->specificType == SDP_ST_INT8)
		*pulChannel = pChannelNode->u.int8;
	else if (pChannelNode->specificType == SDP_ST_UINT16)
		*pulChannel = pChannelNode->u.uint16;
	else if (pChannelNode->specificType == SDP_ST_INT16)
		*pulChannel = pChannelNode->u.int16;
	else if (pChannelNode->specificType == SDP_ST_UINT32)
		*pulChannel = pChannelNode->u.uint32;
	else if (pChannelNode->specificType == SDP_ST_INT32)
		*pulChannel = pChannelNode->u.int32;
	else
		return FALSE; // misformatted response.

	return TRUE;
}

int
WINAPI
WinMain(HINSTANCE hInstance,
		HINSTANCE hPrevInstance,
#ifdef UNDER_NT
		LPSTR     lpCmdLine,
#else
		LPWSTR    lpCmdLine,
#endif
		int       nCmdShow)
{
	ISdpRecord **pRecordArg;
	ISdpRecord *pRecord = NULL;
	
    ULONG ulRecords = 0;
    ULONG i,j,k;
    ULONG  ulChannelId = 0;
    BOOL   fSuccess = FALSE;

    CoInitializeEx(NULL,COINIT_MULTITHREADED);

    // Note: in real scenarios szBuf will be results from BthNsLookupServiceNext() after
    // performing a ServiweAttribute search.
	if (ERROR_SUCCESS != ServiceAndAttributeSearchParse(szBuf,sizeof(szBuf),&pRecordArg,&ulRecords))
		goto done;

	for (i = 0; i < ulRecords; i++) {
	    pRecord = pRecordArg[i];    // particular record to examine in this loop
	    CNodeDataFreeString protocolList;     // contains SDP_ATTRIB_PROTOCOL_DESCRIPTOR_LIST data, if available

		if (ERROR_SUCCESS != pRecord->GetAttribute(SDP_ATTRIB_PROTOCOL_DESCRIPTOR_LIST,&protocolList) ||
		    (protocolList.type != SDP_TYPE_CONTAINER))
		{
			continue;
		}
		
		ISdpNodeContainer *pRecordContainer = protocolList.u.container;
		DWORD cProtocols = 0;
		NodeData protocolDescriptor; // information about a specific protocol (i.e. L2CAP, RFCOMM, ...)

		pRecordContainer->GetNodeCount(&cProtocols);
		for (j = 0; j < cProtocols; j++) {
			pRecordContainer->GetNode(j,&protocolDescriptor);

			if (protocolDescriptor.type != SDP_TYPE_CONTAINER)
				continue;

			ISdpNodeContainer *pProtocolContainer = protocolDescriptor.u.container;
			DWORD cProtocolAtoms;
			pProtocolContainer->GetNodeCount(&cProtocolAtoms);

			for (k = 0; k < cProtocolAtoms; k++) {
				NodeData nodeAtom;  // individual data element, such as what protocol this is or RFCOMM channel id.

				pProtocolContainer->GetNode(k,&nodeAtom);

				if (IsRfcommUuid(&nodeAtom))  {
					if (k+1 == cProtocolAtoms) {
						// misformatted response.  Channel ID should follow RFCOMM uuid
						break;
					}
					NodeData channelID;
					pProtocolContainer->GetNode(k+1,&channelID);

					if (GetChannel(&channelID,&ulChannelId)) {
						fSuccess = TRUE;
						goto done;
					}

					break; // formatting error
				}
			}
		}
	}

done:
    for (i = 0; i < ulRecords; i++) 
		pRecordArg[i]->Release();

    CoTaskMemFree(pRecordArg);

    CoUninitialize();
	return 0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -