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

📄 ndistapi.c

📁 WinCE5.0部分核心源码
💻 C
📖 第 1 页 / 共 4 页
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// This source code is licensed under Microsoft Shared Source License
// Version 1.0 for Windows CE.
// For a copy of the license visit http://go.microsoft.com/fwlink/?LinkId=3223.
//
/*****************************************************************************
* 
*
*   @doc EX_RAS
*   ndistapi.c	Ndis TAPI utilities
*
*/


//  Include Files

#include "windows.h"
#include "ndis.h"
#include "ras.h"
#include "raserror.h"
#include "cxport.h"
#include "protocol.h"
#include "ppp.h"
#include "macp.h"
#include "unimodem.h"

void
ndisTapiProcessDevCaps(
	PNDISWAN_ADAPTER	    pAdapter,
	PNDIS_TAPI_GET_DEV_CAPS	pGetDevCaps)
//
//  This function is called after the adapter has successfully returned
//  DevCaps information. We process the returned info and add it to the
//  pDeviceInfo array for the adapter.
//
{
	DWORD                 dwDeviceID;
	LPTSTR                szDeviceName,
		                  szDeviceType,
						  szMediaName,
						  szProviderName;
	USHORT                wDeviceType;
	PNDISTAPI_DEVICE_INFO pInfo;
	UNIMODEM_INFO         *pUnimodemInfo;
	BOOL                  bIsNullModem = FALSE;

	dwDeviceID = pGetDevCaps->ulDeviceID;

	// We should never have issued a request for a deviceID that is too big
	if (dwDeviceID >= pAdapter->dwNumDevices)
	{
		RETAILMSG(1, (L"PPP: ndisTapiProcessDevCaps ERROR invalid dwDeviceID %u >= %u\n", dwDeviceID, pAdapter->dwNumDevices));
		ASSERT(FALSE);
	}
	else
	{	
		pInfo = &pAdapter->pDeviceInfo[dwDeviceID];

		// Clear existing device info, if any
		LocalFree(pInfo->pwszDeviceName);
		memset(pInfo, 0, sizeof(pInfo));

		szDeviceName = (LPTSTR)((LPBYTE)&(pGetDevCaps->LineDevCaps) + pGetDevCaps->LineDevCaps.ulLineNameOffset);
	            
		//
		//	If we are unable to otherwise determine a device type,
		//  assume it is a "modem" device.
		//
		szDeviceType = RASDT_Modem;
		wDeviceType = 0xFFFF;

		// UNIMODEM and PPTP put TSP name in the ProviderInfo area
		if (pGetDevCaps->LineDevCaps.ulProviderInfoOffset)
		{
			//
			//	ProviderInfo is of the format:
			//		MediaName\0ProviderName\0
			//
            szMediaName = (PTSTR)((PBYTE)&(pGetDevCaps->LineDevCaps)+ pGetDevCaps->LineDevCaps.ulProviderInfoOffset);
			szProviderName = szMediaName + _tcslen(szMediaName) + 1;
			if (szProviderName > (PTSTR)((PBYTE)szMediaName + pGetDevCaps->LineDevCaps.ulProviderInfoSize))
				szProviderName = NULL;

            if (_tcscmp(TEXT("UNIMODEM"), szMediaName) == 0)
			{
                // UNIMODEM device
                if (pGetDevCaps->LineDevCaps.ulDevSpecificOffset)
				{
                    pUnimodemInfo = (UNIMODEM_INFO *)((LPBYTE)&(pGetDevCaps->LineDevCaps) + pGetDevCaps->LineDevCaps.ulDevSpecificOffset);
					wDeviceType = pUnimodemInfo->wDeviceType;
                    switch (pUnimodemInfo->wDeviceType)
                    {
                    case DT_NULL_MODEM :
						bIsNullModem = TRUE;
						// FALLTHROUGH
                    case DT_IRCOMM_MODEM :
                    case DT_DYNAMIC_PORT :
                        szDeviceType = RASDT_Direct;
                        break;
                        
                    case DT_EXTERNAL_MODEM:
                    case DT_INTERNAL_MODEM:
                    case DT_PCMCIA_MODEM:
                    case DT_PARALLEL_PORT:
                    case DT_PARALLEL_MODEM:
                    case DT_DYNAMIC_MODEM :
                    default :
                        szDeviceType = RASDT_Modem;
                        break;
                    }
                }
            }
			else if (_tcsicmp(RASDT_Direct, szMediaName) == 0)
			{
				szDeviceType = RASDT_Direct;
			}
			else if (_tcsicmp(RASDT_Modem, szMediaName) == 0)
			{
				szDeviceType = RASDT_Modem;
			}
			else if (_tcsicmp(RASDT_Vpn, szMediaName) == 0)
			{
				szDeviceType = RASDT_Vpn;
				if (szProviderName && _tcsicmp(szProviderName, RASDT_PPPoE) == 0)
				{
					szDeviceType = RASDT_PPPoE;
				}
			}
        }
		pInfo->bIsNullModem = bIsNullModem;
		pInfo->pwszDeviceName = LocalAlloc(LPTR, (wcslen(szDeviceName) + 1) * sizeof(WCHAR));
		if (pInfo->pwszDeviceName)
		{
			wcscpy(pInfo->pwszDeviceName, szDeviceName);
			pInfo->pwszDeviceType = szDeviceType;
		}
	}
}

void
ndisTapiLineGetDevCapsCompleteCallback(
	PNDIS_REQUEST_BETTER	pRequest,
	PNDISWAN_ADAPTER	    pAdapter,
	NDIS_STATUS				Status)
//
//	This function is called when the miniport driver completes
//	an OID_TAPI_GET_DEV_CAPS request.
//
{
	PNDIS_TAPI_GET_DEV_CAPS	pGetDevCaps;
	DWORD                   dwDeviceID;
	DWORD                   dwNeededSize,
		                    dwExtraSize;

	DEBUGMSG(ZONE_FUNCTION, (L"PPP: +ndisTapiLineGetDevCapsCompleteCallback Status=%x\n", Status));

	pAdapter->bEnumeratingDevices = FALSE;

	if (Status != NDIS_STATUS_SUCCESS)
	{
		DEBUGMSG(ZONE_ERROR, (L"PPP: ndisTapiLineGetDevCapsCompleteCallback got Status = %x for adapter %s\n", Status, pAdapter->szAdapterName));
	}
	else
	{
		if (pRequest->Request.DATA.QUERY_INFORMATION.InformationBufferLength < sizeof(NDIS_TAPI_GET_DEV_CAPS))
		{
			DEBUGMSG(ZONE_ERROR, (L"PPP: ndisTapiGetLinkInfoCompleteCallback BufferLength too small (%u < %u)\n",
				pRequest->Request.DATA.QUERY_INFORMATION.InformationBufferLength, sizeof(NDIS_TAPI_GET_DEV_CAPS)));
		}
		else
		{
			pGetDevCaps = pRequest->Request.DATA.QUERY_INFORMATION.InformationBuffer;
			dwDeviceID = pGetDevCaps->ulDeviceID;
			dwNeededSize = pGetDevCaps->LineDevCaps.ulNeededSize;

			// Check to see if we need a bigger buffer
			if (dwNeededSize <= pGetDevCaps->LineDevCaps.ulTotalSize)
			{
				// Buffer was big enough to receive the required info
				// Extract the returned device information and add it to the adapter
				ndisTapiProcessDevCaps(pAdapter, pGetDevCaps);

				// Advance deviceID to the next device to be enumerated for the adapter
				dwDeviceID++;
				dwExtraSize = 0;
			}
			else
			{
				dwExtraSize = dwNeededSize - sizeof(LINE_DEV_CAPS);
			}

			// Issue a new request if more devices remain to be enumerated, or to retry
			// a request with bigger buffer.
			if (dwDeviceID < pAdapter->dwNumDevices)
			{
				NdisTapiIssueLineGetDevCaps(pAdapter, dwDeviceID, dwExtraSize);
			}
			else
			{
				// No more devices remain to be enumerated
				DEBUGMSG(ZONE_MAC, (L"PPP: Completed device enumeration for adapter %s\n", pAdapter->szAdapterName));
			}
		}
	}

	// Free the memory allocated for the request.
	LocalFree(pRequest->Request.DATA.QUERY_INFORMATION.InformationBuffer);

	DEBUGMSG(ZONE_FUNCTION, (TEXT("PPP: -ndisTapiLineGetDevCapsCompleteCallback\n")));
}

void
NdisTapiIssueLineGetDevCaps(
	PNDISWAN_ADAPTER pAdapter,
	DWORD            dwDeviceID,
	DWORD            dwExtraSize)
//
//  Send an asynchronous OID_TAPI_GET_DEV_CAPS request to the miniport adapter
//  to retrieve device information for the specified dwDeviceID.
//
{
	NDIS_STATUS		        Status;
	PNDIS_TAPI_GET_DEV_CAPS	pGetDevCaps;
	DWORD                   dwGetDevCapsSize;

	//
	// If we already have an OID_TAPI_GET_DEV_CAPS pending, we don't
	// need to issue a new one. When the current one completes it will
	// continue to enumerate all the devices for the adapter.
	//
	if (!pAdapter->bEnumeratingDevices)
	{
		dwGetDevCapsSize = sizeof(NDIS_TAPI_GET_DEV_CAPS) + dwExtraSize;
		pGetDevCaps = LocalAlloc(LPTR, dwGetDevCapsSize);

		if (NULL != pGetDevCaps)
		{
			pAdapter->bEnumeratingDevices = TRUE;

			pGetDevCaps->LineDevCaps.ulTotalSize = dwGetDevCapsSize - offsetof(NDIS_TAPI_GET_DEV_CAPS, LineDevCaps);

			pGetDevCaps->ulRequestID = 0;
			pGetDevCaps->ulDeviceID = dwDeviceID;
			pGetDevCaps->ulExtVersion = 0;

			PppNdisIssueRequest(&Status, 
								pAdapter,
								NdisRequestQueryInformation,
								OID_TAPI_GET_DEV_CAPS,
								pGetDevCaps,
								dwGetDevCapsSize,
								NULL,
								ndisTapiLineGetDevCapsCompleteCallback,
								pAdapter,
								NULL);
		}
	}
}

//
// To reduce the necessity of having to send 2 OID_TAPI_GET_DEV_CAPS because
// the first one doesn't have enough room for extra info, we send this many
// bytes of extra space in the initial request.
//
#define DEFAULT_GETDEVCAPS_EXTRA_BYTES	256

NDIS_STATUS
NdisTapiSetNumLineDevs(
	PNDISWAN_ADAPTER	    pAdapter,
	DWORD                   dwNumLineDevs)
//
//  This function is called to set the number of line devices owned by the adapter.
//  It is called when the OID_TAPI_PROVIDER_INITIALIZE completes to set the initial
//  number of devices, and later when a LINE_CREATE indication is received from the
//  miniport adapter to indicate that new devices have been added (e.g. inserting
//  a PCMCIA modem card).
//
{
	PNDISTAPI_DEVICE_INFO pDevInfoNew;
	NDIS_STATUS           Status = NDIS_STATUS_SUCCESS;
	DWORD                 dwFirstNewDevice;

	DEBUGMSG(ZONE_MAC, (TEXT("PPP: NdisTapiSetNumLineDevs for adapter %s to %u\n"), pAdapter->szAdapterName, pAdapter->dwNumDevices));

	dwFirstNewDevice = pAdapter->dwNumDevices;
	if (dwNumLineDevs <= dwFirstNewDevice)
	{
		DEBUGMSG(dwNumLineDevs && ZONE_WARN, (TEXT("PPP: WARNING New numLineDevs %u <= current %u for adapter %s\n"), dwNumLineDevs, dwFirstNewDevice, pAdapter->szAdapterName));
	}
	else
	{
		// Allocate memory for larger device info array.
		pDevInfoNew = pppAllocateMemory(dwNumLineDevs * sizeof(*pAdapter->pDeviceInfo));
		if (pDevInfoNew == NULL)
		{
			DEBUGMSG(ZONE_ERROR, (TEXT("PPP: ERROR Unable to allocate memory for %u LineDevs for adapter %s\n"), dwNumLineDevs, pAdapter->szAdapterName));
			Status = NDIS_STATUS_RESOURCES;
		}
		else
		{
			// Copy old array to new
			memcpy(pDevInfoNew, pAdapter->pDeviceInfo, dwFirstNewDevice * sizeof(*pAdapter->pDeviceInfo));

			// Free the old array, switch adapter to the new
			pppFreeMemory(pAdapter->pDeviceInfo, dwFirstNewDevice * sizeof(*pAdapter->pDeviceInfo));
			pAdapter->pDeviceInfo = pDevInfoNew;

			pAdapter->dwNumDevices = dwNumLineDevs;

			// Send requests to enumerate the new line devices to get name and type information
			NdisTapiIssueLineGetDevCaps(pAdapter, dwFirstNewDevice, DEFAULT_GETDEVCAPS_EXTRA_BYTES);
		}
	}
	return Status;
}

void
ndisTapiProviderInitializeCompleteCallback(
	PNDIS_REQUEST_BETTER	pRequest,
	PNDISWAN_ADAPTER	    pAdapter,
	NDIS_STATUS				Status)
//
//	This function is called when the miniport driver completes
//	an OID_TAPI_PROVIDER_INITIALIZE request.
//
{
	PNDIS_TAPI_PROVIDER_INITIALIZE	pProvInit;

	DEBUGMSG(ZONE_FUNCTION, (L"PPP: +ndisTapiProviderInitializeCompleteCallback Status=%x\n", Status));

	if (Status != NDIS_STATUS_SUCCESS)
	{
		DEBUGMSG(ZONE_ERROR, (L"PPP: ndisTapiProviderInitializeCompleteCallback got Status = %x for adapter %s\n", Status, pAdapter->szAdapterName));
	}
	else
	{
		if (pRequest->Request.DATA.QUERY_INFORMATION.InformationBufferLength < sizeof(*pProvInit))
		{
			DEBUGMSG(ZONE_ERROR, (L"PPP: ndisTapiGetLinkInfoCompleteCallback BufferLength too small (%u < %u)\n",
				pRequest->Request.DATA.QUERY_INFORMATION.InformationBufferLength, sizeof(*pProvInit)));
		}
		else
		{
			pProvInit = pRequest->Request.DATA.QUERY_INFORMATION.InformationBuffer;

			// Extract the returned device information and add it to the adapter
			DEBUGMSG (ZONE_MAC, (TEXT("PPP: AddAdapter: '%s' returned ProvID=%d NumDev=%d\n"),
				pAdapter->szAdapterName, pAdapter->dwProviderID, pAdapter->dwNumDevices));
			
			pAdapter->dwProviderID = pProvInit->ulProviderID;
			NdisTapiSetNumLineDevs(pAdapter, pProvInit->ulNumLineDevs);
		}
	}

	if (Status != NDIS_STATUS_SUCCESS)
		AdapterDelRef(pAdapter);

	// Free the memory allocated for the request.
	LocalFree(pRequest->Request.DATA.QUERY_INFORMATION.InformationBuffer);

	DEBUGMSG(ZONE_FUNCTION, (TEXT("PPP: -ndisTapiProviderInitializeCompleteCallback\n")));
}

void
NdisTapiAdapterInitialize(
	PNDISWAN_ADAPTER	pAdapter)
//
//  This function is called after we have successfully bound to a new
//  WAN miniport adapter. It gathers information from the adapter to
//  complete initialization.
//
{
	NDIS_STATUS		                Status;
	PNDIS_TAPI_PROVIDER_INITIALIZE	pProvInit;

	pProvInit = LocalAlloc (LPTR, sizeof(*pProvInit));
	if (NULL != pProvInit)
	{
		// pProvInit->ulDeviceIDBase = 0;

		PppNdisIssueRequest(&Status, 
							pAdapter,
							NdisRequestQueryInformation,
							OID_TAPI_PROVIDER_INITIALIZE,
							pProvInit,
							sizeof(*pProvInit),
							NULL,
							ndisTapiProviderInitializeCompleteCallback,
							pAdapter,
							NULL);

	}
}

/*****************************************************************************
*
*
*	@func	LPTSTR	|	TapiLineTranslateAddress |
*			Get the Dialable or Displayable format of a number
*
*	@rdesc	Returns a LPTSTR or NULL.  The caller must free this string.
*
*	@parm	DWORD	| dwDeviceID			|
*			The Device ID to use
*	@parm	DWORD	| dwCountryCode			|
*			The country code
*	@parm	LPCTSTR	| szAreaCode			|

⌨️ 快捷键说明

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