787 lines
19 KiB
C
787 lines
19 KiB
C
|
/*
|
||
|
|
||
|
Copyright (c) 1998, Microsoft Corporation, all rights reserved
|
||
|
|
||
|
Description:
|
||
|
|
||
|
History:
|
||
|
|
||
|
*/
|
||
|
|
||
|
#include "rastcp_.h"
|
||
|
|
||
|
/*
|
||
|
|
||
|
Returns:
|
||
|
|
||
|
Description:
|
||
|
|
||
|
*/
|
||
|
|
||
|
IPADDR
|
||
|
RasTcpDeriveMask(
|
||
|
IN IPADDR nboIpAddr
|
||
|
)
|
||
|
{
|
||
|
IPADDR nboMask = 0;
|
||
|
IPADDR hboMask = 0;
|
||
|
|
||
|
if (CLASSA_NBO_ADDR(nboIpAddr))
|
||
|
{
|
||
|
hboMask = CLASSA_HBO_ADDR_MASK;
|
||
|
}
|
||
|
else if (CLASSB_NBO_ADDR(nboIpAddr))
|
||
|
{
|
||
|
hboMask = CLASSB_HBO_ADDR_MASK;
|
||
|
}
|
||
|
else if (CLASSC_NBO_ADDR(nboIpAddr))
|
||
|
{
|
||
|
hboMask = CLASSC_HBO_ADDR_MASK;
|
||
|
}
|
||
|
|
||
|
nboMask = htonl(hboMask);
|
||
|
|
||
|
return(nboMask);
|
||
|
}
|
||
|
|
||
|
/*
|
||
|
|
||
|
Returns:
|
||
|
VOID
|
||
|
|
||
|
Description:
|
||
|
Sets the ip address for proxy arp"ing" on all lan interfaces.
|
||
|
|
||
|
*/
|
||
|
|
||
|
VOID
|
||
|
RasTcpSetProxyArp(
|
||
|
IN IPADDR nboIpAddr,
|
||
|
IN BOOL fAddAddress
|
||
|
)
|
||
|
{
|
||
|
MIB_IPADDRTABLE* pIpAddrTable = NULL;
|
||
|
HANDLE hHeap = NULL;
|
||
|
DWORD dwNboIpAddr;
|
||
|
DWORD dwNboMask;
|
||
|
DWORD dw;
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
|
||
|
extern IPADDR RasSrvrNboServerIpAddress;
|
||
|
|
||
|
TraceHlp("RasTcpSetProxyArp(IP Addr: 0x%x, fAddAddress: %s)",
|
||
|
nboIpAddr, fAddAddress ? "TRUE" : "FALSE");
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if (NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetProcessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
dwErr = PAllocateAndGetIpAddrTableFromStack(&pIpAddrTable,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("AllocateAndGetIpAddrTableFromStack failed and returned %d",
|
||
|
dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
for (dw = 0; dw < pIpAddrTable->dwNumEntries; dw++)
|
||
|
{
|
||
|
dwNboIpAddr = pIpAddrTable->table[dw].dwAddr;
|
||
|
dwNboMask = pIpAddrTable->table[dw].dwMask;
|
||
|
|
||
|
if ( (ALL_NETWORKS_ROUTE == dwNboIpAddr)
|
||
|
|| (HOST_MASK == dwNboIpAddr)
|
||
|
|| (RasSrvrNboServerIpAddress == dwNboIpAddr))
|
||
|
{
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
if ((nboIpAddr & dwNboMask) != (dwNboIpAddr & dwNboMask))
|
||
|
{
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
dwErr = PSetProxyArpEntryToStack(nboIpAddr, HOST_MASK,
|
||
|
pIpAddrTable->table[dw].dwIndex,
|
||
|
fAddAddress, FALSE);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("SetProxyArpEntryToStack on NIC with address 0x%x failed "
|
||
|
"and returned 0x%x", dwNboIpAddr, dwErr);
|
||
|
|
||
|
dwErr = PSetProxyArpEntryToStack(nboIpAddr, HOST_MASK,
|
||
|
pIpAddrTable->table[dw].dwIndex,
|
||
|
fAddAddress, TRUE);
|
||
|
|
||
|
TraceHlp("SetProxyArpEntryToStack: 0x%x", dwErr);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if ( (NULL != hHeap)
|
||
|
&& (NULL != pIpAddrTable))
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pIpAddrTable);
|
||
|
}
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
/*
|
||
|
|
||
|
Returns:
|
||
|
VOID
|
||
|
|
||
|
Description:
|
||
|
|
||
|
*/
|
||
|
|
||
|
VOID
|
||
|
RasTcpSetRoute(
|
||
|
IN IPADDR nboDestAddr,
|
||
|
IN IPADDR nboNextHopAddr,
|
||
|
IN IPADDR nboIpMask,
|
||
|
IN IPADDR nboLocalAddr,
|
||
|
IN BOOL fAddAddress,
|
||
|
IN DWORD dwMetric,
|
||
|
IN BOOL fSetToStack
|
||
|
)
|
||
|
{
|
||
|
MIB_IPADDRTABLE* pIpAddrTable = NULL;
|
||
|
MIB_IPFORWARDROW IpForwardRow;
|
||
|
HANDLE hHeap = NULL;
|
||
|
DWORD dw;
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
|
||
|
TraceHlp("RasTcpSetRoute(Dest: 0x%x, Mask: 0x%x, NextHop: 0x%x, "
|
||
|
"Intf: 0x%x, %d, %s, %s)",
|
||
|
nboDestAddr, nboIpMask, nboNextHopAddr, nboLocalAddr, dwMetric,
|
||
|
fAddAddress ? "Add" : "Del",
|
||
|
fSetToStack ? "Stack" : "Rtr");
|
||
|
|
||
|
ZeroMemory(&IpForwardRow, sizeof(IpForwardRow));
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if (NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetProcessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
dwErr = PAllocateAndGetIpAddrTableFromStack(&pIpAddrTable,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("AllocateAndGetIpAddrTableFromStack failed and returned %d",
|
||
|
dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
for (dw = 0; dw < pIpAddrTable->dwNumEntries; dw++)
|
||
|
{
|
||
|
if (nboLocalAddr == pIpAddrTable->table[dw].dwAddr)
|
||
|
{
|
||
|
IpForwardRow.dwForwardDest = nboDestAddr;
|
||
|
IpForwardRow.dwForwardMask = nboIpMask;
|
||
|
IpForwardRow.dwForwardPolicy = 0;
|
||
|
IpForwardRow.dwForwardNextHop = nboNextHopAddr;
|
||
|
IpForwardRow.dwForwardIfIndex = pIpAddrTable->table[dw].dwIndex;
|
||
|
IpForwardRow.dwForwardProto = IRE_PROTO_NETMGMT;
|
||
|
IpForwardRow.dwForwardAge = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardNextHopAS = 0;
|
||
|
IpForwardRow.dwForwardMetric1 = dwMetric;
|
||
|
IpForwardRow.dwForwardMetric2 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric3 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric4 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric5 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardType = (fAddAddress ?
|
||
|
IRE_TYPE_DIRECT : IRE_TYPE_INVALID);
|
||
|
|
||
|
if (fSetToStack)
|
||
|
{
|
||
|
dwErr = PSetIpForwardEntryToStack(&IpForwardRow);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
if (fAddAddress)
|
||
|
{
|
||
|
dwErr = PSetIpForwardEntry(&IpForwardRow);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dwErr = PDeleteIpForwardEntry(&IpForwardRow);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("SetIpForwardEntry%s failed and returned 0x%x",
|
||
|
fSetToStack ? "ToStack" : "", dwErr);
|
||
|
}
|
||
|
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if ( (NULL != hHeap)
|
||
|
&& (NULL != pIpAddrTable))
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pIpAddrTable);
|
||
|
}
|
||
|
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
VOID
|
||
|
RasTcpSetRouteEx(
|
||
|
IN IPADDR nboDestAddr,
|
||
|
IN IPADDR nboNextHopAddr,
|
||
|
IN IPADDR nboIpMask,
|
||
|
IN IPADDR nboLocalAddr,
|
||
|
IN BOOL fAddAddress,
|
||
|
IN DWORD dwMetric,
|
||
|
IN BOOL fSetToStack,
|
||
|
IN GUID *pIfGuid
|
||
|
)
|
||
|
{
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
HANDLE hHeap = NULL;
|
||
|
IP_INTERFACE_NAME_INFO *pTable = NULL;
|
||
|
DWORD dw;
|
||
|
DWORD dwCount;
|
||
|
MIB_IPFORWARDROW IpForwardRow;
|
||
|
|
||
|
TraceHlp("RasTcpSetRouteEx(Dest: 0x%x, Mask: 0x%x, NextHop: 0x%x, "
|
||
|
"Intf: 0x%x, %d, %s, %s)",
|
||
|
nboDestAddr, nboIpMask, nboNextHopAddr, nboLocalAddr, dwMetric,
|
||
|
fAddAddress ? "Add" : "Del",
|
||
|
fSetToStack ? "Stack" : "Rtr");
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if(NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetPRocessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
ZeroMemory(&IpForwardRow, sizeof(MIB_IPFORWARDROW));
|
||
|
|
||
|
dwErr = PNhpAllocateAndGetInterfaceInfoFromStack(&pTable, &dwCount,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
for(dw = 0; dw < dwCount; dw++)
|
||
|
{
|
||
|
if(0 == memcmp(&pTable[dw].DeviceGuid,
|
||
|
pIfGuid,
|
||
|
sizeof(GUID)))
|
||
|
{
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if(dw == dwCount)
|
||
|
{
|
||
|
dwErr = ERROR_INVALID_PARAMETER;
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
IpForwardRow.dwForwardDest = nboDestAddr;
|
||
|
IpForwardRow.dwForwardMask = nboIpMask;
|
||
|
IpForwardRow.dwForwardPolicy = 0;
|
||
|
|
||
|
if(nboDestAddr != ALL_NETWORKS_ROUTE)
|
||
|
{
|
||
|
IpForwardRow.dwForwardNextHop = nboNextHopAddr;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
IpForwardRow.dwForwardNextHop = 0;
|
||
|
}
|
||
|
|
||
|
IpForwardRow.dwForwardIfIndex = pTable[dw].Index;
|
||
|
IpForwardRow.dwForwardProto = IRE_PROTO_NETMGMT;
|
||
|
IpForwardRow.dwForwardAge = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardNextHopAS = 0;
|
||
|
IpForwardRow.dwForwardMetric1 = dwMetric;
|
||
|
IpForwardRow.dwForwardMetric2 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric3 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric4 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardMetric5 = (DWORD)-1;
|
||
|
IpForwardRow.dwForwardType = (fAddAddress ?
|
||
|
IRE_TYPE_DIRECT : IRE_TYPE_INVALID);
|
||
|
|
||
|
if (fSetToStack)
|
||
|
{
|
||
|
dwErr = PSetIpForwardEntryToStack(&IpForwardRow);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
if (fAddAddress)
|
||
|
{
|
||
|
dwErr = PSetIpForwardEntry(&IpForwardRow);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dwErr = PDeleteIpForwardEntry(&IpForwardRow);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("SetIpForwardEntry%s failed and returned 0x%x",
|
||
|
fSetToStack ? "ToStack" : "", dwErr);
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if(NULL != pTable)
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pTable);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
/*
|
||
|
|
||
|
Returns:
|
||
|
VOID
|
||
|
|
||
|
Description:
|
||
|
|
||
|
*/
|
||
|
#if 0
|
||
|
|
||
|
VOID
|
||
|
RasTcpSetRoutesForNameServers(
|
||
|
BOOL fSet
|
||
|
)
|
||
|
{
|
||
|
HANDLE hHeap = NULL;
|
||
|
IP_INTERFACE_NAME_INFO* pTable = NULL;
|
||
|
DWORD dw;
|
||
|
DWORD dwCount;
|
||
|
IPADDR nboIpAddress;
|
||
|
IPADDR nboDNS1;
|
||
|
IPADDR nboDNS2;
|
||
|
IPADDR nboWINS1;
|
||
|
IPADDR nboWINS2;
|
||
|
IPADDR nboGateway;
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
|
||
|
TraceHlp("RasTcpSetRoutesForNameServers. fSet=%d", fSet);
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if (NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetProcessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
dwErr = PNhpAllocateAndGetInterfaceInfoFromStack(&pTable, &dwCount,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("NhpAllocateAndGetInterfaceInfoFromStack failed and "
|
||
|
"returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
|
||
|
for (dw = 0; dw < dwCount; dw++)
|
||
|
{
|
||
|
|
||
|
dwErr = GetAdapterInfo(
|
||
|
pTable[dw].Index,
|
||
|
&nboIpAddress,
|
||
|
&nboDNS1, &nboDNS2,
|
||
|
&nboWINS1, &nboWINS2,
|
||
|
&nboGateway,
|
||
|
NULL);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
dwErr = NO_ERROR;
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
if (0 != nboDNS1)
|
||
|
{
|
||
|
RasTcpSetRoute(nboDNS1, nboGateway, HOST_MASK, nboIpAddress,
|
||
|
fSet, 1, TRUE);
|
||
|
}
|
||
|
|
||
|
if (0 != nboDNS2)
|
||
|
{
|
||
|
RasTcpSetRoute(nboDNS2, nboGateway, HOST_MASK, nboIpAddress,
|
||
|
fSet, 1, TRUE);
|
||
|
}
|
||
|
|
||
|
if (0 != nboWINS1)
|
||
|
{
|
||
|
RasTcpSetRoute(nboWINS1, nboGateway, HOST_MASK, nboIpAddress,
|
||
|
fSet, 1, TRUE);
|
||
|
}
|
||
|
|
||
|
if (0 != nboWINS2)
|
||
|
{
|
||
|
RasTcpSetRoute(nboWINS2, nboGateway, HOST_MASK, nboIpAddress,
|
||
|
fSet, 1, TRUE);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if (NULL != pTable)
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pTable);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
#endif
|
||
|
|
||
|
//
|
||
|
//Bump up the metric of all the routes or reduce the metric
|
||
|
//of all multicase routes by 1
|
||
|
//
|
||
|
DWORD
|
||
|
RasTcpAdjustMulticastRouteMetric (
|
||
|
IN IPADDR nboIpAddr,
|
||
|
IN BOOL fSet
|
||
|
)
|
||
|
{
|
||
|
MIB_IPFORWARDTABLE* pIpForwardTable = NULL;
|
||
|
MIB_IPFORWARDROW* pIpForwardRow;
|
||
|
HANDLE hHeap = NULL;
|
||
|
DWORD dw;
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
|
||
|
TraceHlp("RasTcpAdjustMulticastRouteMetric(IP Addr: 0x%x, Set: %s)", nboIpAddr,
|
||
|
fSet ? "TRUE" : "FALSE");
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if (NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetProcessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
dwErr = PAllocateAndGetIpForwardTableFromStack(&pIpForwardTable,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("AllocateAndGetIpAddrTableFromStack failed and returned %d",
|
||
|
dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
//
|
||
|
//Steps to follow:
|
||
|
// 1. Check to see if we have a default route for the interface with
|
||
|
// the ip address passed in.
|
||
|
// 2. If we do then bump up the metric for all interfaces with 0xE0
|
||
|
// as the forward dest.
|
||
|
// Else
|
||
|
// we have nothing to do.
|
||
|
// 3. Add an E0 route with a metric of 1.
|
||
|
for (dw = 0; dw < pIpForwardTable->dwNumEntries; dw++)
|
||
|
{
|
||
|
pIpForwardRow = pIpForwardTable->table + dw;
|
||
|
if ( 0 == pIpForwardRow->dwForwardDest ) //default route
|
||
|
{
|
||
|
IPADDR nboIpIfIpAddr;
|
||
|
//
|
||
|
//get the adapter information
|
||
|
//to see if the ip address matches
|
||
|
//
|
||
|
dwErr = GetAdapterInfo ( pIpForwardRow->dwForwardIfIndex,
|
||
|
&nboIpIfIpAddr,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL
|
||
|
);
|
||
|
if ( NO_ERROR != dwErr )
|
||
|
{
|
||
|
TraceHlp("GetAdapterInfo failed and returned %d",
|
||
|
dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
if ( nboIpAddr == nboIpIfIpAddr )
|
||
|
{
|
||
|
DWORD dw1 = 0;
|
||
|
MIB_IPFORWARDROW * pIpForwardRow1 = NULL;
|
||
|
//
|
||
|
//This means that we have a default route. So we need to bump up the metric of
|
||
|
//all the E0 by 1
|
||
|
for ( dw1 = 0; dw1 < pIpForwardTable->dwNumEntries; dw1 ++ )
|
||
|
{
|
||
|
pIpForwardRow1 = pIpForwardTable->table + dw1;
|
||
|
if (0xE0 == pIpForwardRow1->dwForwardDest /* multicast route */)
|
||
|
{
|
||
|
if (fSet)
|
||
|
{
|
||
|
// Bump up metric (hop count)
|
||
|
|
||
|
pIpForwardRow1->dwForwardMetric1++;
|
||
|
}
|
||
|
else if (pIpForwardRow1->dwForwardMetric1 > 1) // Never make it 0!
|
||
|
{
|
||
|
// Bump down metric
|
||
|
|
||
|
pIpForwardRow1->dwForwardMetric1--;
|
||
|
}
|
||
|
|
||
|
dwErr = PSetIpForwardEntryToStack(pIpForwardRow1);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("SetIpForwardEntryToStack failed and returned 0x%x"
|
||
|
"dest=0x%x, nexthop=0x%x, mask=0x%x",
|
||
|
dwErr,
|
||
|
pIpForwardRow->dwForwardDest,
|
||
|
pIpForwardRow->dwForwardNextHop,
|
||
|
pIpForwardRow->dwForwardMask);
|
||
|
|
||
|
dwErr = NO_ERROR;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
if ( fSet )
|
||
|
{
|
||
|
//
|
||
|
//Set the multicast route metric on this interface
|
||
|
//to 1
|
||
|
RasTcpSetRoute( 0xE0,
|
||
|
nboIpAddr,
|
||
|
0xF0,
|
||
|
nboIpAddr,
|
||
|
TRUE,
|
||
|
1,
|
||
|
TRUE
|
||
|
);
|
||
|
|
||
|
}
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if ( (NULL != hHeap)
|
||
|
&& (NULL != pIpForwardTable))
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pIpForwardTable);
|
||
|
}
|
||
|
|
||
|
return(dwErr);
|
||
|
|
||
|
}
|
||
|
/*
|
||
|
|
||
|
Returns:
|
||
|
Error codes from TCPConfig (your basic nt codes)
|
||
|
|
||
|
Description:
|
||
|
fSet: If TRUE means set existing routes to higher metrics and add OVERRIDE
|
||
|
routes.
|
||
|
If FALSE means mark existing routes to lower metrics.
|
||
|
*/
|
||
|
|
||
|
DWORD
|
||
|
RasTcpAdjustRouteMetrics(
|
||
|
IN IPADDR nboIpAddr,
|
||
|
IN BOOL fSet
|
||
|
)
|
||
|
{
|
||
|
MIB_IPFORWARDTABLE* pIpForwardTable = NULL;
|
||
|
MIB_IPFORWARDROW* pIpForwardRow;
|
||
|
HANDLE hHeap = NULL;
|
||
|
DWORD dw;
|
||
|
DWORD dwErr = NO_ERROR;
|
||
|
|
||
|
TraceHlp("RasTcpAdjustRouteMetrics(IP Addr: 0x%x, Set: %s)", nboIpAddr,
|
||
|
fSet ? "TRUE" : "FALSE");
|
||
|
|
||
|
hHeap = GetProcessHeap();
|
||
|
|
||
|
if (NULL == hHeap)
|
||
|
{
|
||
|
dwErr = GetLastError();
|
||
|
TraceHlp("GetProcessHeap failed and returned %d", dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
dwErr = PAllocateAndGetIpForwardTableFromStack(&pIpForwardTable,
|
||
|
FALSE /* bOrder */, hHeap, LPTR);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("AllocateAndGetIpAddrTableFromStack failed and returned %d",
|
||
|
dwErr);
|
||
|
goto LDone;
|
||
|
}
|
||
|
|
||
|
for (dw = 0; dw < pIpForwardTable->dwNumEntries; dw++)
|
||
|
{
|
||
|
pIpForwardRow = pIpForwardTable->table + dw;
|
||
|
|
||
|
if (0 == pIpForwardRow->dwForwardDest /* default route */)
|
||
|
{
|
||
|
if (fSet)
|
||
|
{
|
||
|
// Bump up metric (hop count)
|
||
|
|
||
|
pIpForwardRow->dwForwardMetric1++;
|
||
|
}
|
||
|
else if (pIpForwardRow->dwForwardMetric1 > 1) // Never make it 0!
|
||
|
{
|
||
|
// Bump down metric
|
||
|
|
||
|
pIpForwardRow->dwForwardMetric1--;
|
||
|
}
|
||
|
|
||
|
dwErr = PSetIpForwardEntryToStack(pIpForwardRow);
|
||
|
|
||
|
if (NO_ERROR != dwErr)
|
||
|
{
|
||
|
TraceHlp("SetIpForwardEntryToStack failed and returned 0x%x"
|
||
|
"dest=0x%x, nexthop=0x%x, mask=0x%x",
|
||
|
dwErr,
|
||
|
pIpForwardRow->dwForwardDest,
|
||
|
pIpForwardRow->dwForwardNextHop,
|
||
|
pIpForwardRow->dwForwardMask);
|
||
|
|
||
|
dwErr = NO_ERROR;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
LDone:
|
||
|
|
||
|
if ( (NULL != hHeap)
|
||
|
&& (NULL != pIpForwardTable))
|
||
|
{
|
||
|
HeapFree(hHeap, 0, pIpForwardTable);
|
||
|
}
|
||
|
|
||
|
return(dwErr);
|
||
|
}
|
||
|
|
||
|
VOID
|
||
|
RasTcpSetDhcpRoutes ( PBYTE pbRouteInfo, IPADDR ipAddrLocal, BOOL fSet )
|
||
|
{
|
||
|
//parse the byte stream and decode destination descriptors to get the subnet number and subnet mask.
|
||
|
//The format of the stream is as follows
|
||
|
//+------------------------------------------------------------------------------------
|
||
|
//+Code | Len | d1 | ... | dn | r1 | r2 | r3 | r4 | d1 | ... | dn | r1 | r2 | r3 | r4 |
|
||
|
//+------------------------------------------------------------------------------------
|
||
|
//length of code = 1 octet
|
||
|
//length of Len = 1 octet
|
||
|
//Length of each d1 ... dn - 1 octet
|
||
|
//Length of each r1 - r4 = 1 octet.
|
||
|
|
||
|
BYTE dwAddrMaskLookup [] = {0x00,0x80,0xC0,0xE0,0xF0,0xF8,0xFC,0xFE,0xFF };
|
||
|
|
||
|
PBYTE pbRover = pbRouteInfo + 1;
|
||
|
BYTE bLen = pbRouteInfo[0];
|
||
|
TraceHlp ( "RasTcpSetDhcpRoutes Begin");
|
||
|
while ( pbRover < pbRouteInfo + 1 + bLen )
|
||
|
{
|
||
|
unsigned char ipszdest[5] = {0};
|
||
|
unsigned char ipszsnetmask[5] = {0};
|
||
|
unsigned char ipsznexthop[5] = {0};
|
||
|
IPADDR ipdest = 0;
|
||
|
IPADDR ipmask = 0;
|
||
|
IPADDR ipnexthop = 0;
|
||
|
|
||
|
|
||
|
if ( *pbRover > 32 )
|
||
|
{
|
||
|
//Error. We cannot have more than 32 1's in the mask
|
||
|
TraceHlp("RasTcpSetDhcpRoutes: invalid destination descriptor first byte %d",
|
||
|
*pbRover);
|
||
|
|
||
|
goto done;
|
||
|
}
|
||
|
else
|
||
|
{ //set the subnet mask first
|
||
|
int n1 = (int)((*pbRover) / 8);
|
||
|
int n2 = (int)((*pbRover) % 8 );
|
||
|
int i;
|
||
|
for ( i = 0; i < n1; i++)
|
||
|
{
|
||
|
ipszsnetmask[i] = (BYTE)0xFF;
|
||
|
}
|
||
|
//set the final byte
|
||
|
if ( n2 ) ipszsnetmask[3] = dwAddrMaskLookup[n2];
|
||
|
pbRover ++;
|
||
|
//now for the ip address
|
||
|
if ( n2 ) n1 ++;
|
||
|
|
||
|
for ( i = 0; i < n1; i ++ )
|
||
|
{
|
||
|
ipszdest[i] = *pbRover;
|
||
|
pbRover++;
|
||
|
}
|
||
|
|
||
|
TraceHlp ( "RasTcpSetDhcpRoutes: Got route dest addr = %d.%d.%d.%d subnet mask = %d.%d.%d.%d route = %d.%d.%d.%d\n",
|
||
|
ipszdest[0],ipszdest[1],ipszdest[2],ipszdest[3],
|
||
|
ipszsnetmask[0],ipszsnetmask[1],ipszsnetmask[2],ipszsnetmask[3],
|
||
|
*pbRover, *(pbRover+1),*(pbRover+2),*(pbRover+3)
|
||
|
);
|
||
|
|
||
|
CopyMemory ( ipsznexthop, pbRover, 4 );
|
||
|
/*
|
||
|
//now set the route
|
||
|
ipdest = inet_addr ((const char FAR *)ipszdest);
|
||
|
ipmask = inet_addr ((const char FAR *)ipszsnetmask);
|
||
|
ipnexthop = inet_addr ((const char FAR *)ipsznexthop);
|
||
|
*/
|
||
|
ipdest = *((ULONG *)ipszdest);
|
||
|
ipmask = *((ULONG *)ipszsnetmask);
|
||
|
ipnexthop = *((ULONG *)ipsznexthop);
|
||
|
RasTcpSetRoute( ipdest,
|
||
|
ipAddrLocal,
|
||
|
ipmask,
|
||
|
ipAddrLocal,
|
||
|
fSet,
|
||
|
1,
|
||
|
TRUE
|
||
|
);
|
||
|
pbRover +=4;
|
||
|
|
||
|
}
|
||
|
}
|
||
|
done:
|
||
|
TraceHlp ( "RasTcpSetDhcpRoutes End");
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
|