|
|
/********************************************************************/ /** Copyright(c) 1995 Microsoft Corporation. **/ /********************************************************************/
//***
//
// Filename: ifapi.c
//
// Description: Contains code to process interface admin api requests
//
// History: May 11,1995 NarenG Created original version.
//
#include "dimsvcp.h"
#include <ras.h>
#include <dimsvc.h> // Generated by MIDL
#include "rpbk.h"
#include <mprapip.h>
#define MAX_GET_INFO_RETRIES 3
//
// DoStartRouter API interface
//
typedef struct _START_ROUTER_DATA { DWORD dwTransportId; DWORD dwInterfaceInfoSize; LPBYTE pInterfaceInfo; DWORD dwGlobalInfoSize; LPBYTE pGlobalInfo;
} START_ROUTER_DATA, *PSTART_ROUTER_DATA;
DWORD RRouterDeviceEnum( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN OUT PDIM_INFORMATION_CONTAINER pInfoStruct, OUT LPDWORD lpdwTotalEntries ) { DWORD dwAccessStatus; DWORD dwRetCode = NO_ERROR; LPRASDEVINFO lpRasDevInfo = NULL; DWORD dwSize = 0, dwRetSize = 0; DWORD dwcDevices = 0; DWORD i = 0; MPR_DEVICE_0* pDev0 = NULL;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwLevel != 0 ) { return( ERROR_NOT_SUPPORTED ); }
do { *lpdwTotalEntries = 0; // Find out how much memory to allocate
//
dwRetCode = RasEnumDevices( NULL, &dwSize, &dwcDevices); if ( ( dwRetCode != NO_ERROR ) && ( dwRetCode != ERROR_BUFFER_TOO_SMALL ) ) { break; }
if ( dwSize == 0 ) { dwRetCode = NO_ERROR; break; }
// Allocate the ras device info
//
lpRasDevInfo = LOCAL_ALLOC ( LPTR, dwSize ); if ( lpRasDevInfo == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY; break; } ZeroMemory(lpRasDevInfo, dwSize );
// Allocate the return value
//
dwRetSize = dwcDevices * sizeof(MPR_DEVICE_0); pInfoStruct->pBuffer = MIDL_user_allocate( dwRetSize ); if ( pInfoStruct->pBuffer == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY; break; } ZeroMemory(pInfoStruct->pBuffer, dwRetSize ); pDev0 = (MPR_DEVICE_0*) pInfoStruct->pBuffer;
// Read in the device info
lpRasDevInfo->dwSize = sizeof(RASDEVINFO); dwRetCode = RasEnumDevices( lpRasDevInfo, &dwSize, &dwcDevices); if ( dwRetCode == ERROR_BUFFER_TOO_SMALL ) { dwRetCode = NO_ERROR; } if ( dwRetCode != NO_ERROR ) { break; }
// Copy the device info over
for ( i = 0; i < dwcDevices; i++ ) { wcscpy(pDev0[i].szDeviceType, lpRasDevInfo[i].szDeviceType); wcscpy(pDev0[i].szDeviceName, lpRasDevInfo[i].szDeviceName); }
// Everything's ok, go ahead and set the return values
//
*lpdwTotalEntries = dwcDevices; pInfoStruct->dwBufferSize = dwRetSize; } while( FALSE );
// Cleanup
{ if ( lpRasDevInfo ) { LOCAL_FREE( lpRasDevInfo ); }
if ( dwRetCode != NO_ERROR ) { if ( pInfoStruct->pBuffer ) { MIDL_user_free ( pInfoStruct->pBuffer ); pInfoStruct->pBuffer = NULL; } } }
/*TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS,
"DeviceEnum returned %d", dwRetCode );*/
return( dwRetCode ); }
//**
//
// Call: DoStartRouter
//
// Returns: NO_ERROR - Success
// Non-zero returns - Failure
//
// Description:
//
VOID DoStartRouter( IN PVOID pParameter ) { DWORD dwRetCode = NO_ERROR; DWORD dwIndex = gblDIMConfigInfo.dwNumRouterManagers; ROUTER_INTERFACE_OBJECT * pIfObject; START_ROUTER_DATA * pStartRouterData = (START_ROUTER_DATA *)pParameter; DWORD (*StartRouter)( IN OUT DIM_ROUTER_INTERFACE * pDimRouterIf, IN BOOL fLANModeOnly, IN LPVOID pGlobalInfo );
//
// Wait for setup to finsh
//
Sleep( 15000 );
//
// Load the StartRouter
//
StartRouter = (PVOID)GetProcAddress( gblRouterManagers[dwIndex].hModule, "StartRouter" );
if ( StartRouter == NULL ) { if ( pStartRouterData->pInterfaceInfo != NULL ) { LOCAL_FREE( pStartRouterData->pInterfaceInfo ); }
if ( pStartRouterData->pGlobalInfo != NULL ) { LOCAL_FREE( pStartRouterData->pGlobalInfo ); }
LOCAL_FREE( pStartRouterData );
return; }
gblRouterManagers[dwIndex].DdmRouterIf.ConnectInterface = DIMConnectInterface; gblRouterManagers[dwIndex].DdmRouterIf.DisconnectInterface = DIMDisconnectInterface; gblRouterManagers[dwIndex].DdmRouterIf.SaveInterfaceInfo = DIMSaveInterfaceInfo; gblRouterManagers[dwIndex].DdmRouterIf.RestoreInterfaceInfo = DIMRestoreInterfaceInfo; gblRouterManagers[dwIndex].DdmRouterIf.SaveGlobalInfo = DIMSaveGlobalInfo; gblRouterManagers[dwIndex].DdmRouterIf.RouterStopped = DIMRouterStopped; gblRouterManagers[dwIndex].DdmRouterIf.InterfaceEnabled = DIMInterfaceEnabled; dwRetCode = (*StartRouter)( &(gblRouterManagers[dwIndex].DdmRouterIf), gblDIMConfigInfo.dwRouterRole == ROUTER_ROLE_LAN, pStartRouterData->pGlobalInfo );
if ( dwRetCode != NO_ERROR ) { DIMTRACE1( "Start Router failed with %d", dwRetCode );
if ( pStartRouterData->pInterfaceInfo != NULL ) { LOCAL_FREE( pStartRouterData->pInterfaceInfo ); }
if ( pStartRouterData->pGlobalInfo != NULL ) { LOCAL_FREE( pStartRouterData->pGlobalInfo ); } LOCAL_FREE( pStartRouterData );
return; }
//
// Save the global client info
//
if ( pStartRouterData->pInterfaceInfo == NULL ) { gblRouterManagers[dwIndex].pDefaultClientInterface = NULL; gblRouterManagers[dwIndex].dwDefaultClientInterfaceSize = 0; } else { LPBYTE lpData = LOCAL_ALLOC(LPTR,pStartRouterData->dwInterfaceInfoSize);
if ( lpData == NULL ) { if ( pStartRouterData->pInterfaceInfo != NULL ) { LOCAL_FREE( pStartRouterData->pInterfaceInfo ); }
if ( pStartRouterData->pGlobalInfo != NULL ) { LOCAL_FREE( pStartRouterData->pGlobalInfo ); }
LOCAL_FREE( pStartRouterData );
return; }
CopyMemory( lpData, pStartRouterData->pInterfaceInfo, pStartRouterData->dwInterfaceInfoSize );
gblRouterManagers[dwIndex].pDefaultClientInterface = lpData;
gblRouterManagers[dwIndex].dwDefaultClientInterfaceSize = pStartRouterData->dwInterfaceInfoSize; }
gblRouterManagers[dwIndex].fIsRunning = TRUE;
gblDIMConfigInfo.dwNumRouterManagers++;
//
// Register all interfaces with the router manager
//
AddInterfacesToRouterManager( NULL, pStartRouterData->dwTransportId );
//
// Notify router manager that all interfaces have been added to the
// router
//
gblRouterManagers[dwIndex].DdmRouterIf.RouterBootComplete();
if ( gblDIMConfigInfo.dwRouterRole != ROUTER_ROLE_LAN ) { DWORD (*DDMTransportCreate)( DWORD ) = (DWORD(*)( DWORD ))GetDDMEntryPoint("DDMTransportCreate");
if(NULL == DDMTransportCreate) { return ; }
DDMTransportCreate( pStartRouterData->dwTransportId ); }
//
// We can only make this call while not holding the interface table
// lock
//
DIMTRACE( "Setting router attributes in the identity object" );
RouterIdentityObjectUpdateAttributes( FALSE, FALSE );
if ( pStartRouterData->pInterfaceInfo != NULL ) { LOCAL_FREE( pStartRouterData->pInterfaceInfo ); }
if ( pStartRouterData->pGlobalInfo != NULL ) { LOCAL_FREE( pStartRouterData->pGlobalInfo ); }
LOCAL_FREE( pStartRouterData ); }
//**
//
// Call: RRouterInterfaceTransportCreate
//
// Returns: NO_ERROR - Success
// Non-zero returns - Failure
//
// Description:
//
DWORD RRouterInterfaceTransportCreate( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwTransportId, IN LPWSTR lpwsTransportName, IN PDIM_INTERFACE_CONTAINER pInfoStruct, IN LPWSTR lpwsDLLPath ) { DWORD dwAccessStatus = 0; DWORD dwRetCode = NO_ERROR; DWORD dwIndex = gblDIMConfigInfo.dwNumRouterManagers; START_ROUTER_DATA * pStartRouterData = NULL;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( GetTransportIndex( dwTransportId ) != (DWORD) -1 ) { return( ERROR_PROTOCOL_ALREADY_INSTALLED ); }
#if (WINVER >= 0x0501)
if ( dwTransportId == PID_IP ) #else
if ( ( dwTransportId == PID_IP ) || ( dwTransportId == PID_IPX ) ) #endif
{ DWORD cbSize = 0; WCHAR * pDllExpandedPath = NULL;
//
// Replace the %SystemRoot% with the actual path.
//
cbSize = ExpandEnvironmentStrings( lpwsDLLPath, NULL, 0 );
if ( cbSize == 0 ) { return( GetLastError() ); } else { cbSize *= sizeof( WCHAR ); }
pDllExpandedPath = (LPWSTR)LOCAL_ALLOC( LPTR, cbSize*sizeof(WCHAR) );
if ( pDllExpandedPath == (LPWSTR)NULL ) { return( ERROR_NOT_ENOUGH_MEMORY ); }
cbSize = ExpandEnvironmentStrings( lpwsDLLPath, pDllExpandedPath, cbSize ); if ( cbSize == 0 ) { LOCAL_FREE( pDllExpandedPath );
return( GetLastError() ); }
//
// Load the DLL
//
gblRouterManagers[dwIndex].hModule = LoadLibrary( pDllExpandedPath );
LOCAL_FREE( pDllExpandedPath );
if ( gblRouterManagers[dwIndex].hModule == NULL ) { return( GetLastError() ); }
pStartRouterData = LOCAL_ALLOC( LPTR, sizeof( START_ROUTER_DATA ) );
if ( pStartRouterData == NULL ) { return( ERROR_NOT_ENOUGH_MEMORY ); }
pStartRouterData->dwTransportId = dwTransportId; pStartRouterData->dwInterfaceInfoSize = pInfoStruct->dwInterfaceInfoSize;
if ( pStartRouterData->dwInterfaceInfoSize != 0 ) { pStartRouterData->pInterfaceInfo = LOCAL_ALLOC( LPTR, pStartRouterData->dwInterfaceInfoSize ); if ( pStartRouterData->pInterfaceInfo == NULL ) { LOCAL_FREE( pStartRouterData );
return( ERROR_NOT_ENOUGH_MEMORY ); } else { CopyMemory( pStartRouterData->pInterfaceInfo, pInfoStruct->pInterfaceInfo, pInfoStruct->dwInterfaceInfoSize ); } }
pStartRouterData->dwGlobalInfoSize = pInfoStruct->dwGlobalInfoSize;
if ( pStartRouterData->dwGlobalInfoSize != 0 ) { pStartRouterData->pGlobalInfo = LOCAL_ALLOC( LPTR, pStartRouterData->dwGlobalInfoSize );
if ( pStartRouterData->pGlobalInfo == NULL ) { if ( pStartRouterData->pInterfaceInfo != NULL ) { LOCAL_FREE( pStartRouterData->pInterfaceInfo ); }
LOCAL_FREE( pStartRouterData );
return( ERROR_NOT_ENOUGH_MEMORY ); } else { CopyMemory( pStartRouterData->pGlobalInfo, pInfoStruct->pGlobalInfo, pInfoStruct->dwGlobalInfoSize ); } }
//
// Schedule this for 15 seconds after returning from this call since setup
// may have a ways to go to complete doing all its installation.
// This is a low risk fix to
//
RtlQueueWorkItem( DoStartRouter, pStartRouterData, WT_EXECUTEDEFAULT ); }
return( NO_ERROR ); }
//**
//
// Call: RRouterInterfaceTransportSetGlobalInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_UNKNOWN_PROTOCOL_ID
// non-zero returns from SetGlobalInfo
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportSetGlobalInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwTransportId, IN PDIM_INTERFACE_CONTAINER pInfoStruct ) { LPBYTE lpData; DWORD dwAccessStatus = 0; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwTransportId ); BOOL fGlobalDataUpdated = FALSE;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( pInfoStruct->pGlobalInfo != NULL ) { dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.SetGlobalInfo( pInfoStruct->pGlobalInfo );
if ( dwRetCode != NO_ERROR ) { break; }
//
// Update router identity object since we may be adding or
// removing a routing protocol
//
fGlobalDataUpdated = TRUE; }
if ( pInfoStruct->pInterfaceInfo != NULL ) { lpData=gblRouterManagers[dwTransportIndex].pDefaultClientInterface;
if ( lpData != NULL ) { LOCAL_FREE( lpData ); }
lpData = LOCAL_ALLOC( LPTR, pInfoStruct->dwInterfaceInfoSize );
if ( lpData == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY;
break; }
CopyMemory( lpData, pInfoStruct->pInterfaceInfo, pInfoStruct->dwInterfaceInfoSize );
gblRouterManagers[dwTransportIndex].pDefaultClientInterface=lpData;
gblRouterManagers[dwTransportIndex].dwDefaultClientInterfaceSize = pInfoStruct->dwInterfaceInfoSize; }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
if ( ( dwRetCode == NO_ERROR ) && ( fGlobalDataUpdated ) ) { //
// We can only make this call while not holding the interface table
// lock
//
RouterIdentityObjectUpdateAttributes( FALSE, FALSE ); }
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "SetGlobalInfo returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceTransportGetGlobalInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_UNKNOWN_PROTOCOL_ID
// non-zero returns from GetGlobalInfo
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportGetGlobalInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwTransportId, IN PDIM_INTERFACE_CONTAINER pInfoStruct ) { DWORD dwAccessStatus = 0; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwTransportId ); ULONG ulNumAttempts;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( pInfoStruct->fGetGlobalInfo ) { ulNumAttempts = 0; pInfoStruct->pGlobalInfo = NULL; do { //
// The first iteration should get the size
// The second iteration should get the info.
// iteration 3 is only required if the
// size of the info. changes between first and
// second iteration.
// of course the size can change between iteration
// 2 and 3 and so on. So we try MAX_GET_INFO_RETRIES
// many times and quit if we still have not
// successfully retrieved the info.
//
dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.GetGlobalInfo( pInfoStruct->pGlobalInfo, &(pInfoStruct->dwGlobalInfoSize) );
/*TracePrintfExA(
gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "GetGlobalInfo: Transport %d requires size %d, result %d", dwTransportIndex, pInfoStruct->dwGlobalInfoSize, dwRetCode ); */ if ( dwRetCode != ERROR_INSUFFICIENT_BUFFER ) { break; }
//
// release previous allocation
//
if ( ulNumAttempts ) { MIDL_user_free( pInfoStruct->pGlobalInfo ); pInfoStruct-> pGlobalInfo = NULL; } if ( pInfoStruct->dwGlobalInfoSize > 0 ) { pInfoStruct->pGlobalInfo = MIDL_user_allocate( pInfoStruct->dwGlobalInfoSize );
if ( pInfoStruct->pGlobalInfo == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY;
break; } }
else { break; } ulNumAttempts++; } while ( (dwRetCode == ERROR_INSUFFICIENT_BUFFER) && (ulNumAttempts < MAX_GET_INFO_RETRIES) ); }
if ( dwRetCode != NO_ERROR ) { break; } if ((gblRouterManagers[dwTransportIndex].dwDefaultClientInterfaceSize>0) && ( pInfoStruct->fGetInterfaceInfo ) ) {
pInfoStruct->dwInterfaceInfoSize = gblRouterManagers[dwTransportIndex].dwDefaultClientInterfaceSize;
pInfoStruct->pInterfaceInfo = MIDL_user_allocate(pInfoStruct->dwInterfaceInfoSize);
if ( pInfoStruct->pInterfaceInfo == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY;
break; }
CopyMemory( pInfoStruct->pInterfaceInfo, gblRouterManagers[dwTransportIndex].pDefaultClientInterface, pInfoStruct->dwInterfaceInfoSize );
}
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
/*TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS,
"GetGlobalInfo returned %d", dwRetCode );*/
return( dwRetCode ); }
//**
//
// Call: InterfaceAjustVLSPointers
//
// Returns: none
//
// Description: Adjusts pointers in variable length structures
// dealing with interface info
//
DWORD InterfaceAjustVLSPointers ( DWORD dwLevel, LPBYTE lpbBuffer) { if ( dwLevel == 1 ) { MPRI_INTERFACE_1 * pIf1 = (MPRI_INTERFACE_1*)lpbBuffer;
if ( pIf1->dwDialoutHoursRestrictionOffset ) { pIf1->dwDialoutHoursRestrictionOffset = sizeof(MPRI_INTERFACE_1); } }
else if ( dwLevel == 2 ) { MPRI_INTERFACE_2 * pIf2 = (MPRI_INTERFACE_2*)lpbBuffer; DWORD dwOffset = 0;
// Adjust the custom auth data pointer
//
dwOffset += sizeof(MPRI_INTERFACE_2); if ( pIf2->dwCustomAuthDataSize ) { pIf2->dwCustomAuthDataOffset = dwOffset; }
// Adjust the alternates list pointer
//
dwOffset += pIf2->dwCustomAuthDataSize; if ( pIf2->dwAlternatesOffset ) { pIf2->dwAlternatesOffset = dwOffset; } }
return NO_ERROR; } //**
//
// Call: GetMprInterface0Data
//
// Returns: none
//
// Description: Given a pointer to an interface object will fill an
// MPR_INTERFACE_0 structure appropriately.
//
VOID GetMprInterface0Data( IN ROUTER_INTERFACE_OBJECT * pIfObject, OUT MPRI_INTERFACE_0 * pMprIf0 ) { wcscpy( pMprIf0->wszInterfaceName, pIfObject->lpwsInterfaceName );
pMprIf0->dwIfType = pIfObject->IfType; pMprIf0->dwInterface = PtrToUlong(pIfObject->hDIMInterface); pMprIf0->dwLastError = pIfObject->dwLastError; pMprIf0->fEnabled = ( pIfObject->fFlags & IFFLAG_ENABLED );
pMprIf0->fUnReachabilityReasons = ( pIfObject->fFlags & IFFLAG_OUT_OF_RESOURCES ) ? MPR_INTERFACE_OUT_OF_RESOURCES : 0;
if ( !( pIfObject->fFlags & IFFLAG_ENABLED ) ) { pMprIf0->fUnReachabilityReasons |= MPR_INTERFACE_ADMIN_DISABLED; }
if ( gblDIMConfigInfo.ServiceStatus.dwCurrentState == SERVICE_PAUSED ) { pMprIf0->fUnReachabilityReasons |= MPR_INTERFACE_SERVICE_PAUSED; }
if ( pIfObject->fFlags & IFFLAG_CONNECTION_FAILURE ) { pMprIf0->fUnReachabilityReasons |= MPR_INTERFACE_CONNECTION_FAILURE; }
if ( pIfObject->fFlags & IFFLAG_DIALOUT_HOURS_RESTRICTION ) { pMprIf0->fUnReachabilityReasons |= MPR_INTERFACE_DIALOUT_HOURS_RESTRICTION; }
if ( pIfObject->fFlags & IFFLAG_NO_MEDIA_SENSE ) { pMprIf0->fUnReachabilityReasons |= MPR_INTERFACE_NO_MEDIA_SENSE; }
switch( pIfObject->State ) {
case RISTATE_CONNECTED:
pMprIf0->dwConnectionState = ROUTER_IF_STATE_CONNECTED;
break;
case RISTATE_DISCONNECTED:
if ( pMprIf0->fUnReachabilityReasons != 0 ) { pMprIf0->dwConnectionState = ROUTER_IF_STATE_UNREACHABLE; } else { pMprIf0->dwConnectionState = ROUTER_IF_STATE_DISCONNECTED; }
break;
case RISTATE_CONNECTING:
pMprIf0->dwConnectionState = ROUTER_IF_STATE_CONNECTING;
break; } }
//**
//
// Call: GetMprInterfaceData
//
// Returns: none
//
// Description: Given a pointer to an interface object will fill an
// MPRI_INTERFACE_* structure appropriately.
//
LPBYTE GetMprInterfaceData( IN ROUTER_INTERFACE_OBJECT * pIfObject, IN DWORD dwLevel, OUT LPDWORD lpdwcbSizeOfData ) { DWORD cbDialoutHoursRestriction = 0; DWORD dwErr; MPRI_INTERFACE_0 * pMprIf0 = NULL; MPRI_INTERFACE_1 * pIf1 = NULL; LPBYTE pInterfaceData = NULL; HANDLE hEntry = NULL;
switch ( dwLevel ) { // Basic
//
case 0: *lpdwcbSizeOfData = sizeof( MPRI_INTERFACE_0 ); dwErr = NO_ERROR; break;
// Basic plus dialout hours restriction
//
case 1: *lpdwcbSizeOfData = sizeof( MPRI_INTERFACE_1 ); if ( pIfObject->lpwsDialoutHoursRestriction != NULL ) { cbDialoutHoursRestriction = GetSizeOfDialoutHoursRestriction( pIfObject->lpwsDialoutHoursRestriction); *lpdwcbSizeOfData += cbDialoutHoursRestriction; } dwErr = NO_ERROR; break;
// Basic plus router phonebook entry info
//
case 2: dwErr = RpbkOpenEntry(pIfObject, &hEntry); if (dwErr == NO_ERROR) { dwErr = RpbkEntryToIfDataSize( hEntry, dwLevel, lpdwcbSizeOfData); } break; }
if (dwErr != NO_ERROR) { return( NULL ); } do { // Allocate the return value
pInterfaceData = MIDL_user_allocate( *lpdwcbSizeOfData ); if ( pInterfaceData == NULL ) { dwErr = ERROR_NOT_ENOUGH_MEMORY; break; }
//
// Add any appropriate information
//
switch ( dwLevel ) { case 0: GetMprInterface0Data( pIfObject, (MPRI_INTERFACE_0 *)pInterfaceData ); break;
case 1: GetMprInterface0Data( pIfObject, (MPRI_INTERFACE_0 *)pInterfaceData ); pIf1 = (MPRI_INTERFACE_1*)pInterfaceData; if ( pIfObject->lpwsDialoutHoursRestriction != NULL ) { CopyMemory( pIf1 + 1, pIfObject->lpwsDialoutHoursRestriction, cbDialoutHoursRestriction );
pIf1->dwDialoutHoursRestrictionOffset = TRUE; } else { pIf1->dwDialoutHoursRestrictionOffset = 0; } break;
case 2: GetMprInterface0Data( pIfObject, (MPRI_INTERFACE_0 *)pInterfaceData ); dwErr = RpbkEntryToIfData( hEntry, dwLevel, pInterfaceData ); break; } } while (FALSE);
// Cleanup
{ if ( dwErr != NO_ERROR ) { if ( pInterfaceData ) { MIDL_user_free( pInterfaceData ); } }
if ( hEntry ) { RpbkCloseEntry( hEntry ); } }
return( pInterfaceData ); }
//**
//
// Call: GetMprInterfaceData
//
// Returns: none
//
// Description: Given a pointer to an interface object will fill an
// MPR_INTERFACE_* structure appropriately.
//
DWORD GetMprInterfaceDeviceData( IN ROUTER_INTERFACE_OBJECT * pIfObject, IN DWORD dwIndex, IN DWORD dwLevel, OUT LPDWORD lpdwcbSizeOfData, OUT LPBYTE* lplpbReturn ) { DWORD dwErr = NO_ERROR; LPBYTE pDevData = NULL; HANDLE hSubEntry = NULL;
*lplpbReturn = NULL;
switch ( dwLevel ) { // Basic
//
case 0: *lpdwcbSizeOfData = sizeof( MPR_DEVICE_0 ); dwErr = NO_ERROR; break;
// Basic plus phone numbers
//
case 1: dwErr = RpbkOpenSubEntry(pIfObject, dwIndex, &hSubEntry); if (dwErr == NO_ERROR) { dwErr = RpbkSubEntryToDevDataSize( hSubEntry, dwLevel, lpdwcbSizeOfData); } break; }
if (dwErr != NO_ERROR) { return( dwErr ); } do { // Allocate the return value
//
pDevData = MIDL_user_allocate( *lpdwcbSizeOfData ); if ( pDevData == NULL ) { dwErr = ERROR_NOT_ENOUGH_MEMORY; break; }
//
// Add any appropriate information
//
switch ( dwLevel ) { case 0: case 1: dwErr = RpbkSubEntryToDevData( hSubEntry, dwLevel, pDevData ); break; } } while (FALSE);
// Cleanup
{ if ( hSubEntry ) { RpbkCloseSubEntry( hSubEntry ); } if ( dwErr != NO_ERROR ) { if ( pDevData ) { MIDL_user_free( pDevData ); } } else { *lplpbReturn = pDevData; } }
return( dwErr ); }
//**
//
// Call: RRouterInterfaceCreate
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_NOT_SUPPORTED
//
// Description: Creates an interface with DIM.
//
DWORD RRouterInterfaceCreate( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN LPDWORD phInterface ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject; DWORD IfState; DWORD dwRetCode = NO_ERROR; LPWSTR lpwsDialoutHoursRestriction = NULL; BOOL fLANInterfaceAdded = FALSE; MPRI_INTERFACE_0 * pMprIf0; MPRI_INTERFACE_1 * pMprIf1; MPRI_INTERFACE_2 * pMprIf2;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwLevel > 2 ) { return( ERROR_NOT_SUPPORTED ); }
if ( ( pInfoStruct == NULL ) || ( pInfoStruct->dwBufferSize == 0 ) || ( pInfoStruct->pBuffer == NULL ) ) { return( ERROR_INVALID_PARAMETER ); }
pMprIf0 = (MPRI_INTERFACE_0*) pInfoStruct->pBuffer;
pMprIf1 = (MPRI_INTERFACE_1*) pInfoStruct->pBuffer;
pMprIf2 = (MPRI_INTERFACE_2*) pInfoStruct->pBuffer;
if ( pMprIf0->dwIfType == ROUTER_IF_TYPE_TUNNEL1) { return( ERROR_NOT_SUPPORTED ); }
//
// Adjust the given buffer for any pointers to
// variable length data.
//
InterfaceAjustVLSPointers ( dwLevel, pInfoStruct->pBuffer ); if ( ( pMprIf0->dwIfType == ROUTER_IF_TYPE_DEDICATED ) || ( pMprIf0->dwIfType == ROUTER_IF_TYPE_INTERNAL ) || ( pMprIf0->dwIfType == ROUTER_IF_TYPE_LOOPBACK ) || ( pMprIf0->dwIfType == ROUTER_IF_TYPE_TUNNEL1 ) ) { IfState = RISTATE_CONNECTED;
if ( !pMprIf0->fEnabled ) { return( ERROR_INVALID_PARAMETER ); }
//
// Update router identity object since we are adding a LAN interface
//
fLANInterfaceAdded = TRUE; } else if ( ( pMprIf0->dwIfType == ROUTER_IF_TYPE_CLIENT ) || ( pMprIf0->dwIfType == ROUTER_IF_TYPE_HOME_ROUTER ) || ( pMprIf0->dwIfType == ROUTER_IF_TYPE_FULL_ROUTER ) ) { if ( gblDIMConfigInfo.dwRouterRole == ROUTER_ROLE_LAN ) { return( ERROR_DDM_NOT_RUNNING ); } else { IfState = RISTATE_DISCONNECTED; } } else { return( ERROR_INVALID_PARAMETER ); }
if ( dwLevel == 1 ) { if ( pMprIf1->dwDialoutHoursRestrictionOffset != 0 ) { DWORD cbDialoutHoursRestriction;
cbDialoutHoursRestriction = GetSizeOfDialoutHoursRestriction((LPWSTR)(pMprIf1 + 1));
DIMTRACE1( "Creating l1 interface with %d bytes of dohr", cbDialoutHoursRestriction);
lpwsDialoutHoursRestriction = LOCAL_ALLOC( LPTR, cbDialoutHoursRestriction );
if ( lpwsDialoutHoursRestriction == NULL ) { return( ERROR_NOT_ENOUGH_MEMORY ); } } }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( pMprIf0->dwIfType != ROUTER_IF_TYPE_CLIENT ) { //
// Check for duplicates if we are not adding a client interface
//
pIfObject = IfObjectGetPointerByName( pMprIf0->wszInterfaceName, FALSE );
if ( pIfObject != NULL ) { dwRetCode = ERROR_INTERFACE_ALREADY_EXISTS;
break; } }
//
// If phonebook information is being specified, set it
// before continuing
//
if (dwLevel == 2) { dwRetCode = RpbkSetEntry(dwLevel, (LPBYTE)pMprIf2); if (dwRetCode != NO_ERROR) { break; } }
pIfObject = IfObjectAllocateAndInit( pMprIf0->wszInterfaceName, IfState, pMprIf0->dwIfType, (HCONN)0, pMprIf0->fEnabled, 600, 21600, lpwsDialoutHoursRestriction, NULL);
if ( pIfObject == NULL ) { dwRetCode = GetLastError();
break; }
if ( ( dwRetCode = IfObjectInsertInTable( pIfObject ) ) != NO_ERROR ) { LOCAL_FREE( pIfObject );
break; }
*phInterface = PtrToUlong(pIfObject->hDIMInterface);
if ( lpwsDialoutHoursRestriction != NULL ) { VOID (*IfObjectSetDialoutHoursRestriction)( ROUTER_INTERFACE_OBJECT * ) = (VOID(*)( ROUTER_INTERFACE_OBJECT *)) GetDDMEntryPoint("IfObjectSetDialoutHoursRestriction");
//
// Set dialout hours restriction if there was one
//
IfObjectSetDialoutHoursRestriction( pIfObject ); }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceCreate returned %d", dwRetCode );
if ( dwRetCode != NO_ERROR ) { if ( lpwsDialoutHoursRestriction != NULL ) { //
// If there was some error then free this memory
//
LOCAL_FREE( lpwsDialoutHoursRestriction ); } } else { if ( fLANInterfaceAdded ) { //
// Can only call this API while not holding the interface lock
//
RouterIdentityObjectUpdateAttributes( FALSE, FALSE ); } }
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceGetInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_NOT_SUPPORTED
//
// Description: Gets information about a DIM interface.
//
DWORD RRouterInterfaceGetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD hInterface ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject; DWORD dwRetCode = NO_ERROR;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( ( (int) dwLevel < 0 ) || ( dwLevel > 2 ) ) { return( ERROR_NOT_SUPPORTED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
// pmay: 274487
//
// Validate the type of the interface against the level
//
if ( ( dwLevel == 2 ) && ( pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER ) ) { dwRetCode = ERROR_INVALID_LEVEL;
break; }
pInfoStruct->pBuffer = GetMprInterfaceData( pIfObject, dwLevel, &(pInfoStruct->dwBufferSize) );
if ( pInfoStruct->pBuffer == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY;
break; }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceSetInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_NOT_SUPPORTED
//
// Description: Sets interface configuration information
//
DWORD RRouterInterfaceSetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD hInterface ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject; DWORD IfState; DWORD dwRetCode = NO_ERROR; BOOL fNotify = FALSE; DWORD dwIndex; MPRI_INTERFACE_0 * pMprIf0 = (MPRI_INTERFACE_0*)pInfoStruct->pBuffer; MPRI_INTERFACE_1 * pMprIf1 = (MPRI_INTERFACE_1*)pInfoStruct->pBuffer; MPRI_INTERFACE_2 * pMprIf2 = (MPRI_INTERFACE_2*)pInfoStruct->pBuffer; //
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( ( (int) dwLevel < 0 ) || ( dwLevel > 2 ) ) { return( ERROR_NOT_SUPPORTED ); }
//
// Adjust the given buffer for any pointers to
// variable length data.
//
InterfaceAjustVLSPointers ( dwLevel, pInfoStruct->pBuffer ); EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
if ( ( pIfObject->IfType == ROUTER_IF_TYPE_DEDICATED ) || ( pIfObject->IfType == ROUTER_IF_TYPE_TUNNEL1 ) || ( pIfObject->IfType == ROUTER_IF_TYPE_INTERNAL ) ) { if ( !pMprIf0->fEnabled ) { dwRetCode = ERROR_INVALID_PARAMETER; }
//
// Nothing can be set for these interfaces
//
break; }
if ( pMprIf0->fEnabled ) { if ( !( pIfObject->fFlags & IFFLAG_ENABLED ) ) { pIfObject->fFlags |= IFFLAG_ENABLED;
fNotify = TRUE; } } else { if ( pIfObject->fFlags & IFFLAG_ENABLED ) { pIfObject->fFlags &= ~IFFLAG_ENABLED;
fNotify = TRUE; }
if ( pIfObject->State != RISTATE_DISCONNECTED ) { fNotify = FALSE; } }
if ( fNotify ) { VOID (*IfObjectNotifyOfReachabilityChange)( ROUTER_INTERFACE_OBJECT *, BOOL, UNREACHABILITY_REASON ) = (VOID(*)( ROUTER_INTERFACE_OBJECT *, BOOL, UNREACHABILITY_REASON )) GetDDMEntryPoint("IfObjectNotifyOfReachabilityChange");
if(NULL != IfObjectNotifyOfReachabilityChange) { IfObjectNotifyOfReachabilityChange( pIfObject, pMprIf0->fEnabled, INTERFACE_DISABLED ); } }
//
// Check level 1 values
//
if ( dwLevel == 1 ) { VOID (*IfObjectSetDialoutHoursRestriction)( ROUTER_INTERFACE_OBJECT * ) = (VOID(*)( ROUTER_INTERFACE_OBJECT *)) GetDDMEntryPoint("IfObjectSetDialoutHoursRestriction");
if ( pMprIf1->dwDialoutHoursRestrictionOffset == 0 ) { if ( pIfObject->lpwsDialoutHoursRestriction != NULL ) { LOCAL_FREE( pIfObject->lpwsDialoutHoursRestriction );
pIfObject->lpwsDialoutHoursRestriction = NULL;
IfObjectSetDialoutHoursRestriction( pIfObject ); } } else { DWORD cbDialoutHoursRestriction = GetSizeOfDialoutHoursRestriction( (LPWSTR)(pMprIf1 + 1) );
if ( pIfObject->lpwsDialoutHoursRestriction != NULL ) { //
// Free currently allocated memory for dialout hours
//
LOCAL_FREE( pIfObject->lpwsDialoutHoursRestriction );
pIfObject->lpwsDialoutHoursRestriction = NULL; }
DIMTRACE1( "Setting info on l1 interface. %d bytes dohr", cbDialoutHoursRestriction);
pIfObject->lpwsDialoutHoursRestriction = LOCAL_ALLOC( LPTR, cbDialoutHoursRestriction );
if ( pIfObject->lpwsDialoutHoursRestriction == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY; break; }
CopyMemory( pIfObject->lpwsDialoutHoursRestriction, (LPBYTE)(pMprIf1 + 1), cbDialoutHoursRestriction );
IfObjectSetDialoutHoursRestriction( pIfObject ); } }
//
// Check level 2 values
//
else if ( dwLevel == 2 ) { if (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER) { dwRetCode = ERROR_INVALID_PARAMETER; } else { dwRetCode = RpbkSetEntry(dwLevel, (LPBYTE)pMprIf2); } } }while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceSetInfo returned %d", dwRetCode );
return( dwRetCode ); }
DWORD RRouterInterfaceDeviceGetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD dwIndex, IN DWORD hInterface ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject; DWORD dwRetCode = NO_ERROR;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( ( (int) dwLevel < 0 ) || ( dwLevel > 1 ) ) { return( ERROR_NOT_SUPPORTED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
dwRetCode = GetMprInterfaceDeviceData( pIfObject, dwIndex, dwLevel, &(pInfoStruct->dwBufferSize), &(pInfoStruct->pBuffer));
if ( dwRetCode != NO_ERROR ) { if ( dwRetCode == ERROR_CANNOT_FIND_PHONEBOOK_ENTRY ) { dwRetCode = ERROR_DEV_NOT_EXIST; } break; }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
/*TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS,
"InterfaceDeviceGetInfo returned %d", dwRetCode );*/
return( dwRetCode ); } DWORD RRouterInterfaceDeviceSetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD dwIndex, IN DWORD hInterface ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject; DWORD dwRetCode = NO_ERROR; MPR_DEVICE_0 * pDev0 = (MPR_DEVICE_0*)pInfoStruct->pBuffer; MPR_DEVICE_1 * pDev1 = (MPR_DEVICE_1*)pInfoStruct->pBuffer;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( ( (int) dwLevel < 0 ) || ( dwLevel > 1 ) ) { return( ERROR_NOT_SUPPORTED ); }
// Adjust the variable-length structure pointers
//
if ( dwLevel == 1 ) { if ( pDev1->szAlternates ) { pDev1->szAlternates = (PWCHAR)(pDev1 + 1); } }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// Set the subentry
//
if (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER) { dwRetCode = ERROR_INVALID_PARAMETER; } else { dwRetCode = RpbkSetSubEntry( pIfObject->lpwsInterfaceName, dwIndex, dwLevel, pInfoStruct->pBuffer); } }while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceDeviceSetInfo returned %d", dwRetCode );
return( dwRetCode ); } //**
//
// Call: RRouterInterfaceGetHandle
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
//
// Description:
//
DWORD RRouterInterfaceGetHandle( IN MPR_SERVER_HANDLE hMprServer, IN LPWSTR lpwsInterfaceName, IN LPDWORD phInterface, IN DWORD fIncludeClientInterfaces ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { pIfObject = IfObjectGetPointerByName( lpwsInterfaceName, fIncludeClientInterfaces );
if ( pIfObject == NULL ) { dwRetCode = ERROR_NO_SUCH_INTERFACE;
break; }
*phInterface = PtrToUlong(pIfObject->hDIMInterface);
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceDelete
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
//
// Description: Deletes and interface from the DIM database.
// work.
//
DWORD RRouterInterfaceDelete( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hInterface ) { DWORD dwAccessStatus; DWORD dwTransportIndex; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR; BOOL fLANInterfaceRemoved = FALSE; BOOL fDeletePbkEntry = FALSE; //
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// If this is a demand dial dynamic interface then we cannot delete
// it if it is connected.
//
if ( ( pIfObject->IfType == ROUTER_IF_TYPE_CLIENT ) || ( pIfObject->IfType == ROUTER_IF_TYPE_HOME_ROUTER ) || ( pIfObject->IfType == ROUTER_IF_TYPE_FULL_ROUTER ) ) { if ( pIfObject->State != RISTATE_DISCONNECTED ) { dwRetCode = ERROR_INTERFACE_CONNECTED;
break; }
fDeletePbkEntry = TRUE;
//
// Remove credentials for this interface if they were set.
//
MprAdminInterfaceSetCredentials( NULL, pIfObject->lpwsInterfaceName, NULL, NULL, NULL ); } else { //
// Update router identity object since we are removing a LAN
// interface
//
fLANInterfaceRemoved = TRUE; }
//
// Delete any transport interfaces that might still be around
//
for ( dwTransportIndex = 0; dwTransportIndex < gblDIMConfigInfo.dwNumRouterManagers; dwTransportIndex++ ) { if ( pIfObject->Transport[dwTransportIndex].hInterface != INVALID_HANDLE_VALUE ) { dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.DeleteInterface( pIfObject->Transport[dwTransportIndex].hInterface );
if ( dwRetCode != NO_ERROR ) { break; }
pIfObject->Transport[dwTransportIndex].hInterface = INVALID_HANDLE_VALUE;
pIfObject->Transport[dwTransportIndex].fState = 0; } }
if ( fDeletePbkEntry ) { RpbkDeleteEntry( pIfObject->lpwsInterfaceName ); }
IfObjectRemove( (HANDLE)UlongToPtr(hInterface) );
} while ( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
if ( ( dwRetCode == NO_ERROR ) && ( fLANInterfaceRemoved ) ) { //
// Can only call this API while not holding the interface lock
//
RouterIdentityObjectUpdateAttributes( FALSE, FALSE ); }
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "DeleteInterface returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceTransportRemove
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportRemove( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hInterface, IN DWORD dwTransportId ) { DWORD dwAccessStatus; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwTransportId );
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface)) ) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// If this is a demand dial dynamic interface then we cannot delete
// it if it is connected.
//
if ( ( pIfObject->IfType == ROUTER_IF_TYPE_CLIENT ) || ( pIfObject->IfType == ROUTER_IF_TYPE_HOME_ROUTER ) || ( pIfObject->IfType == ROUTER_IF_TYPE_FULL_ROUTER ) ) { if ( pIfObject->State == RISTATE_CONNECTED ) { dwRetCode = ERROR_INTERFACE_CONNECTED;
break; } }
//
// Remove the transport interface.
//
if ( pIfObject->Transport[dwTransportIndex].hInterface != INVALID_HANDLE_VALUE ) { dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.DeleteInterface( pIfObject->Transport[dwTransportIndex].hInterface );
if ( dwRetCode == NO_ERROR ) { pIfObject->Transport[dwTransportIndex].hInterface = INVALID_HANDLE_VALUE; } } else { dwRetCode = ERROR_NO_SUCH_INTERFACE; }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "RemoveInterface returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceTransportGetInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_UNKNOWN_PROTOCOL_ID
// ERROR_INVALID_HANDLE
// non-zero returns from GetInterfaceInfo
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportGetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hInterface, IN DWORD dwTransportId, IN DIM_INTERFACE_CONTAINER * pInfoStruct ) { DWORD dwAccessStatus = 0; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwTransportId ); ULONG ulNumAttempts;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do {
if ( ( pIfObject = IfObjectGetPointer( (HANDLE) UlongToPtr(hInterface ))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// If the interface has not been added for this protocol
//
if ( pIfObject->Transport[dwTransportIndex].hInterface == INVALID_HANDLE_VALUE ) { dwRetCode = ERROR_NO_SUCH_INTERFACE;
break; }
if ( pInfoStruct->fGetInterfaceInfo ) { ulNumAttempts = 0; pInfoStruct->pInterfaceInfo = NULL;
do { dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.GetInterfaceInfo( pIfObject->Transport[dwTransportIndex].hInterface, pInfoStruct->pInterfaceInfo, &(pInfoStruct->dwInterfaceInfoSize) );
if ( dwRetCode != ERROR_INSUFFICIENT_BUFFER ) { break; }
//
// Release previous allocation
//
if ( ulNumAttempts ) { MIDL_user_free( pInfoStruct->pInterfaceInfo ); pInfoStruct->pInterfaceInfo = NULL; } if ( pInfoStruct->dwInterfaceInfoSize > 0 ) { pInfoStruct->pInterfaceInfo = MIDL_user_allocate( pInfoStruct->dwInterfaceInfoSize);
if ( pInfoStruct->pInterfaceInfo == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY;
break; } }
else { break; }
ulNumAttempts++; } while ( (dwRetCode == ERROR_INSUFFICIENT_BUFFER) && (ulNumAttempts < MAX_GET_INFO_RETRIES) ); } } while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
/*TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS,
"InterfaceGetInfo returned %d", dwRetCode );*/
if ( !pInfoStruct->fGetInterfaceInfo ) { pInfoStruct->dwInterfaceInfoSize = 0; }
if ( dwRetCode != NO_ERROR ) { pInfoStruct->dwInterfaceInfoSize = 0; }
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceTransportAdd
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_UNKNOWN_PROTOCOL_ID
// ERROR_INVALID_HANDLE
// non-zero returns from AddInterface
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportAdd( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hInterface, IN DWORD dwTransportId, IN DIM_INTERFACE_CONTAINER * pInfoStruct ) { DWORD dwAccessStatus = 0; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR; DWORD dwIndex = GetTransportIndex( dwTransportId );
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface) )) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// If the handle to the interface is NULL, then we have to add the
// interface
//
if ( pIfObject->Transport[dwIndex].hInterface == INVALID_HANDLE_VALUE ) { if (IsInterfaceRoleAcceptable(pIfObject, dwTransportId)) { dwRetCode = gblRouterManagers[dwIndex].DdmRouterIf.AddInterface( pIfObject->lpwsInterfaceName, pInfoStruct->pInterfaceInfo, pIfObject->IfType, pIfObject->hDIMInterface, &pIfObject->Transport[dwIndex].hInterface);
if ( dwRetCode != NO_ERROR ) { pIfObject->Transport[dwIndex].hInterface = INVALID_HANDLE_VALUE; } else { if ( !( pIfObject->fFlags & IFFLAG_ENABLED ) || ( pIfObject->fFlags & IFFLAG_OUT_OF_RESOURCES ) || ( gblDIMConfigInfo.ServiceStatus.dwCurrentState == SERVICE_PAUSED)) { TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceTransportAdd: Set if to unreachable");
gblRouterManagers[dwIndex].DdmRouterIf.InterfaceNotReachable( pIfObject->Transport[dwIndex].hInterface, INTERFACE_DISABLED ); } } } else { pIfObject->Transport[dwIndex].hInterface = INVALID_HANDLE_VALUE; } } else { dwRetCode = ERROR_INTERFACE_ALREADY_EXISTS; }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceTransportAdd returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceTransportSetInfo
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_UNKNOWN_PROTOCOL_ID
// ERROR_INVALID_HANDLE
// non-zero returns from AddInterface or SetInterfaceInfo
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceTransportSetInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hInterface, IN DWORD dwTransportId, IN DIM_INTERFACE_CONTAINER * pInfoStruct ) { DWORD dwAccessStatus = 0; ROUTER_INTERFACE_OBJECT * pIfObject = NULL; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwTransportId );
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// If the handle to the interface is NULL, then we have to add the
// interface
//
if ( pIfObject->Transport[dwTransportIndex].hInterface == INVALID_HANDLE_VALUE ) { dwRetCode = ERROR_NO_SUCH_INTERFACE; } else { dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.SetInterfaceInfo( pIfObject->Transport[dwTransportIndex].hInterface, pInfoStruct->pInterfaceInfo ); }
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceSetInfo returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceEnum
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
// ERROR_NOT_SUPPORTED
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceEnum( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN OUT PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD dwPreferedMaximumLength, OUT LPDWORD lpdwEntriesRead, OUT LPDWORD lpdwTotalEntries, IN OUT LPDWORD lpdwResumeHandle OPTIONAL ) { DWORD dwAccessStatus; PMPRI_INTERFACE_0 pInterface0 = NULL; DWORD dwIfIndex = 0; DWORD dwBucketIndex= 0; PROUTER_INTERFACE_OBJECT pIfObject = NULL; DWORD dwStartIndex = ( lpdwResumeHandle == NULL ) ? 0 : *lpdwResumeHandle; //
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwLevel != 0 ) { return( ERROR_NOT_SUPPORTED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
if ( gblInterfaceTable.dwNumTotalInterfaces < dwStartIndex ) { LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( ERROR_NO_MORE_ITEMS ); }
*lpdwTotalEntries = gblInterfaceTable.dwNumTotalInterfaces - dwStartIndex;
if ( dwPreferedMaximumLength != -1 ) { *lpdwEntriesRead = dwPreferedMaximumLength / sizeof( MPR_INTERFACE_0 );
if ( *lpdwEntriesRead > *lpdwTotalEntries ) { *lpdwEntriesRead = *lpdwTotalEntries; } } else { *lpdwEntriesRead = *lpdwTotalEntries; }
pInfoStruct->dwBufferSize = *lpdwEntriesRead * sizeof( MPR_INTERFACE_0 );
pInfoStruct->pBuffer = MIDL_user_allocate( pInfoStruct->dwBufferSize );
if ( pInfoStruct->pBuffer == NULL ) { LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
pInfoStruct->dwBufferSize = 0;
return( ERROR_NOT_ENOUGH_MEMORY ); }
pInterface0 = (PMPRI_INTERFACE_0)pInfoStruct->pBuffer;
for ( dwBucketIndex = 0; dwBucketIndex < NUM_IF_BUCKETS; dwBucketIndex++ ) { for( pIfObject = gblInterfaceTable.IfBucket[dwBucketIndex]; pIfObject != (ROUTER_INTERFACE_OBJECT *)NULL; pIfObject = pIfObject->pNext ) { //
// Check if this interface is within the range we need to copy
// from.
//
if ( ( dwIfIndex >= dwStartIndex ) && ( dwIfIndex < ( dwStartIndex + *lpdwEntriesRead ) ) ) { //
// Copy the info
//
GetMprInterface0Data( pIfObject, pInterface0 );
pInterface0++; } else if ( dwIfIndex >= (dwStartIndex+*lpdwEntriesRead) ) { //
// Beyond the range so exit
//
if ( lpdwResumeHandle != NULL ) { *lpdwResumeHandle = dwIfIndex; }
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( ERROR_MORE_DATA ); }
dwIfIndex++; } }
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( NO_ERROR ); }
//**
//
// Call: RRouterInterfaceUpdateRoutes
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceUpdateRoutes( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hDimInterface, IN DWORD dwPid, IN ULONG_PTR hEvent, IN DWORD dwCallersProcessId ) { DWORD dwAccessStatus; PROUTER_INTERFACE_OBJECT pIfObject = NULL; HANDLE hEventDuplicated; HANDLE hEventToBeDuplicated; HANDLE hClientProcess; DWORD dwRetCode = NO_ERROR; DWORD dwTransportIndex = GetTransportIndex( dwPid );
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
if ( hEvent == PtrToUlong(NULL) ) { //
// This call is to be synchrnonous, create an event and block on
// it.
//
hEventToBeDuplicated = CreateEvent( NULL, FALSE, FALSE, NULL );
if ( hEventToBeDuplicated == NULL ) { return( GetLastError() ); }
dwCallersProcessId = GetCurrentProcessId(); } else { hEventToBeDuplicated = (HANDLE)hEvent; }
//
// Get process handle of the caller of this API
//
hClientProcess = OpenProcess( STANDARD_RIGHTS_REQUIRED | SPECIFIC_RIGHTS_ALL, FALSE, dwCallersProcessId);
if ( hClientProcess == NULL ) { return( GetLastError() ); }
//
// Duplicate the handle to the event
//
if ( !DuplicateHandle( hClientProcess, (HANDLE)hEventToBeDuplicated, GetCurrentProcess(), &hEventDuplicated, 0, FALSE, DUPLICATE_SAME_ACCESS ) ) { CloseHandle( hClientProcess );
return( GetLastError() ); }
CloseHandle( hClientProcess );
//
// Validate the interface handle and check to see if it is connected
//
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hDimInterface))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
if ( pIfObject->State != RISTATE_CONNECTED ) { dwRetCode = ERROR_INTERFACE_NOT_CONNECTED;
break; }
//
// Make sure the handle to the interface is NULL, then the interface
// has not yet been added to the transport.
//
if ( pIfObject->Transport[dwTransportIndex].hInterface == INVALID_HANDLE_VALUE ) { dwRetCode = ERROR_NO_SUCH_INTERFACE;
break; }
dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.UpdateRoutes( pIfObject->Transport[dwTransportIndex].hInterface, (HANDLE)hEventDuplicated );
} while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
if ( ( dwRetCode != NO_ERROR ) && ( dwRetCode != PENDING ) ) { CloseHandle( hEventDuplicated ); }
if ( hEvent == PtrToUlong(NULL) ) { if ( ( dwRetCode == NO_ERROR ) || ( dwRetCode == PENDING ) ) { //
// Wait for this event to be signalled
//
if ( WaitForSingleObject( hEventToBeDuplicated, INFINITE ) == WAIT_FAILED ) { dwRetCode = GetLastError(); } }
CloseHandle( hEventToBeDuplicated );
if ( dwRetCode == PENDING ) { dwRetCode = NO_ERROR; } }
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceUpdateRoutes returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceQueryUpdateResult
//
// Returns: NO_ERROR - Success
// ERROR_ACCESS_DENIED - FAILURE
//
//
// Description: Simply called the appropriate router manager to do the real
// work.
//
DWORD RRouterInterfaceQueryUpdateResult( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hDimInterface, IN DWORD dwPid, IN LPDWORD pUpdateResult ) { DWORD dwAccessStatus; DWORD dwRetCode = NO_ERROR; PROUTER_INTERFACE_OBJECT pIfObject = NULL; DWORD dwTransportIndex = GetTransportIndex( dwPid );
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( dwTransportIndex == (DWORD)-1 ) { return( ERROR_UNKNOWN_PROTOCOL_ID ); }
//
// Validate the interface handle and check to see if it is connected
//
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hDimInterface))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
if ( pIfObject->State != RISTATE_CONNECTED ) { dwRetCode = ERROR_INTERFACE_NOT_CONNECTED;
break; }
//
// Make sure the handle to the interface is NULL, then the interface
// has not yet been added to the transport.
//
if ( pIfObject->Transport[dwTransportIndex].hInterface == INVALID_HANDLE_VALUE ) { dwRetCode = ERROR_NO_SUCH_INTERFACE;
break; }
dwRetCode = gblRouterManagers[dwTransportIndex].DdmRouterIf.GetUpdateRoutesResult( pIfObject->Transport[dwTransportIndex].hInterface, pUpdateResult );
}while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "QueryUpdateResult returned %d", dwRetCode );
return( dwRetCode ); }
//**
//
// Call: RRouterInterfaceConnect
//
// Returns: ERROR_ACCESS_DENIED - The caller does not have sufficient priv.
// ERROR_DDM_NOT_RUNNING - This call cannot be made because DDM is
// not loaded
// non-zero returns from DDMAdminInterfaceConnect
//
// Description: Simply calles into DDM to do the work.
//
DWORD RRouterInterfaceConnect( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hDimInterface, IN ULONG_PTR hEvent, IN DWORD fBlocking, IN DWORD dwCallersProcessId ) { DWORD dwAccessStatus;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR ) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( gblDIMConfigInfo.dwRouterRole == ROUTER_ROLE_LAN ) { return( ERROR_DDM_NOT_RUNNING ); } else { DWORD (*DDMAdminInterfaceConnect)( HANDLE, HANDLE, BOOL, DWORD ) = (DWORD(*)( HANDLE, HANDLE, BOOL, DWORD ) ) GetDDMEntryPoint("DDMAdminInterfaceConnect");
if(NULL == DDMAdminInterfaceConnect) { return ERROR_PROC_NOT_FOUND; }
return( DDMAdminInterfaceConnect( DimIndexToHandle(hDimInterface), (HANDLE)hEvent, (BOOL)fBlocking, (DWORD)dwCallersProcessId ) ); } }
//**
//
// Call: RRouterInterfaceDisconnect
//
// Returns: ERROR_ACCESS_DENIED - The caller does not have sufficient priv.
// ERROR_DDM_NOT_RUNNING - This call cannot be made because DDM is
// not loaded
// non-zero returns from DDMAdminInterfaceDisconnect
//
// Description: Simply calles into DDM to do the work.
//
DWORD RRouterInterfaceDisconnect( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hDimInterface ) { DWORD dwAccessStatus;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR ) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( gblDIMConfigInfo.dwRouterRole == ROUTER_ROLE_LAN ) { return( ERROR_DDM_NOT_RUNNING ); } else { DWORD (*DDMAdminInterfaceDisconnect)( HANDLE ) = (DWORD(*)( HANDLE ) )GetDDMEntryPoint("DDMAdminInterfaceDisconnect");
if(NULL == DDMAdminInterfaceDisconnect) { return ERROR_PROC_NOT_FOUND; }
return( DDMAdminInterfaceDisconnect( DimIndexToHandle(hDimInterface) ) ); } }
//**
//
// Call: RRouterInterfaceUpdatePhonebookInfo
//
// Returns: NO_ERROR - Success
/// ERROR_ACCESS_DENIED - The caller does not have sufficient priv.
// non-zero returns
//
// Description: Will update the phonebook information for a given interface
//
DWORD RRouterInterfaceUpdatePhonebookInfo( IN MPR_SERVER_HANDLE hMprServer, IN DWORD hDimInterface ) { DWORD dwAccessStatus; DWORD dwRetCode; PROUTER_INTERFACE_OBJECT pIfObject = NULL;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR ) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( gblDIMConfigInfo.dwRouterRole == ROUTER_ROLE_LAN ) { return( ERROR_DDM_NOT_RUNNING ); }
//
// Validate the interface handle and check to see if it is connected
//
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { DWORD (*IfObjectLoadPhonebookInfo)( ROUTER_INTERFACE_OBJECT *, VOID * ) = (DWORD(*)( ROUTER_INTERFACE_OBJECT *, VOID * )) GetDDMEntryPoint("IfObjectLoadPhonebookInfo");
if(NULL == IfObjectLoadPhonebookInfo) { dwRetCode = ERROR_PROC_NOT_FOUND; break; }
if ( ( pIfObject = IfObjectGetPointer( DimIndexToHandle(hDimInterface))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE;
break; }
//
// Load phonebook information for this interface
//
dwRetCode = IfObjectLoadPhonebookInfo( pIfObject, NULL );
} while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
return( dwRetCode ); }
DWORD RRouterInterfaceSetCredentialsEx( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD hInterface ) { ROUTER_INTERFACE_OBJECT * pIfObject = NULL; PWCHAR pszPath = NULL; DWORD dwAccessStatus; DWORD dwRetCode = NO_ERROR; MPR_CREDENTIALSEX_0 * pCredsEx0 = NULL;
MPR_CREDENTIALSEX_1 * pCredsEx1 = NULL;
MPR_CREDENTIALSEXI * pCredsI = NULL;
//
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( (dwLevel != 0 ) && (dwLevel != 1 ) && (dwLevel != 2 )) { return( ERROR_NOT_SUPPORTED ); }
if ( ( pInfoStruct == NULL ) || ( pInfoStruct->dwBufferSize == 0 ) || ( pInfoStruct->pBuffer == NULL ) ) { return( ERROR_INVALID_PARAMETER ); } pCredsI = (MPR_CREDENTIALSEXI *) pInfoStruct->pBuffer;
//
// Adjust the given buffer for any pointers to
// variable length data.
//
if ( dwLevel == 0 ) { //
// Thunk the credentials structure
//
pCredsEx0 = LOCAL_ALLOC(LPTR, pCredsI->dwSize + sizeof(MPR_CREDENTIALSEX_0));
if(pCredsEx0 == NULL) { return ERROR_NOT_ENOUGH_MEMORY; } pCredsEx0->dwSize = pCredsI->dwSize; pCredsEx0->lpbCredentialsInfo = (PBYTE) (pCredsEx0 + 1); CopyMemory(pCredsEx0->lpbCredentialsInfo, ((PBYTE) pCredsI) + pCredsI->dwOffset, pCredsI->dwSize);
}
if( ( dwLevel == 1 ) || ( dwLevel == 2 )) {
//
// Thunk the credentials structure
//
pCredsEx1 = LOCAL_ALLOC(LPTR, pCredsI->dwSize + sizeof(MPR_CREDENTIALSEX_1));
if(pCredsEx1 == NULL) { return ERROR_NOT_ENOUGH_MEMORY; } pCredsEx1->dwSize = pCredsI->dwSize; pCredsEx1->lpbCredentialsInfo = (PBYTE) (pCredsEx1 + 1); CopyMemory(pCredsEx1->lpbCredentialsInfo, ((PBYTE) pCredsI) + pCredsI->dwOffset, pCredsI->dwSize); } EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if (( 2 != dwLevel ) && ( pIfObject = IfObjectGetPointer(DimIndexToHandle(hInterface))) == NULL ) { dwRetCode = ERROR_INVALID_HANDLE; break; }
//
// Process Level 0
//
if ( dwLevel == 0 ) { if (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER) { dwRetCode = ERROR_INVALID_PARAMETER; break; }
dwRetCode = RpbkGetPhonebookPath( &pszPath ); if ( dwRetCode != NO_ERROR) { break; } dwRetCode = RasSetEapUserDataW( NULL, pszPath, pIfObject->lpwsInterfaceName, pCredsEx0->lpbCredentialsInfo, pCredsEx0->dwSize); }
//
// Process Levels 1 and 2
//
if (( dwLevel == 1 ) || ( dwLevel == 2 )) { HANDLE hEntry = NULL; if( ((NULL != pIfObject) && (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER)) || (pCredsEx1->dwSize > (PWLEN+1) * sizeof(WCHAR))) { dwRetCode = ERROR_INVALID_PARAMETER; break; }
dwRetCode = RpbkGetPhonebookPath (&pszPath); if( dwRetCode != NO_ERROR ) { break; } { RASCREDENTIALS rasCredentials;
ZeroMemory(&rasCredentials, sizeof(RASCREDENTIALS));
rasCredentials.dwSize = sizeof(RASCREDENTIALS);
if(dwLevel == 1) { rasCredentials.dwMask = RASCM_DDMPreSharedKey; } else if(dwLevel == 2) { rasCredentials.dwMask = RASCM_ServerPreSharedKey; }
memcpy((PBYTE) &rasCredentials.szPassword, pCredsEx1->lpbCredentialsInfo, pCredsEx1->dwSize); //
// Call Ras api to set the credentials.
//
dwRetCode = RasSetCredentials( pszPath, (NULL != pIfObject) ? pIfObject->lpwsInterfaceName : NULL, &rasCredentials, (pCredsEx1->dwSize == 0) ? TRUE : FALSE);
//
// If these are server credentials, the set might fail
// because of no listens being posted on l2tp ports.
// Attempt to post listens on l2tp ports now that we
// have a preshared key.
//
if( (ERROR_IPSEC_MM_AUTH_NOT_FOUND == dwRetCode) && (pCredsEx1->dwSize > 0) && (dwLevel == 2)) { VOID (*DDMServicePostListens)(VOID *);
DDMServicePostListens = (VOID(*)(VOID *)) GetDDMEntryPoint("DDMServicePostListens"); if(DDMServicePostListens != NULL) { DWORD rdt = RDT_Tunnel_L2tp;
DDMServicePostListens((VOID *) &rdt);
dwRetCode = ERROR_SUCCESS; } } } } } while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
// Cleanup
{ if ( pszPath ) { RpbkFreePhonebookPath( pszPath ); }
if(pCredsEx0) { SecureZeroMemory(pCredsEx0, sizeof(*pCredsEx0)); LOCAL_FREE(pCredsEx0); }
if(pCredsEx1) { SecureZeroMemory(pCredsEx1, sizeof(*pCredsEx1)); LOCAL_FREE(pCredsEx1); } } TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceSetCredEx returned %d", dwRetCode );
return( dwRetCode ); }
DWORD RRouterInterfaceGetCredentialsEx( IN MPR_SERVER_HANDLE hMprServer, IN DWORD dwLevel, IN PDIM_INFORMATION_CONTAINER pInfoStruct, IN DWORD hInterface ) { ROUTER_INTERFACE_OBJECT * pIfObject = NULL; PWCHAR pszPath = NULL; DWORD dwAccessStatus; DWORD dwRetCode = NO_ERROR, dwSize = 0; MPR_CREDENTIALSEXI * pCredsI = NULL; //
// Check if caller has access
//
if ( DimSecObjAccessCheck( DIMSVC_ALL_ACCESS, &dwAccessStatus) != NO_ERROR) { return( ERROR_ACCESS_DENIED ); }
if ( dwAccessStatus ) { return( ERROR_ACCESS_DENIED ); }
if ( (dwLevel != 0 ) && (dwLevel != 1 ) && (dwLevel != 2 )) { return( ERROR_NOT_SUPPORTED ); }
EnterCriticalSection( &(gblInterfaceTable.CriticalSection) );
do { if ( (dwLevel != 2) && (( pIfObject = IfObjectGetPointer( DimIndexToHandle(hInterface))) == NULL )) { dwRetCode = ERROR_INVALID_HANDLE; break; }
//
// Process Level 0
//
if ( dwLevel == 0 ) { if (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER) { dwRetCode = ERROR_INVALID_PARAMETER; break; }
dwRetCode = RpbkGetPhonebookPath( &pszPath ); if ( dwRetCode != NO_ERROR) { break; }
// Find out how big the data is
//
dwSize = 0; dwRetCode = RasGetEapUserDataW( NULL, pszPath, pIfObject->lpwsInterfaceName, NULL, &dwSize); if ( (dwRetCode != NO_ERROR) && (dwRetCode != ERROR_BUFFER_TOO_SMALL) ) { break; }
// Allocate the return value
//
pCredsI = (MPR_CREDENTIALSEXI *) MIDL_user_allocate(dwSize + sizeof(MPR_CREDENTIALSEXI)); if ( pCredsI == NULL ) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY; break; }
// Initialize
ZeroMemory(pCredsI, dwSize + sizeof(MPR_CREDENTIALSEXI)); pCredsI->dwSize = dwSize; pCredsI->dwOffset = FIELD_OFFSET(MPR_CREDENTIALSEXI, bData); if ( pCredsI->dwSize == 0) { dwRetCode = NO_ERROR; break; } // Read in the credentials info
//
// pCredsEx0->lpbCredentialsInfo = (BYTE*) (pCredsEx0 + 1);
dwRetCode = RasGetEapUserDataW( NULL, pszPath, pIfObject->lpwsInterfaceName, pCredsI->bData, &dwSize); if ( dwRetCode != NO_ERROR ) { break; } } else if( (dwLevel == 1 ) || (dwLevel == 2)) { RASCREDENTIALS rasCredentials; if ( (dwLevel != 2) && (pIfObject->IfType != ROUTER_IF_TYPE_FULL_ROUTER)) { dwRetCode = ERROR_INVALID_PARAMETER; break; }
dwRetCode = RpbkGetPhonebookPath( &pszPath ); if ( dwRetCode != NO_ERROR) { break; }
ZeroMemory(&rasCredentials, sizeof(RASCREDENTIALS));
rasCredentials.dwSize = sizeof(RASCREDENTIALS);
if(dwLevel == 1) { rasCredentials.dwMask = RASCM_DDMPreSharedKey; } else if(dwLevel == 2) { rasCredentials.dwMask = RASCM_ServerPreSharedKey; }
dwRetCode = RasGetCredentials( pszPath, (NULL != pIfObject) ? pIfObject->lpwsInterfaceName : NULL, &rasCredentials);
if(dwRetCode != NO_ERROR) { break; }
dwSize = (1 + wcslen(rasCredentials.szPassword)) * sizeof(WCHAR);
//
// allocate for pCredsEx1
//
pCredsI = (MPR_CREDENTIALSEXI *) MIDL_user_allocate(dwSize + sizeof(MPR_CREDENTIALSEXI)); if(NULL == pCredsI) { dwRetCode = ERROR_NOT_ENOUGH_MEMORY; break; }
ZeroMemory(pCredsI, dwSize + sizeof(MPR_CREDENTIALSEXI)); pCredsI->dwSize = dwSize; pCredsI->dwOffset = FIELD_OFFSET(MPR_CREDENTIALSEXI, bData); CopyMemory((pCredsI->bData), (PBYTE) rasCredentials.szPassword, dwSize); SecureZeroMemory(&rasCredentials, sizeof(RASCREDENTIALS)); } } while( FALSE );
LeaveCriticalSection( &(gblInterfaceTable.CriticalSection) );
// Assign the return value
//
if ( dwRetCode == NO_ERROR ) {
pInfoStruct->pBuffer = (BYTE*)pCredsI; pInfoStruct->dwBufferSize = sizeof(MPR_CREDENTIALSEXI) + pCredsI->dwSize; } // Cleanup
{ if ( pszPath ) { RpbkFreePhonebookPath( pszPath ); } } TracePrintfExA( gblDIMConfigInfo.dwTraceId, DIM_TRACE_FLAGS, "InterfaceSetCredEx returned %d", dwRetCode );
return( dwRetCode ); }
|