mirror of https://github.com/lianthony/NT4.0
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
878 lines
16 KiB
878 lines
16 KiB
/*++
|
|
|
|
Copyright (c) 1992 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
detmca.c
|
|
|
|
Abstract:
|
|
|
|
This is the main file for the autodetection DLL for all the mca adapters
|
|
which MS is shipping with Windows NT.
|
|
|
|
Author:
|
|
|
|
Sean Selitrennikoff (SeanSe) October 1992.
|
|
|
|
Environment:
|
|
|
|
|
|
Revision History:
|
|
|
|
|
|
--*/
|
|
|
|
#include <nt.h>
|
|
#include <ntrtl.h>
|
|
#include <nturtl.h>
|
|
|
|
#include <windows.h>
|
|
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
#include "ntddnetd.h"
|
|
#include "detect.h"
|
|
|
|
//
|
|
// Helper functions
|
|
//
|
|
|
|
ULONG
|
|
FindMcaCard(
|
|
IN ULONG AdapterNumber,
|
|
IN ULONG BusNumber,
|
|
IN BOOLEAN fFirst,
|
|
OUT PULONG lConfidence
|
|
);
|
|
|
|
//
|
|
// Structure for holding a particular adapter's complete information
|
|
//
|
|
typedef struct _MCA_ADAPTER_INFO
|
|
{
|
|
LONG Index;
|
|
PWCHAR InfId;
|
|
ULONG PosId;
|
|
ULONG PosMask;
|
|
PWCHAR Parameters;
|
|
NC_DETECT_FIRST_NEXT FirstNext;
|
|
|
|
ULONG BusNumber;
|
|
ULONG SlotNumber;
|
|
}
|
|
MCA_ADAPTER_INFO,
|
|
*PMCA_ADAPTER_INFO;
|
|
|
|
UINT gLoadMcaAdapterInfo = 0;
|
|
ULONG gNumberOfMcaAdapters = 0;
|
|
PMCA_ADAPTER_INFO gMcaAdapterList = NULL;
|
|
PWCHAR gMcaParameters = L"SLOTNUMBER\0"
|
|
L"1\0"
|
|
L"100\0";
|
|
|
|
#define MCA_SEARCH_ORDER 999
|
|
|
|
|
|
VOID
|
|
FreeMcaAdapterInfo(
|
|
VOID
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
Arguments:
|
|
|
|
Return Value:
|
|
|
|
--*/
|
|
{
|
|
if (--gLoadMcaAdapterInfo == 0)
|
|
{
|
|
FreeAdapterInformation(gMcaAdapterList, gNumberOfMcaAdapters);
|
|
gMcaAdapterList = NULL;
|
|
gNumberOfMcaAdapters = 0;
|
|
}
|
|
}
|
|
|
|
BOOLEAN
|
|
LoadMcaAdapterInfo(
|
|
VOID
|
|
)
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
Arguments:
|
|
|
|
Return Value:
|
|
|
|
--*/
|
|
{
|
|
PMCA_ADAPTER_INFO AdapterList;
|
|
UINT NumberOfAdapters;
|
|
BOOLEAN f;
|
|
UINT c;
|
|
|
|
//
|
|
// Have we already loaded the adapter information?
|
|
//
|
|
if (gLoadMcaAdapterInfo > 0)
|
|
{
|
|
gLoadMcaAdapterInfo++;
|
|
return(TRUE);
|
|
}
|
|
|
|
//
|
|
// Load the registry specific information.
|
|
//
|
|
f = LoadAdapterInformation(
|
|
L"MCA",
|
|
sizeof(MCA_ADAPTER_INFO),
|
|
&AdapterList,
|
|
&NumberOfAdapters);
|
|
if (!f || (0 == NumberOfAdapters))
|
|
{
|
|
#if _DBG
|
|
DbgPrint("LoadAdapterInformation(MCA) failed!\n");
|
|
#endif
|
|
return(FALSE);
|
|
}
|
|
|
|
//
|
|
// Fill in common adapter information.
|
|
//
|
|
for (c = 0; c < NumberOfAdapters; c++)
|
|
{
|
|
AdapterList[c].Parameters = gMcaParameters;
|
|
}
|
|
|
|
gNumberOfMcaAdapters = NumberOfAdapters;
|
|
gMcaAdapterList = AdapterList;
|
|
gLoadMcaAdapterInfo = 1;
|
|
|
|
return(TRUE);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaIdentifyHandler(
|
|
IN LONG lIndex,
|
|
IN WCHAR * pwchBuffer,
|
|
IN LONG cwchBuffSize
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine returns information about the netcards supported by
|
|
this file.
|
|
|
|
Arguments:
|
|
|
|
lIndex - The index of the netcard being address. The first
|
|
cards information is at index 1000, the second at 1100, etc.
|
|
|
|
pwchBuffer - Buffer to store the result into.
|
|
|
|
cwchBuffSize - Number of bytes in pwchBuffer
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
LONG Code = lIndex % 100;
|
|
LONG Length;
|
|
ULONG i;
|
|
|
|
lIndex = lIndex - Code;
|
|
|
|
if ((ULONG)((lIndex / 100) - 10) < gNumberOfMcaAdapters)
|
|
{
|
|
for (i = 0; i < gNumberOfMcaAdapters; i++)
|
|
{
|
|
if (gMcaAdapterList[i].Index == lIndex)
|
|
{
|
|
switch (Code)
|
|
{
|
|
case 0:
|
|
//
|
|
// Find the string length
|
|
//
|
|
Length = UnicodeStrLen(gMcaAdapterList[i].InfId);
|
|
|
|
Length ++;
|
|
|
|
if (cwchBuffSize < Length)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
memcpy((PVOID)pwchBuffer, gMcaAdapterList[i].InfId, Length * sizeof(WCHAR));
|
|
break;
|
|
|
|
case 3:
|
|
|
|
//
|
|
// Maximum value is 1000
|
|
//
|
|
if (cwchBuffSize < 5)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
wsprintf((PVOID)pwchBuffer, L"%d", MCA_SEARCH_ORDER);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
return(0);
|
|
}
|
|
}
|
|
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
return(ERROR_NO_MORE_ITEMS);
|
|
}
|
|
|
|
|
|
extern
|
|
LONG McaFirstNextHandler(
|
|
IN LONG NetcardId,
|
|
IN INTERFACE_TYPE InterfaceType,
|
|
IN ULONG BusNumber,
|
|
IN BOOL fFirst,
|
|
OUT PVOID *ppvToken,
|
|
OUT LONG *lConfidence
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine finds the instances of a physical adapter identified
|
|
by the NetcardId.
|
|
|
|
Arguments:
|
|
|
|
lNetcardId - The index of the netcard being address. The first
|
|
cards information is id 1000, the second id 1100, etc.
|
|
|
|
InterfaceType - Microchannel
|
|
|
|
BusNumber - The bus number of the bus to search.
|
|
|
|
fFirst - TRUE is we are to search for the first instance of an
|
|
adapter, FALSE if we are to continue search from a previous stopping
|
|
point.
|
|
|
|
ppvToken - A pointer to a handle to return to identify the found
|
|
instance
|
|
|
|
lConfidence - A pointer to a long for storing the confidence factor
|
|
that the card exists.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
ULONG PosId;
|
|
ULONG ReturnValue;
|
|
ULONG NetCardIndex;
|
|
|
|
if (InterfaceType != MicroChannel)
|
|
{
|
|
*lConfidence = 0;
|
|
return(0);
|
|
}
|
|
|
|
NetCardIndex = (NetcardId / 100) - 10;
|
|
|
|
//
|
|
// Call FindFirst Routine
|
|
//
|
|
ReturnValue = FindMcaCard(
|
|
NetCardIndex,
|
|
BusNumber,
|
|
(BOOLEAN)fFirst,
|
|
lConfidence);
|
|
if (ReturnValue == 0)
|
|
{
|
|
#if _DBG
|
|
DbgPrint("FindFirstNext, FindMcaCard OK!\n");
|
|
#endif
|
|
//
|
|
// The adapter token is the index into our array.
|
|
//
|
|
*ppvToken = (PVOID)NetCardIndex;
|
|
}
|
|
|
|
return(ReturnValue);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaOpenHandleHandler(
|
|
IN PVOID pvToken,
|
|
OUT PVOID *ppvHandle
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine takes a token returned by FirstNext and converts it
|
|
into a permanent handle.
|
|
|
|
Arguments:
|
|
|
|
Token - The token.
|
|
|
|
ppvHandle - A pointer to the handle, so we can store the resulting
|
|
handle.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
//
|
|
// The token is the index into the adapter list for the adapter
|
|
// that they want to open.
|
|
//
|
|
*ppvHandle = (PVOID)&gMcaAdapterList[(ULONG)pvToken];
|
|
|
|
return(0);
|
|
}
|
|
|
|
LONG
|
|
McaCreateHandleHandler(
|
|
IN LONG lNetcardId,
|
|
IN INTERFACE_TYPE InterfaceType,
|
|
IN ULONG BusNumber,
|
|
OUT PVOID *ppvHandle
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine is used to force the creation of a handle for cases
|
|
where a card is not found via FirstNext, but the user says it does
|
|
exist.
|
|
|
|
Arguments:
|
|
|
|
lNetcardId - The id of the card to create the handle for.
|
|
|
|
InterfaceType - Microchannel
|
|
|
|
BusNumber - The bus number of the bus in the system.
|
|
|
|
ppvHandle - A pointer to the handle, for storing the resulting handle.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
ULONG i;
|
|
|
|
if (InterfaceType != MicroChannel)
|
|
{
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
for (i = 0; i < gNumberOfMcaAdapters; i++)
|
|
{
|
|
if (gMcaAdapterList[i].Index == lNetcardId)
|
|
{
|
|
gMcaAdapterList[i].SlotNumber = 1;
|
|
gMcaAdapterList[i].BusNumber = BusNumber;
|
|
|
|
*ppvHandle = (PVOID)&gMcaAdapterList[i];
|
|
|
|
return(0);
|
|
}
|
|
}
|
|
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaCloseHandleHandler(
|
|
IN PVOID pvHandle
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This frees any resources associated with a handle.
|
|
|
|
Arguments:
|
|
|
|
pvHandle - The handle.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
return(0);
|
|
}
|
|
|
|
LONG
|
|
McaQueryCfgHandler(
|
|
IN PVOID pvHandle,
|
|
OUT WCHAR *pwchBuffer,
|
|
IN LONG cwchBuffSize
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine calls the appropriate driver's query config handler to
|
|
get the parameters for the adapter associated with the handle.
|
|
|
|
Arguments:
|
|
|
|
pvHandle - The handle.
|
|
|
|
pwchBuffer - The resulting parameter list.
|
|
|
|
cwchBuffSize - Length of the given buffer in WCHARs.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
PMCA_ADAPTER_INFO Adapter = (PMCA_ADAPTER_INFO)&gMcaAdapterList[(ULONG)pvHandle];
|
|
LONG OutputLengthLeft = cwchBuffSize;
|
|
LONG CopyLength;
|
|
ULONG PosId;
|
|
PVOID BusHandle;
|
|
ULONG ReturnValue;
|
|
ULONG Confidence;
|
|
ULONG StartPointer = (ULONG)pwchBuffer;
|
|
|
|
//
|
|
// Verify the SlotNumber
|
|
//
|
|
if (!GetMcaKey(Adapter->BusNumber, &BusHandle))
|
|
{
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
if (!GetMcaPosId(BusHandle, Adapter->SlotNumber, &PosId))
|
|
{
|
|
//
|
|
// Fail
|
|
//
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
if (Adapter->PosId != PosId)
|
|
{
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
//
|
|
// Build resulting buffer
|
|
//
|
|
|
|
//
|
|
// Put in SlotNumber
|
|
//
|
|
|
|
//
|
|
// Copy in the title string
|
|
//
|
|
|
|
CopyLength = UnicodeStrLen(SlotNumberString) + 1;
|
|
|
|
if (OutputLengthLeft < CopyLength)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
RtlMoveMemory((PVOID)pwchBuffer,
|
|
(PVOID)SlotNumberString,
|
|
(CopyLength * sizeof(WCHAR)));
|
|
|
|
pwchBuffer = &(pwchBuffer[CopyLength]);
|
|
OutputLengthLeft -= CopyLength;
|
|
|
|
//
|
|
// Copy in the value
|
|
//
|
|
if (OutputLengthLeft < 8)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
CopyLength = wsprintf(pwchBuffer, L"0x%x", Adapter->SlotNumber);
|
|
|
|
if (CopyLength < 0)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
CopyLength++; // Add in the \0
|
|
|
|
pwchBuffer = &(pwchBuffer[CopyLength]);
|
|
OutputLengthLeft -= CopyLength;
|
|
|
|
//
|
|
// Copy in final \0
|
|
//
|
|
if (OutputLengthLeft < 1)
|
|
{
|
|
return(ERROR_INSUFFICIENT_BUFFER);
|
|
}
|
|
|
|
CopyLength = (ULONG)pwchBuffer - StartPointer;
|
|
((PUCHAR)StartPointer)[CopyLength] = L'\0';
|
|
|
|
return(0);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaVerifyCfgHandler(
|
|
IN PVOID pvHandle,
|
|
IN WCHAR *pwchBuffer
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine verifys that a given parameter list is complete and
|
|
correct for the adapter associated with the handle.
|
|
|
|
Arguments:
|
|
|
|
pvHandle - The handle.
|
|
|
|
pwchBuffer - The parameter list.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
PMCA_ADAPTER_INFO Adapter = (PMCA_ADAPTER_INFO)(pvHandle);
|
|
WCHAR *Place;
|
|
ULONG PosId;
|
|
ULONG SlotNumber;
|
|
PVOID BusHandle;
|
|
BOOLEAN Found;
|
|
|
|
//
|
|
// Parse out the parameter.
|
|
//
|
|
|
|
//
|
|
// Get the SlotNumber
|
|
//
|
|
Place = FindParameterString(pwchBuffer, SlotNumberString);
|
|
if (Place == NULL)
|
|
{
|
|
return(ERROR_INVALID_DATA);
|
|
}
|
|
|
|
Place += UnicodeStrLen(SlotNumberString) + 1;
|
|
|
|
//
|
|
// Now parse the thing.
|
|
//
|
|
ScanForNumber(Place, &SlotNumber, &Found);
|
|
if (Found == FALSE)
|
|
{
|
|
return(ERROR_INVALID_DATA);
|
|
}
|
|
|
|
//
|
|
// Verify the SlotNumber
|
|
//
|
|
if (!GetMcaKey(Adapter->BusNumber, &BusHandle))
|
|
{
|
|
return(ERROR_INVALID_DATA);
|
|
}
|
|
|
|
if (!GetMcaPosId(BusHandle, SlotNumber, &PosId))
|
|
{
|
|
//
|
|
// Fail
|
|
//
|
|
return(ERROR_INVALID_DATA);
|
|
}
|
|
|
|
//
|
|
// Verify the pos id.
|
|
//
|
|
if (Adapter->PosId != PosId)
|
|
{
|
|
return(ERROR_INVALID_DATA);
|
|
}
|
|
|
|
return(0);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaQueryMaskHandler(
|
|
IN LONG lNetcardId,
|
|
OUT WCHAR *pwchBuffer,
|
|
IN LONG cwchBuffSize
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine returns the parameter list information for a specific
|
|
network card.
|
|
|
|
Arguments:
|
|
|
|
lNetcardId - The id of the desired netcard.
|
|
|
|
pwchBuffer - The buffer for storing the parameter information.
|
|
|
|
cwchBuffSize - Length of pwchBuffer in WCHARs.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
WCHAR *Result;
|
|
LONG Length;
|
|
LONG NumberOfAdapters;
|
|
ULONG i;
|
|
|
|
//
|
|
// Find the adapter
|
|
//
|
|
for (i = 0; i < gNumberOfMcaAdapters; i++)
|
|
{
|
|
if (gMcaAdapterList[i].Index == lNetcardId)
|
|
{
|
|
Result = gMcaAdapterList[i].Parameters;
|
|
|
|
//
|
|
// Find the string length (Ends with 2 NULLs)
|
|
//
|
|
for (Length = 0; ; Length++)
|
|
{
|
|
if (Result[Length] == L'\0')
|
|
{
|
|
++Length;
|
|
|
|
if (Result[Length] == L'\0')
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
Length++;
|
|
|
|
if (cwchBuffSize < Length)
|
|
{
|
|
return(ERROR_NOT_ENOUGH_MEMORY);
|
|
}
|
|
|
|
memcpy((PVOID)pwchBuffer, Result, Length * sizeof(WCHAR));
|
|
|
|
return(0);
|
|
}
|
|
}
|
|
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
extern
|
|
LONG
|
|
McaParamRangeHandler(
|
|
IN LONG lNetcardId,
|
|
IN WCHAR *pwchParam,
|
|
OUT LONG *plValues,
|
|
OUT LONG *plBuffSize
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine returns a list of valid values for a given parameter name
|
|
for a given card.
|
|
|
|
Arguments:
|
|
|
|
lNetcardId - The Id of the card desired.
|
|
|
|
pwchParam - A WCHAR string of the parameter name to query the values of.
|
|
|
|
plValues - A pointer to a list of LONGs into which we store valid values
|
|
for the parameter.
|
|
|
|
plBuffSize - At entry, the length of plValues in LONGs. At exit, the
|
|
number of LONGs stored in plValues.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
*plBuffSize = 0;
|
|
|
|
return(0);
|
|
}
|
|
|
|
extern
|
|
LONG McaQueryParameterNameHandler(
|
|
IN WCHAR *pwchParam,
|
|
OUT WCHAR *pwchBuffer,
|
|
IN LONG cwchBufferSize
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
Returns a localized, displayable name for a specific parameter. All the
|
|
parameters that this file uses are define by MS, so no strings are
|
|
needed here.
|
|
|
|
Arguments:
|
|
|
|
pwchParam - The parameter to be queried.
|
|
|
|
pwchBuffer - The buffer to store the result into.
|
|
|
|
cwchBufferSize - The length of pwchBuffer in WCHARs.
|
|
|
|
Return Value:
|
|
|
|
ERROR_INVALID_PARAMETER -- To indicate that the MS supplied strings
|
|
should be used.
|
|
|
|
--*/
|
|
|
|
{
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
ULONG
|
|
FindMcaCard(
|
|
IN ULONG AdapterNumber,
|
|
IN ULONG BusNumber,
|
|
IN BOOLEAN fFirst,
|
|
OUT PULONG lConfidence
|
|
)
|
|
|
|
/*++
|
|
|
|
Routine Description:
|
|
|
|
This routine finds the instances of a physical adapter identified
|
|
by the PosId.
|
|
|
|
Arguments:
|
|
|
|
AdapterNumber - The index into the global array of adapters for the card.
|
|
|
|
BusNumber - The bus number of the bus to search.
|
|
|
|
fFirst - TRUE is we are to search for the first instance of an
|
|
adapter, FALSE if we are to continue search from a previous stopping
|
|
point.
|
|
|
|
PosId - The MCA POS Id of the card.
|
|
|
|
lConfidence - A pointer to a long for storing the confidence factor
|
|
that the card exists.
|
|
|
|
Return Value:
|
|
|
|
0 if nothing went wrong, else the appropriate WINERROR.H value.
|
|
|
|
--*/
|
|
|
|
{
|
|
PMCA_ADAPTER_INFO Adapter = &gMcaAdapterList[AdapterNumber];
|
|
PVOID BusHandle;
|
|
ULONG TmpPosId;
|
|
|
|
if (fFirst)
|
|
{
|
|
Adapter->SlotNumber = 0;
|
|
}
|
|
else
|
|
{
|
|
Adapter->SlotNumber++;
|
|
}
|
|
|
|
if (!GetMcaKey(BusNumber, &BusHandle))
|
|
{
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
while (TRUE)
|
|
{
|
|
if (!GetMcaPosId(BusHandle, Adapter->SlotNumber, &TmpPosId))
|
|
{
|
|
*lConfidence = 0;
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
if (Adapter->PosId == TmpPosId)
|
|
{
|
|
*lConfidence = 100;
|
|
return(0);
|
|
}
|
|
|
|
Adapter->SlotNumber++;
|
|
|
|
}
|
|
|
|
DeleteMcaKey(BusHandle);
|
|
|
|
return(ERROR_INVALID_PARAMETER);
|
|
}
|
|
|
|
|