|
|
/*
*============================================================================ * Copyright (c) 1994-95, Microsoft Corp. * * File: map.c * * Routes can be added to and deleted from the IP routing table by other * means. Therefore, it is necessary for any protocol using these functions * to reload the routing tables periodically. *============================================================================ */
#include "pchrip.h"
#pragma hdrstop
//----------------------------------------------------------------------------
// GetIpAddressTable
//
// This function retrieves the list of addresses for the logical interfaces
// configured on this system.
//----------------------------------------------------------------------------
DWORD GetIPAddressTable( OUT PMIB_IPADDRROW *lplpAddrTable, OUT LPDWORD lpdwAddrCount ) {
DWORD dwSize = 0, dwErr = 0; PMIB_IPADDRTABLE pmiatTable = NULL;
*lplpAddrTable = NULL; *lpdwAddrCount = 0;
do {
//
// retrieve ip address table. First call to find size of
// structure to be allocated.
//
dwErr = GetIpAddrTable( pmiatTable, &dwSize, TRUE );
if ( dwErr != ERROR_INSUFFICIENT_BUFFER ) { dbgprintf( "GetIpAddrTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_ADDR_INIT_FAILED, 0, NULL, dwErr );
break; }
//
// allocate requiste buffer
//
pmiatTable = HeapAlloc( GetProcessHeap(), 0 , dwSize );
if ( pmiatTable == NULL ) { dwErr = ERROR_NOT_ENOUGH_MEMORY; dbgprintf( "GetIpAddrTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_ADDR_ALLOC_FAILED, 0, NULL, dwErr );
break; }
//
// now retrieve address table
//
dwErr = GetIpAddrTable( pmiatTable, &dwSize, TRUE ); if ( dwErr != NO_ERROR ) { dbgprintf( "GetIpAddrTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_ADDR_INIT_FAILED, 0, NULL, dwErr );
break; }
*lpdwAddrCount = pmiatTable-> dwNumEntries;
*lplpAddrTable = pmiatTable-> table;
return NO_ERROR; } while ( FALSE );
//
// Error condition
//
if ( pmiatTable ) { HeapFree( GetProcessHeap(), 0, pmiatTable ); }
return dwErr; }
//----------------------------------------------------------------------------
// FreeIPAddressTable
//
// This function releases the memory allocated for the IP address table by
// the GetIpAddressTable API.
//----------------------------------------------------------------------------
DWORD FreeIPAddressTable( IN PMIB_IPADDRROW lpAddrTable ) {
PMIB_IPADDRTABLE pmiatTable = NULL;
pmiatTable = CONTAINING_RECORD( lpAddrTable, MIB_IPADDRTABLE, table );
if ( pmiatTable != NULL ) { HeapFree( GetProcessHeap(), 0, pmiatTable );
return NO_ERROR; }
return ERROR_INVALID_PARAMETER; }
//----------------------------------------------------------------------------
// GetRouteTable
//
// This function retrieves the route table.
//----------------------------------------------------------------------------
DWORD GetRouteTable( OUT LPIPROUTE_ENTRY *lplpRouteTable, OUT LPDWORD lpdwRouteCount ) {
DWORD dwErr = (DWORD) -1, dwSize = 0; PMIB_IPFORWARDTABLE pmiftTable = NULL;
*lplpRouteTable = NULL; *lpdwRouteCount = 0;
do {
//
// get size of buffer required.
//
dwErr = GetIpForwardTable( pmiftTable, &dwSize, TRUE );
if ( dwErr != ERROR_INSUFFICIENT_BUFFER ) { dbgprintf( "GetIpNetTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_ROUTEINIT_FAILED, 0, NULL, dwErr );
break; }
//
// allocate requiste buffer space
//
pmiftTable = HeapAlloc( GetProcessHeap(), 0, dwSize );
if ( pmiftTable == NULL ) { dwErr = ERROR_NOT_ENOUGH_MEMORY; dbgprintf( "GetIpAddrTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_RTAB_INIT_FAILED, 0, NULL, dwErr );
break; }
//
// now retrieve route table
//
dwErr = GetIpForwardTable( pmiftTable, &dwSize, TRUE ); if ( dwErr != NO_ERROR ) { dbgprintf( "GetIpNetTable failed with error %x\n", dwErr );
RipLogError( RIPLOG_RTAB_INIT_FAILED, 0, NULL, dwErr );
break; }
*lpdwRouteCount = pmiftTable-> dwNumEntries;
*lplpRouteTable = (LPIPROUTE_ENTRY) pmiftTable-> table;
return NO_ERROR; } while ( FALSE );
//
// Error condition
//
if ( pmiftTable ) { HeapFree( GetProcessHeap(), 0, pmiftTable ); }
return dwErr; }
//----------------------------------------------------------------------------
// FreeIPRouteTable
//
// This function releases the memory allocated for the IP route table by
// the GetIpAddressTable API.
//----------------------------------------------------------------------------
DWORD FreeRouteTable( IN LPIPROUTE_ENTRY lpRouteTable ) {
PMIB_IPFORWARDTABLE pmiftTable = NULL;
pmiftTable = CONTAINING_RECORD( lpRouteTable, MIB_IPFORWARDTABLE, table );
if ( pmiftTable != NULL ) { HeapFree( GetProcessHeap(), 0, pmiftTable );
return NO_ERROR; }
return ERROR_INVALID_PARAMETER; }
//----------------------------------------------------------------------------
// AddRoute
//
// This function adds a route to the IP stack
//----------------------------------------------------------------------------
DWORD AddRoute( IN DWORD dwProtocol, IN DWORD dwType, IN DWORD dwIndex, IN DWORD dwDestVal, IN DWORD dwMaskVal, IN DWORD dwGateVal, IN DWORD dwMetric ) {
DWORD dwErr = 0;
MIB_IPFORWARDROW mifr;
ZeroMemory( &mifr, sizeof( MIB_IPFORWARDROW ) );
mifr.dwForwardDest = dwDestVal; mifr.dwForwardMask = dwMaskVal; mifr.dwForwardPolicy = 0; mifr.dwForwardNextHop = dwGateVal; mifr.dwForwardIfIndex = dwIndex; mifr.dwForwardType = dwType; mifr.dwForwardProto = MIB_IPPROTO_NT_AUTOSTATIC; mifr.dwForwardMetric1 = dwMetric;
dwErr = CreateIpForwardEntry( &mifr );
if ( dwErr == ERROR_ALREADY_EXISTS ) { //
// Bug # : 405469
//
// For the case where IPRIP (Rip Listener) is running at the
// same time as the RemoteAccess service.
// In this case the IPHLPAPI go via the IPRTRMGR to the stack
// and trying to create a route that already exists will fail
// with ERROR_ALREADY_EXISTS. To work around this case, set
// the forward entry.
//
dwErr = SetIpForwardEntry( &mifr ); } if ( dwErr != NO_ERROR ) { dbgprintf( "Create/Set IpForwardEntry failed with error %x\n", dwErr );
RipLogError( RIPLOG_ADD_ROUTE_FAILED, 0, NULL, dwErr ); }
return dwErr; }
//----------------------------------------------------------------------------
// DelRoute
//
// This function deletes a route to the IP stack
//----------------------------------------------------------------------------
DWORD DeleteRoute( IN DWORD dwIndex, IN DWORD dwDestVal, IN DWORD dwMaskVal, IN DWORD dwGateVal ) {
DWORD dwErr = 0;
MIB_IPFORWARDROW mifr;
ZeroMemory( &mifr, sizeof( MIB_IPFORWARDROW ) );
mifr.dwForwardDest = dwDestVal; mifr.dwForwardMask = dwMaskVal; mifr.dwForwardPolicy = 0; mifr.dwForwardProto = MIB_IPPROTO_NT_AUTOSTATIC; mifr.dwForwardNextHop = dwGateVal; mifr.dwForwardIfIndex = dwIndex;
dwErr = DeleteIpForwardEntry( &mifr );
if ( dwErr != NO_ERROR ) { dbgprintf( "DeleteIpForwardEntry failed with error %x\n", dwErr );
RipLogError( RIPLOG_DELETE_ROUTE_FAILED, 0, NULL, dwErr ); }
return dwErr; }
//----------------------------------------------------------------------------
// DelRoute
//
// This function deletes a route to the IP stack
//----------------------------------------------------------------------------
DWORD ReloadIPAddressTable( OUT PMIB_IPADDRROW *lplpAddrTable, OUT LPDWORD lpdwAddrCount ) { return GetIPAddressTable( lplpAddrTable, lpdwAddrCount ); }
|