?? smsc100fd.c
字號:
//
// 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.
//
/****************************************************************
* *
* SMSC100FD Ethernet Driver for Windows CE. *
* *
****************************************************************/
#include <ndis.h>
#include "Smsc100Fd.h"
#include <Smsc100FdCommon.h>
#include <winreg.h>
#include <nkintr.h>
int glbl_tmp;
//static unsigned pVirtualRegisterBase;
//static unsigned uMultiplier;
//
// Read and Write word macros for accessing the SMSC100FD Registers
//
_inline UINT16 ReadWord(PSMSC100FD_ADAPTER pAdapter,UINT wOffset)
{
USHORT usData;
NdisReadRegisterUshort(
(PUSHORT)((pAdapter->pVirtualRegisterBase) + (wOffset*pAdapter->uMultiplier)),
&usData);
return usData;
}
_inline DWORD ReadDWord(PSMSC100FD_ADAPTER pAdapter,UINT wOffset)
{
DWORD dwData;
NdisReadRegisterUlong(
(PULONG)((pAdapter->pVirtualRegisterBase) + (wOffset*pAdapter->uMultiplier)),
&dwData);
return dwData;
};
_inline void WriteWord(PSMSC100FD_ADAPTER pAdapter,UINT wOffset, UINT16 Value)
{
NdisWriteRegisterUshort(
(PUSHORT)((pAdapter->pVirtualRegisterBase) + (wOffset*pAdapter->uMultiplier)),
Value);
}
#define SelectBank(x,Bank) WriteWord (x,BANK_SELECT, Bank)
void printregs(IN PSMSC100FD_ADAPTER pAdapter);
//
// The global Miniport driver block.
//
DRIVER_BLOCK gSmsc100FdMiniportBlock = {0};
#if DBG
DBGPARAM dpCurSettings = {
TEXT("Smsc100Fd"), {
TEXT("Errors"),TEXT("Warnings"),TEXT("Functions"),TEXT("Init"),
TEXT("Interrupts"),TEXT("Receives"),TEXT("Transmits"),TEXT("Link"),
TEXT("Undefined"),TEXT("Undefined"),TEXT("Undefined"),TEXT("Undefined"),
TEXT("Undefined"),TEXT("Undefined"),TEXT("Undefined"),TEXT("Undefined") },
ZONE_INIT_MASK | ZONE_ERROR_MASK
};
#endif
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD]
REG_VALUE_DESCR CommSmsc100FdKeyValues[] = {
{(TEXT ("DisplayName")), REG_SZ, (PBYTE)(TEXT ("SMSC100FD Ethernet Driver"))},
{(TEXT ("Group")), REG_SZ, (PBYTE)(TEXT ("NDIS"))},
{(TEXT ("ImagePath")), REG_SZ, (PBYTE)(TEXT ("Smsc100Fd.dll"))},
{NULL, 0, NULL}};
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD\Linkage]
REG_VALUE_DESCR CommSmsc100FdLinkageKeyValues[] = {
{(TEXT ("Route")), REG_MULTI_SZ, (PBYTE)(TEXT ("SMSC100FD1"))},
{NULL, 0, NULL}};
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD1]
REG_VALUE_DESCR CommSmsc100Fd1KeyValues[] = {
{(TEXT ("DisplayName")), REG_SZ, (PBYTE)(TEXT ("SMSC100FD Ethernet Driver"))},
{(TEXT ("Group")), REG_SZ, (PBYTE)(TEXT ("NDIS"))},
{(TEXT ("ImagePath")), REG_SZ, (PBYTE)(TEXT ("Smsc100Fd.dll"))},
{NULL, 0, NULL}};
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD1\Parms]
REG_VALUE_DESCR CommSmsc100Fd1ParmsKeyValues[] = {
{(TEXT ("BusNumber")), REG_SZ, (PBYTE)(TEXT ("SMSC100FD Ethernet Driver"))},
{(TEXT ("BusType")), REG_SZ, (PBYTE)(TEXT ("NDIS"))},
{NULL, 0, NULL}};
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD1\Parms\TcpIp]
REG_VALUE_DESCR CommSmsc100Fd1ParmsTcpIpKeyValues[] = {
{(TEXT ("EnableDHCP")), REG_DWORD, (PBYTE)1},
{(TEXT ("DefaultGateway")), REG_MULTI_SZ, (PBYTE)(TEXT ("0.0.0.0"))},
{(TEXT ("IpAddress")), REG_MULTI_SZ, (PBYTE)(TEXT ("0.0.0.0"))},
{(TEXT ("Subnetmask")), REG_MULTI_SZ, (PBYTE)(TEXT ("0.0.0.0"))},
{(TEXT ("WINS")), REG_MULTI_SZ, (PBYTE)(TEXT (""))},
{(TEXT ("DNS")), REG_MULTI_SZ, (PBYTE)(TEXT (""))},
{NULL, 0, NULL}};
// Values for [HKEY_LOCAL_MACHINE\Comm\SMSC100FD1\Parms\TcpIp]
REG_VALUE_DESCR CommTcpIpLinkageKeyValues[] = {
{(TEXT ("Bind")), REG_MULTI_SZ, (PBYTE)(TEXT ("SMSC100FD1"))},
{NULL, 0, NULL}};
PREG_VALUE_DESCR Values[] = {
CommSmsc100FdKeyValues,
CommSmsc100FdLinkageKeyValues,
CommSmsc100Fd1KeyValues,
CommSmsc100Fd1ParmsKeyValues,
CommSmsc100Fd1ParmsTcpIpKeyValues,
CommTcpIpLinkageKeyValues,
};
LPWSTR KeyNames[] = {
(TEXT ("Comm\\SMSC100FD")),
(TEXT ("Comm\\SMSC100FD\\Linkage")),
(TEXT ("Comm\\SMSC100FD1")),
(TEXT ("Comm\\SMSC100FD1\\Parms")),
(TEXT ("Comm\\SMSC100FD1\\Parms\\TcpIp")),
(TEXT ("Comm\\TcpIp\\Linkage")),
};
/*
* Description:
* The Install_Driver routine sets up the registry keys and values required to install this
* DLL as a Windows CE driver.
*
* Arguments:
* lpPnpId - The device's plug and play identifier string.
* An install function can use lpPnpId to set up a key HKEY_LOCAL_MACHINE\Drivers\PCMCIA\<lpPnpId> under the
* assumption that the user will continue to use the same device that generates the same plug and play
* id string. If there is a general detection method for the card, then lpPnpId can be ignored and a
* detection function can be registered under HKEY_LOCAL_MACHINE\Drivers\PCMCIA\Detect.
* lpRegPath - Buffer to contain the newly installed driver's device key under HKEY_LOCAL_MACHINE in the registry.
* Windows CE will attempt to load the the newly installed device driver upon completion of its
* Install_Driver function.
* cRegPathSize - Number of bytes in lpRegPath.
*
* Return Value:
* lpRegPath if successful, NULL for failure.
*
*/
LPWSTR
Install_Driver (LPWSTR lpPnpId, LPWSTR lpRegPath, DWORD cRegPathSize)
{
UINT uiIndex;
// NKDbgPrintfW (L"SMSC100FD: Install_Driver\r\n");
DEBUGMSG (ZONE_INIT, (TEXT ("+SMSC100FD: Install_Driver (%s, %s, %d)\r\n"), lpPnpId, lpRegPath, cRegPathSize));
for (uiIndex = 0; uiIndex < (sizeof (KeyNames) / sizeof (LPWSTR)); uiIndex++)
{
if (!AddKeyValues (KeyNames[uiIndex], Values[uiIndex]))
{
//
// Clean up after failure.
//
for (uiIndex = 0; uiIndex < (sizeof (KeyNames) / sizeof (LPWSTR)); uiIndex++)
RegDeleteKey (HKEY_LOCAL_MACHINE, KeyNames[uiIndex]);
DEBUGMSG (ZONE_INIT, (TEXT ("-SMSC100FD: Install_Driver: Failed\r\n")));
return (NULL);
}
}
//
// Return "HKEY_LOCAL_MACHINE\Drivers\SMSC100FD"
//
wcscpy (lpRegPath, KeyNames[0]);
DEBUGMSG (ZONE_INIT, (TEXT ("-SMSC100FD: Install_Driver: Success\r\n")));
return (lpRegPath);
}
/*
* Description:
* Add the specified key and its values to the registry under HKEY_LOCAL_MACHINE
*
* Arguments:
* KeyName - The key name under HKLM.
* Vals - The kays values.
*
* Return Value:
* TRUE if successful, else FALSE.
*
*/
BOOL
AddKeyValues (LPWSTR KeyName, PREG_VALUE_DESCR Vals)
{
DWORD Status;
DWORD dwDisp;
HKEY hKey;
PREG_VALUE_DESCR pValue;
DWORD ValLen;
PBYTE pVal;
DWORD dwVal;
LPWSTR pStr;
Status = RegCreateKeyEx (HKEY_LOCAL_MACHINE, KeyName, 0, NULL, REG_OPTION_NON_VOLATILE, 0, NULL, &hKey, &dwDisp);
if (Status != ERROR_SUCCESS)
return (FALSE);
pValue = Vals;
while (pValue->val_name)
{
switch (pValue->val_type)
{
case REG_DWORD:
pVal = (PBYTE)&dwVal;
dwVal = (DWORD)pValue->val_data;
ValLen = sizeof (DWORD);
break;
case REG_SZ:
pVal = (PBYTE)pValue->val_data;
ValLen = (wcslen ((LPWSTR)pVal) + 1) * sizeof (WCHAR);
break;
case REG_MULTI_SZ:
dwVal = wcslen ((LPWSTR)pValue->val_data);
ValLen = (dwVal + 2) * sizeof (WCHAR);
pVal = LocalAlloc (LPTR, ValLen);
if (pVal == NULL)
{
RegCloseKey (hKey);
return (FALSE);
}
wcscpy ((LPWSTR)pVal, (LPWSTR)pValue->val_data);
pStr = (LPWSTR)pVal + dwVal;
pStr[1] = 0;
break;
}
Status = RegSetValueEx (hKey, pValue->val_name, 0, pValue->val_type, pVal, ValLen);
if (pValue->val_type == REG_MULTI_SZ)
LocalFree (pVal);
if (Status != ERROR_SUCCESS)
{
RegCloseKey (hKey);
return (FALSE);
}
pValue++;
}
RegCloseKey (hKey);
return (TRUE);
}
/*
* Description:
* Standard Windows DLL entrypoint.
*
* Arguments:
* hDLL - Handle to the DLL.
* dwReason - Reason for DllEntry call.
* lpReserved - Reserved.
*
* Return Value:
* TRUE.
*
*/
BOOL __stdcall
DllEntry (HANDLE hDLL, DWORD dwReason, LPVOID lpReserved)
{
DEBUGMSG (ZONE_FUNCTION, (TEXT ("+SMSC100FD: DllEntry\r\n")));
switch (dwReason)
{
case DLL_PROCESS_ATTACH:
DEBUGREGISTER (hDLL);
DEBUGMSG (ZONE_INIT, (TEXT (" SMSC100FD: DLL_PROCESS_ATTACH\r\n")));
DisableThreadLibraryCalls((HMODULE) hDLL);
break;
case DLL_PROCESS_DETACH:
DEBUGMSG (ZONE_INIT, (TEXT (" SMSC100FD: DLL_PROCESS_DETACH\r\n")));
break;
}
DEBUGMSG (ZONE_FUNCTION, (TEXT ("-SMSC100FD: DllEntry\r\n")));
return (TRUE);
}
//
// List of supported OID for this the SMSC100FD driver.
//
static UINT Smsc100FdSupportedOids[] = {
OID_GEN_SUPPORTED_LIST,
OID_GEN_HARDWARE_STATUS,
OID_GEN_MEDIA_SUPPORTED,
OID_GEN_MEDIA_IN_USE,
OID_GEN_MAXIMUM_LOOKAHEAD,
OID_GEN_MAXIMUM_FRAME_SIZE,
OID_GEN_MAXIMUM_TOTAL_SIZE,
OID_GEN_MAC_OPTIONS,
OID_GEN_PROTOCOL_OPTIONS,
OID_GEN_LINK_SPEED,
OID_GEN_TRANSMIT_BUFFER_SPACE,
OID_GEN_RECEIVE_BUFFER_SPACE,
OID_GEN_TRANSMIT_BLOCK_SIZE,
OID_GEN_RECEIVE_BLOCK_SIZE,
OID_GEN_VENDOR_DESCRIPTION,
OID_GEN_VENDOR_ID,
OID_GEN_DRIVER_VERSION,
OID_GEN_CURRENT_PACKET_FILTER,
OID_GEN_CURRENT_LOOKAHEAD,
OID_GEN_XMIT_OK,
OID_GEN_RCV_OK,
OID_GEN_XMIT_ERROR,
OID_GEN_RCV_ERROR,
OID_GEN_RCV_NO_BUFFER,
OID_802_3_PERMANENT_ADDRESS,
OID_802_3_CURRENT_ADDRESS,
OID_802_3_MULTICAST_LIST,
OID_802_3_MAXIMUM_LIST_SIZE,
OID_802_3_RCV_ERROR_ALIGNMENT,
OID_802_3_XMIT_ONE_COLLISION,
#ifndef UNDER_CE
OID_802_3_XMIT_MORE_COLLISIONS
#else
OID_802_3_XMIT_MORE_COLLISIONS,
OID_GEN_MEDIA_CONNECT_STATUS,
OID_GEN_MAXIMUM_SEND_PACKETS,
OID_GEN_VENDOR_DRIVER_VERSION
#endif
};
/*
* Description:
* The Smsc100FdQueryInformation processes a Query request for NDIS_OIDs that are specific to the Driver.
*
* Arguments:
* hMiniportAdapterContext - A pointer to the adapter.
* Oid - The NDIS_OID to process.
* InformationBuffer - A pointer to where to put the result of the query.
* InformationBufferLength - A pointer to the number of bytes left in the InformationBuffer.
* BytesWritten - A pointer to the number of bytes written into the InformationBuffer.
* BytesNeeded - If there is not enough room in the information buffer then this will contain the number
* of bytes needed to complete the request.
*
* Return Value:
* The status of the operation.
*
*/
NDIS_STATUS
Smsc100FdQueryInformation (IN NDIS_HANDLE hMiniportAdapterContext, IN NDIS_OID Oid, IN PVOID pInformationBuffer, IN ULONG ulInformationBufferLength, OUT PULONG pulBytesWritten, OUT PULONG pulBytesNeeded)
{
//
// Pointer to the adapter structure.
//
PSMSC100FD_ADAPTER pAdapter = (PSMSC100FD_ADAPTER)(hMiniportAdapterContext);
//
// General Algorithm:
//
// Switch(Request)
// Get requested information
// Store results in a common variable.
// default:
// Try protocol query information
// If that fails, fail query.
//
// Copy result in common variable to result buffer.
// Finish processing
NDIS_STATUS StatusToReturn = NDIS_STATUS_SUCCESS;
NDIS_HARDWARE_STATUS HardwareStatus = NdisHardwareStatusReady;
NDIS_MEDIUM Medium = NdisMedium802_3;
UCHAR VendorString[] = "SMSC91C100FD Ethernet Controller.";
//
// These variables holds the result of the query
//
ULONG ulGeneric;
USHORT usGeneric;
UCHAR ucGenericArray[6];
ULONG ulMoveBytes = sizeof (ULONG);
PVOID pMoveSource = (PVOID)(&ulGeneric);
DEBUGMSG (ZONE_FUNCTION, (TEXT ("+SMSC100FD: QueryInformation OID = 0x%x pAdapter = 0x%x hMiniportAdapterContext = 0x%x\r\n"), Oid, pAdapter, hMiniportAdapterContext));
//
// Make sure that an int is 4 bytes. Else GenericULong must change
// to something of size 4.
//
ASSERT(sizeof (ULONG) == 4);
//
// Switch on request type
//
switch (Oid)
{
case OID_GEN_MAC_OPTIONS:
ulGeneric = (ULONG)(NDIS_MAC_OPTION_TRANSFERS_NOT_PEND | NDIS_MAC_OPTION_RECEIVE_SERIALIZED | NDIS_MAC_OPTION_COPY_LOOKAHEAD_DATA | NDIS_MAC_OPTION_NO_LOOPBACK);
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -