📄 nulmrxnp.c
字号:
{
RemoteName[CopyBytes/sizeof(WCHAR)] = L'\0';
lstrcpyn( ConnectionName, DD_NULMRX_FS_DEVICE_NAME_U, 126 );
wcsncat( ConnectionName, L"\\;", 3);
wcsncat( ConnectionName, LocalName, 128-wcslen(ConnectionName) );
wcsncat( ConnectionName, RemoteName, 128-wcslen(ConnectionName) );
ConnectionName[127] = L'\0';
CopyBytes = 0;
Status = SendToMiniRdr( IOCTL_NULMRX_DELCONN, ConnectionName,
( wcslen( ConnectionName ) + 1 ) * sizeof( WCHAR ),
NULL, &CopyBytes );
if ( Status == WN_SUCCESS )
{
if ( !DefineDosDevice( DDD_REMOVE_DEFINITION | DDD_RAW_TARGET_PATH | DDD_EXACT_MATCH_ON_REMOVE,
LocalName,
ConnectionName ) )
{
Status = GetLastError( );
}
}
}
else
{
Status = WN_NOT_CONNECTED;
}
}
}
return Status;
}
DWORD APIENTRY
NPGetConnection(
LPWSTR lpLocalName,
LPWSTR lpRemoteName,
LPDWORD lpBufferSize )
/*++
Routine Description:
This routine returns the information associated with a connection
Arguments:
lpLocalName - local name associated with the connection
lpRemoteName - the remote name associated with the connection
lpBufferSize - the remote name buffer size
Return Value:
WN_SUCCESS if successful, otherwise the appropriate error
Notes:
--*/
{
DWORD Status, len, i;
ULONG CopyBytes;
WCHAR RemoteName[128];
WCHAR LocalName[3];
Status = WN_NOT_CONNECTED;
DbgP(( L"NPGetConnection....\n" ));
if(lpLocalName == NULL)
return Status;
if ( wcslen( lpLocalName ) > 1 )
{
if ( lpLocalName[1] == L':' )
{
CopyBytes = 128*sizeof(WCHAR);
// LocalName[0] = (WCHAR) CharUpper( (PWCHAR) MAKELONG( (USHORT) lpLocalName[0], 0 ) );
LocalName[0] = (WCHAR) toupper(lpLocalName[0]);
LocalName[1] = L':';
LocalName[2] = L'\0';
Status = SendToMiniRdr( IOCTL_NULMRX_GETCONN, LocalName, 3 * sizeof( WCHAR ),
(PVOID) RemoteName, &CopyBytes );
}
}
if ( Status == WN_SUCCESS )
{
len = CopyBytes + sizeof(WCHAR);
if ( *lpBufferSize > len )
{
*lpRemoteName++ = L'\\';
CopyMemory( lpRemoteName, RemoteName, CopyBytes );
lpRemoteName[CopyBytes/sizeof(WCHAR)] = L'\0';
}
else
{
Status = WN_MORE_DATA;
*lpBufferSize = len;
}
}
return Status;
}
DWORD APIENTRY
NPOpenEnum(
DWORD dwScope,
DWORD dwType,
DWORD dwUsage,
LPNETRESOURCE lpNetResource,
LPHANDLE lphEnum )
/*++
Routine Description:
This routine opens a handle for enumeration of resources. The only capability
implemented in the sample is for enumerating connected shares
Arguments:
dwScope - the scope of enumeration
dwType - the type of resources to be enumerated
dwUsage - the usage parameter
lpNetResource - a pointer to the desired NETRESOURCE struct.
lphEnum - aptr. for passing nack the enumeration handle
Return Value:
WN_SUCCESS if successful, otherwise the appropriate error
Notes:
The sample only supports the notion of enumerating connected shares
The handle passed back is merely the index of the last entry returned
--*/
{
DWORD Status;
DbgP((L"NPOpenEnum\n"));
*lphEnum = NULL;
switch ( dwScope )
{
case RESOURCE_CONNECTED:
{
*lphEnum = HeapAlloc( GetProcessHeap( ), HEAP_ZERO_MEMORY, sizeof( ULONG ) );
if (*lphEnum )
{
Status = WN_SUCCESS;
}
else
{
Status = WN_OUT_OF_MEMORY;
}
break;
}
break;
case RESOURCE_CONTEXT:
default:
Status = WN_NOT_SUPPORTED;
break;
}
DbgP((L"NPOpenEnum returning Status %lx\n",Status));
return(Status);
}
DWORD APIENTRY
NPEnumResource(
HANDLE hEnum,
LPDWORD lpcCount,
LPVOID lpBuffer,
LPDWORD lpBufferSize)
/*++
Routine Description:
This routine uses the handle obtained by a call to NPOpenEnum for
enuerating the connected shares
Arguments:
hEnum - the enumeration handle
lpcCount - the number of resources returned
lpBuffer - the buffere for passing back the entries
lpBufferSize - the size of the buffer
Return Value:
WN_SUCCESS if successful, otherwise the appropriate error
WN_NO_MORE_ENTRIES - if the enumeration has exhausted the entries
WN_MORE_DATA - if nmore data is available
Notes:
The sample only supports the notion of enumerating connected shares
The handle passed back is merely the index of the last entry returned
--*/
{
DWORD Status = WN_SUCCESS;
BYTE ConnectionList[26];
ULONG CopyBytes;
ULONG EntriesCopied;
ULONG i;
LPNETRESOURCE pNetResource;
ULONG SpaceNeeded;
ULONG SpaceAvailable;
WCHAR LocalName[3];
WCHAR RemoteName[128];
PWCHAR StringZone;
DbgP((L"NPEnumResource\n"));
DbgP((L"NPEnumResource Count Requested %d\n", *lpcCount));
pNetResource = (LPNETRESOURCE) lpBuffer;
SpaceAvailable = *lpBufferSize;
EntriesCopied = 0;
StringZone = (PWCHAR) ((PBYTE)lpBuffer + *lpBufferSize);
CopyBytes = 26;
Status = SendToMiniRdr( IOCTL_NULMRX_GETLIST, NULL, 0,
(PVOID) ConnectionList, &CopyBytes );
i = *((PULONG)hEnum);
if ( Status == WN_SUCCESS)
{
for ( i = *((PULONG) hEnum); EntriesCopied < *lpcCount && i < 26; i++ )
{
if ( ConnectionList[i] )
{
CopyBytes = 128*sizeof(WCHAR);
LocalName[0] = L'A' + (WCHAR) i;
LocalName[1] = L':';
LocalName[2] = L'\0';
Status = SendToMiniRdr( IOCTL_NULMRX_GETCONN, LocalName, 3 * sizeof(WCHAR),
(PVOID) RemoteName, &CopyBytes );
// if something strange happended then just say there are no more entries
if ( Status != WN_SUCCESS || CopyBytes == 0 )
{
Status = WN_NO_MORE_ENTRIES;
break;
}
// Determine the space needed for this entry...
SpaceNeeded = sizeof( NETRESOURCE ); // resource struct
SpaceNeeded += 3 * sizeof(WCHAR); // local name
SpaceNeeded += 2 * sizeof(WCHAR) + CopyBytes; // remote name
SpaceNeeded += 5 * sizeof(WCHAR); // comment
SpaceNeeded += sizeof(NULMRX_PROVIDER_NAME_U); // provider name
if ( SpaceNeeded > SpaceAvailable )
{
break;
}
else
{
SpaceAvailable -= SpaceNeeded;
pNetResource->dwScope = RESOURCE_CONNECTED;
pNetResource->dwType = RESOURCETYPE_DISK;
pNetResource->dwDisplayType = RESOURCEDISPLAYTYPE_SHARE;
pNetResource->dwUsage = 0;
// setup string area at opposite end of buffer
SpaceNeeded -= sizeof( NETRESOURCE );
StringZone = (PWCHAR)( (PBYTE) StringZone - SpaceNeeded );
// copy local name
pNetResource->lpLocalName = StringZone;
*StringZone++ = L'A' + (WCHAR) i;
*StringZone++ = L':';
*StringZone++ = L'\0';
// copy remote name
pNetResource->lpRemoteName = StringZone;
*StringZone++ = L'\\';
CopyMemory( StringZone, RemoteName, CopyBytes );
StringZone += CopyBytes / sizeof(WCHAR);
*StringZone++ = L'\0';
// copy comment
pNetResource->lpComment = StringZone;
*StringZone++ = L'A';
*StringZone++ = L'_';
*StringZone++ = L'O';
*StringZone++ = L'K';
*StringZone++ = L'\0';
// copy provider name
pNetResource->lpProvider = StringZone;
lstrcpyn( StringZone, NULMRX_PROVIDER_NAME_U, sizeof(NULMRX_PROVIDER_NAME_U)/sizeof(WCHAR) );
EntriesCopied++;
// set new bottom of string zone
StringZone = (PWCHAR)( (PBYTE) StringZone - SpaceNeeded );
}
pNetResource++;
}
}
}
else
{
Status = WN_NO_MORE_ENTRIES;
}
*lpcCount = EntriesCopied;
if ( EntriesCopied == 0 && Status == WN_SUCCESS )
{
if ( i > 25 )
{
Status = WN_NO_MORE_ENTRIES;
}
else
{
DbgP((L"NPEnumResource More Data Needed - %d\n", SpaceNeeded));
Status = WN_MORE_DATA;
*lpBufferSize = SpaceNeeded;
}
}
// update entry index
*(PULONG) hEnum = i;
DbgP((L"NPEnumResource Entries returned - %d\n", EntriesCopied));
return Status;
}
DWORD APIENTRY
NPCloseEnum(
HANDLE hEnum )
/*++
Routine Description:
This routine closes the handle for enumeration of resources.
Arguments:
hEnum - the enumeration handle
Return Value:
WN_SUCCESS if successful, otherwise the appropriate error
Notes:
The sample only supports the notion of enumerating connected shares
--*/
{
DbgP((L"NPCloseEnum\n"));
HeapFree( GetProcessHeap( ), 0, (PVOID) hEnum );
return WN_SUCCESS;
}
DWORD APIENTRY
NPGetResourceParent(
LPNETRESOURCE lpNetResource,
LPVOID lpBuffer,
LPDWORD lpBufferSize )
/*++
Routine Description:
This routine returns the information about net resource parent
Arguments:
lpNetResource - the NETRESOURCE struct
lpBuffer - the buffer for passing back the parent information
lpBufferSize - the buffer size
Return Value:
Notes:
--*/
{
DbgP(( L"NPGetResourceParent: WN_NOT_SUPPORTED\n" ));
return WN_NOT_SUPPORTED;
}
DWORD APIENTRY
NPGetResourceInformation(
LPNETRESOURCE lpNetResource,
LPVOID lpBuffer,
LPDWORD lpBufferSize,
LPWSTR *lplpSystem )
/*++
Routine Description:
This routine returns the information associated net resource
Arguments:
lpNetResource - the NETRESOURCE struct
lpBuffer - the buffer for passing back the parent information
lpBufferSize - the buffer size
lplpSystem -
Return Value:
Notes:
--*/
{
DbgP(( L"NPGetResourceInformation: WN_NOT_SUPPORTED\n" ));
return WN_NOT_SUPPORTED;
}
DWORD APIENTRY
NPGetUniversalName(
LPCWSTR lpLocalPath,
DWORD dwInfoLevel,
LPVOID lpBuffer,
LPDWORD lpBufferSize )
/*++
Routine Description:
This routine returns the information associated net resource
Arguments:
lpLocalPath - the local path name
dwInfoLevel - the desired info level
lpBuffer - the buffer for the univeral name
lpBufferSize - the buffer size
Return Value:
WN_SUCCESS if successful
Notes:
--*/
{
DbgP(( L"NPGetUniversalName: WN_NOT_SUPPORTED\n" ));
return WN_NOT_SUPPORTED;
}
int _cdecl _vsnwprintf( wchar_t *buffer, size_t count, wchar_t *format, va_list arg_ptr);
// Format and write debug information to OutputDebugString
ULONG _cdecl WideDbgPrint( LPTSTR Format, ... )
{
ULONG rc = 0;
TCHAR szbuffer[256];
va_list marker;
va_start( marker, Format );
{
rc = _vsnwprintf( szbuffer, 254, Format, marker );
szbuffer[255] = (TCHAR)0;
OutputDebugString( TRACE_TAG );
OutputDebugString( szbuffer );
}
return rc;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -