|
|
// Copyright (c) 1995, Microsoft Corporation, all rights reserved
//
// pbk.c
// Remote Access phonebook library
// General routines
// Listed alphabetically
//
// 06/20/95 Steve Cobb
#include "pbkp.h"
#include <search.h> // Qsort
#include <tapi.h>
#ifdef UNICODE
#define SZ_PathCanonicalize "PathCanonicalizeW"
#define SZ_PathRemoveFileSpec "PathRemoveFileSpecW"
#else
#define SZ_PathCanonicalize "PathCanonicalizeA"
#define SZ_PathRemoveFileSpec "PathRemoveFileSpecA"
#endif
PbkPathInfo g_PbkPathInfo;
//----------------------------------------------------------------------------
// Local prototypes
//----------------------------------------------------------------------------
DWORD AppendPbportToList( IN HANDLE hConnection, IN DTLLIST* pdtllist, IN RASMAN_PORT* pPort );
DWORD AppendStringToList( IN DTLLIST* pdtllist, IN TCHAR* psz );
int __cdecl CompareDevices( const void* pDevice1, const void* pDevice2 );
int __cdecl ComparePorts( const void* pPort1, const void* pPort2 );
CHAR* PbMedia( IN PBDEVICETYPE pbdt, IN CHAR* pszMedia );
WCHAR * GetUnicodeName(HANDLE hPort);
//----------------------------------------------------------------------------
// Routines
//----------------------------------------------------------------------------
DWORD RdtFromPbdt(PBDEVICETYPE pbdt, DWORD dwFlags) { DWORD rdt;
switch(pbdt) { case PBDT_Modem: { rdt = RDT_Modem;
if(PBP_F_NullModem & dwFlags) { rdt |= (RDT_Direct | RDT_Null_Modem); } break; }
case PBDT_X25: { rdt = RDT_X25; break; }
case PBDT_Isdn: { rdt = RDT_Isdn; break; }
case PBDT_Serial: { rdt = RDT_Serial; break; }
case PBDT_FrameRelay: { rdt = RDT_FrameRelay; break; }
case PBDT_Atm: { rdt = RDT_Atm; break; }
case PBDT_Vpn: { rdt = RDT_Tunnel;
if(PBP_F_L2tpDevice & dwFlags) { rdt |= RDT_Tunnel_L2tp; } else if(PBP_F_PptpDevice & dwFlags) { rdt |= RDT_Tunnel_Pptp; } break; }
case PBDT_Sonet: { rdt = RDT_Sonet; break; }
case PBDT_Sw56: { rdt = RDT_Sw56; break; }
case PBDT_Irda: { rdt = (RDT_Irda | RDT_Direct); break; }
case PBDT_Parallel: { rdt = (RDT_Parallel | RDT_Direct); break; }
case PBDT_Null: { rdt = (RDT_Direct | RDT_Null_Modem); break; }
case PBDT_PPPoE: { rdt = (RDT_PPPoE | RDT_Broadband); break; }
default: { rdt = RDT_Other; break; } }
return rdt; }
PBDEVICETYPE PbdtFromRdt( IN DWORD rdt ) { PBDEVICETYPE pbdt;
switch(rdt) { case RDT_Modem: { pbdt = PBDT_Modem; break; }
case RDT_X25: { pbdt = PBDT_X25; break; }
case RDT_Isdn: { pbdt = PBDT_Isdn; break; }
case RDT_Serial: { pbdt = PBDT_Serial; break; }
case RDT_FrameRelay: { pbdt = PBDT_FrameRelay; break; }
case RDT_Atm: { pbdt = PBDT_Atm; break; }
case RDT_Tunnel_Pptp: case RDT_Tunnel_L2tp: { pbdt = PBDT_Vpn; break; }
case RDT_Sonet: { pbdt = PBDT_Sonet; break; }
case RDT_Sw56: { pbdt = PBDT_Sw56; break; }
case RDT_Irda: { pbdt = PBDT_Irda; break; }
case RDT_Parallel: { pbdt = PBDT_Parallel; break; }
case RDT_PPPoE: { pbdt = PBDT_PPPoE; break; }
default: { pbdt = PBDT_Other; break; } }
return pbdt; }
TCHAR * pszDeviceTypeFromRdt(RASDEVICETYPE rdt) { TCHAR *pszDeviceType = NULL; switch(RAS_DEVICE_TYPE(rdt)) { case RDT_Modem: { pszDeviceType = RASDT_Modem; break; }
case RDT_X25: { pszDeviceType = RASDT_X25; break; }
case RDT_Isdn: { pszDeviceType = RASDT_Isdn; break; }
case RDT_Serial: { pszDeviceType = RASDT_Serial; break; }
case RDT_FrameRelay: { pszDeviceType = RASDT_FrameRelay; break; }
case RDT_Atm: { pszDeviceType = RASDT_Atm; break; }
case RDT_Sonet: { pszDeviceType = RASDT_Sonet; break; }
case RDT_Sw56: { pszDeviceType = RASDT_SW56; break; }
case RDT_Tunnel_Pptp: case RDT_Tunnel_L2tp: { pszDeviceType = RASDT_Vpn; break; }
case RDT_Irda: { pszDeviceType = RASDT_Irda; break; }
case RDT_Parallel: { pszDeviceType = RASDT_Parallel; break; }
case RDT_PPPoE: { pszDeviceType = RASDT_PPPoE; break; }
default: { pszDeviceType = NULL; break; } }
return StrDup(pszDeviceType); }
DWORD AppendPbportToList( IN HANDLE hConnection, IN DTLLIST* pdtllist, IN RASMAN_PORT* pPort )
// Append a PBPORT onto the list 'pdtllist' which has the characteristics
// of RAS Manager port 'pPort'.
//
// Returns 0 if successful, otherwise a non-zero error code.
//
{ DWORD dwErr; DTLNODE* pdtlnode; PBPORT* ppbport; DWORD dwType, dwClass;
dwErr = 0;
pdtlnode = CreatePortNode(); if ( !pdtlnode) { return ERROR_NOT_ENOUGH_MEMORY; }
// Get detailed information about the device from
// rasman
dwClass = RAS_DEVICE_CLASS(pPort->P_rdtDeviceType); dwType = RAS_DEVICE_TYPE(pPort->P_rdtDeviceType);
// Now set the device info
ppbport = (PBPORT* )DtlGetData( pdtlnode ); // ppbport->pszDevice = StrDupTFromAUsingAnsiEncoding( pPort->P_DeviceName );
ppbport->pszDevice = GetUnicodeName(pPort->P_Handle); if(ppbport->pszDevice == NULL) { ppbport->pszDevice = StrDupTFromAUsingAnsiEncoding( pPort->P_DeviceName ); } ppbport->pszPort = StrDupTFromAUsingAnsiEncoding( pPort->P_PortName );
// Record the flags appropriate to this device
if ( dwType == RDT_Tunnel_Pptp ) { ppbport->dwFlags |= PBP_F_PptpDevice; } else if ( dwType == RDT_Tunnel_L2tp ) { ppbport->dwFlags |= PBP_F_L2tpDevice; } //For whistler 349087 345068 gangz
//
else if ( dwType == RDT_PPPoE ) { ppbport->dwFlags |= PBP_F_PPPoEDevice; } if ( dwClass & RDT_Null_Modem ) { ppbport->dwFlags |= PBP_F_NullModem; } //For whistler 349087 345068 gangz
//
else if ( dwClass & RDT_Broadband ) { ppbport->dwFlags |= PBP_F_PPPoEDevice; }
// Compute the phonebook device type
//
ppbport->pbdevicetype = PbdtFromRdt(dwType); if ( PBDT_Other == ppbport->pbdevicetype ) { ppbport->pbdevicetype = PbdevicetypeFromPszTypeA( pPort->P_DeviceType); }
ppbport->pszMedia = StrDupTFromAUsingAnsiEncoding( PbMedia( ppbport->pbdevicetype, pPort->P_MediaName ) );
if (!ppbport->pszPort || !ppbport->pszDevice || !ppbport->pszMedia) { dwErr = ERROR_NOT_ENOUGH_MEMORY; } else if ((ppbport->pbdevicetype == PBDT_Modem) || (ppbport->dwFlags & PBP_F_NullModem)) {
#ifdef MXSMODEMS
if (pPort->P_LineDeviceId == 0xFFFFFFFF) { // MXS modem port.
//
ppbport->fMxsModemPort = TRUE;
GetRasPortMaxBps( pPort->P_Handle, &ppbport->dwMaxConnectBps, &ppbport->dwMaxCarrierBps );
GetRasPortModemSettings( pPort->P_Handle, &ppbport->fHwFlowDefault, &ppbport->fEcDefault, &ppbport->fEccDefault ); } else #else
ASSERT( pPort->P_LineDeviceId != 0xFFFFFFFF ); #endif
{ // Unimodem port.
//
UNIMODEMINFO info;
ZeroMemory((PBYTE) &info, sizeof(info));
GetRasUnimodemInfo( hConnection, pPort->P_Handle, pPort->P_DeviceType, &info );
TRACE6( "Port=%s,fHw=%d,fEc=%d,bps=%d,fSp=%d,prot=%x", pPort->P_PortName, info.fHwFlow, info.fEc, info.dwBps, info.fSpeaker, info.dwModemProtocol );
ppbport->fHwFlowDefault = info.fHwFlow; ppbport->fEcDefault = info.fEc; ppbport->fEccDefault = info.fEcc; ppbport->dwBpsDefault = info.dwBps; ppbport->fSpeakerDefault = info.fSpeaker;
// pmay: 228565
// Add the modem protocol information
//
ppbport->dwModemProtDefault = info.dwModemProtocol; ppbport->pListProtocols = info.pListProtocols; } }
if (dwErr == 0) { ppbport->dwType = EntryTypeFromPbport( ppbport ); DtlAddNodeLast( pdtllist, pdtlnode ); } else { Free0( ppbport->pszDevice ); Free0( ppbport->pszMedia ); Free0( ppbport->pszPort ); DtlDestroyNode( pdtlnode ); }
return dwErr; }
DWORD AppendStringToList( IN DTLLIST* pdtllist, IN TCHAR* psz )
// Appends a copy of 'psz' to the end of list 'pdtllist'.
//
// Returns 0 if successful, otherwise a non-zero error code.
// ERROR_NOT_ENOUGH_MEMORY is returned if 'psz' is NULL.
//
{ DTLNODE* pdtlnode; TCHAR* pszDup;
if (!psz) { return ERROR_NOT_ENOUGH_MEMORY; }
pszDup = StrDup( psz ); if (!pszDup) { return ERROR_NOT_ENOUGH_MEMORY; }
pdtlnode = DtlCreateNode( pszDup, 0L ); if (!pdtlnode ) { Free( pszDup ); return ERROR_NOT_ENOUGH_MEMORY; }
DtlAddNodeLast( pdtllist, pdtlnode ); return 0; }
DTLNODE* CloneEntryNode( DTLNODE* pdtlnodeSrc )
// Duplicates entry node 'pdtlnodeSrc' with fields that cannot be cloned
// set to "like new" settings.
//
{ DTLNODE* pdtlnode = NULL; RPC_STATUS rpcStatus = RPC_S_OK; PBENTRY* ppbentry = NULL; HRESULT hr = S_OK;
__try { pdtlnode = DuplicateEntryNode( pdtlnodeSrc );
if ( NULL == pdtlnode ) { hr = E_FAIL; __leave; } ppbentry = (PBENTRY* )DtlGetData( pdtlnode ); ASSERT( ppbentry );
if ( NULL == ppbentry ) { hr = E_FAIL; __leave; } ppbentry->fSkipDownLevelDialog = FALSE; ppbentry->fSkipDoubleDialDialog = FALSE; ppbentry->fSkipNwcWarning = FALSE; ppbentry->dwDialParamsUID = GetTickCount();
if (ppbentry->dwType != RASET_Phone) { ppbentry->fPreviewPhoneNumber = FALSE; ppbentry->fSharedPhoneNumbers = FALSE; }
Free0( ppbentry->pGuid ); ppbentry->pGuid = Malloc( sizeof(GUID) ); if ( NULL == ppbentry->pGuid) { hr = E_OUTOFMEMORY; __leave; } // For Whistler bug 513885
rpcStatus = UuidCreate( (UUID* )ppbentry->pGuid );
if( !( ( RPC_S_OK == rpcStatus) || ( RPC_S_UUID_LOCAL_ONLY == rpcStatus ) ) ) { hr = E_FAIL; __leave; }
ppbentry->fDirty = FALSE; } __finally { if ( S_OK != hr ) { if ( pdtlnode ) { DestroyEntryNode( pdtlnode ); pdtlnode = NULL; } } } return pdtlnode; }
int __cdecl CompareDevices( const void* pDevice1, const void* pDevice2 )
// Qsort compare function for RASMAN_DEVICEs.
//
{ return lstrcmpiA( ((RASMAN_DEVICE* )pDevice1)->D_Name, ((RASMAN_DEVICE* )pDevice2)->D_Name ); }
int __cdecl ComparePorts( const void* pPort1, const void* pPort2 )
// Qsort compare function for RASMAN_PORTs.
//
{ return lstrcmpiA( ((RASMAN_PORT* )pPort1)->P_PortName, ((RASMAN_PORT* )pPort2)->P_PortName ); }
DWORD CopyToPbport( IN PBPORT* ppbportDst, IN PBPORT* ppbportSrc )
// Make a duplicate of 'ppbportSrc' in 'ppbportDst'. If 'ppbportSrc' is
// NULL it sets 'ppbportDst' to defaults.
//
// Returns 0 if successful or an error code.
//
{ DTLNODE *pdtlnode, *pNode; WCHAR *pwsz; DTLLIST *pdtllist = NULL; Free0( ppbportDst->pszDevice ); Free0( ppbportDst->pszMedia ); Free0( ppbportDst->pszPort );
if (!ppbportSrc) { ppbportDst->pszPort = NULL; ppbportDst->fConfigured = TRUE; ppbportDst->pszDevice = NULL; ppbportDst->pszMedia = NULL; ppbportDst->pbdevicetype = PBDT_None; ppbportDst->dwType = RASET_Phone; ppbportDst->fHwFlowDefault = FALSE; ppbportDst->fEcDefault = FALSE; ppbportDst->fEccDefault = FALSE; ppbportDst->dwBpsDefault = 0; ppbportDst->fSpeakerDefault = TRUE; ppbportDst->fScriptBeforeTerminal = FALSE; ppbportDst->fScriptBefore = FALSE; ppbportDst->pszScriptBefore = NULL; return 0; }
CopyMemory( ppbportDst, ppbportSrc, sizeof(*ppbportDst) ); ppbportDst->pszDevice = StrDup( ppbportSrc->pszDevice ); ppbportDst->pszMedia = StrDup( ppbportSrc->pszMedia ); ppbportDst->pszPort = StrDup( ppbportSrc->pszPort ); ppbportDst->pszScriptBefore = StrDup( ppbportSrc->pszScriptBefore );
//
// Copy the protocol list.
//
if(ppbportSrc->pListProtocols) { for (pdtlnode = DtlGetFirstNode( ppbportSrc->pListProtocols); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { if(NULL == pdtllist) { pdtllist = DtlCreateList(0); if(NULL == pdtllist) { return ERROR_NOT_ENOUGH_MEMORY; } } pwsz = (WCHAR *) DtlGetData(pdtlnode);
pNode = DtlCreateSizedNode( (wcslen(pwsz) + 1) * sizeof(WCHAR), pdtlnode->lNodeId);
if(NULL == pNode) { return ERROR_NOT_ENOUGH_MEMORY; }
wcscpy((WCHAR *) DtlGetData(pNode), pwsz); DtlAddNodeLast(pdtllist, pNode); } }
ppbportDst->pListProtocols = pdtllist;
if ((ppbportSrc->pszDevice && !ppbportDst->pszDevice) || (ppbportSrc->pszMedia && !ppbportDst->pszMedia) || (ppbportSrc->pszPort && !ppbportDst->pszPort) || (ppbportSrc->pszScriptBefore && !ppbportDst->pszScriptBefore)) { return ERROR_NOT_ENOUGH_MEMORY; }
return 0; }
VOID ChangeEntryType( PBENTRY* ppbentry, DWORD dwType )
// Changes the type of 'ppbentry' to 'dwType' and sets defaults
// accordingly.
//
{ ppbentry->dwType = dwType;
if (dwType == RASET_Phone) { ppbentry->fPreviewPhoneNumber = TRUE;
// Defaults for Phones changed per bug 230240 and 363809.
//
ppbentry->dwAuthRestrictions = AR_F_TypicalUnsecure; ppbentry->dwTypicalAuth = TA_Unsecure; ppbentry->dwDataEncryption = DE_IfPossible; ppbentry->fIpHeaderCompression = TRUE; ppbentry->fShareMsFilePrint = FALSE;
// Disable File and Print services by default for phone
//
EnableOrDisableNetComponent( ppbentry, TEXT("ms_server"), FALSE);
ppbentry->fBindMsNetClient = TRUE;
EnableOrDisableNetComponent( ppbentry, TEXT("ms_msclient"), TRUE); } else if (dwType == RASET_Vpn) { // NOTE: If you change this you may need to also make a change in
// CloneEntryNode.
//
ppbentry->fPreviewPhoneNumber = FALSE; ppbentry->fSharedPhoneNumbers = FALSE;
// Defaults for VPN changed per bug 230240 and 363809.
//
ppbentry->dwAuthRestrictions = AR_F_TypicalSecure; ppbentry->dwTypicalAuth = TA_Secure; ppbentry->dwDataEncryption = DE_Require; ppbentry->fIpHeaderCompression = FALSE; // We share file and print by default for vpn
//
ppbentry->fShareMsFilePrint = TRUE;
// Enable File and Print services by default
//
EnableOrDisableNetComponent( ppbentry, TEXT("ms_server"), TRUE); ppbentry->fBindMsNetClient = TRUE;
EnableOrDisableNetComponent( ppbentry, TEXT("ms_msclient"), TRUE); } else if (dwType == RASET_Broadband) { // NOTE: If you change this you may need to also make a change in
// CloneEntryNode.
//
ppbentry->fPreviewPhoneNumber = FALSE; ppbentry->fSharedPhoneNumbers = FALSE;
// Defaults for broadband connections
//
ppbentry->dwAuthRestrictions = AR_F_TypicalSecure; ppbentry->dwTypicalAuth = TA_Secure; ppbentry->dwDataEncryption = DE_IfPossible; ppbentry->fIpHeaderCompression = FALSE; // We share file and print by default for vpn
//
ppbentry->fShareMsFilePrint = TRUE;
// Enable File and Print services by default
//
EnableOrDisableNetComponent( ppbentry, TEXT("ms_server"), FALSE); ppbentry->fBindMsNetClient = TRUE;
EnableOrDisableNetComponent( ppbentry, TEXT("ms_msclient"), TRUE); } else if (dwType == RASET_Direct) { // NOTE: If you change this you may need to also make a change in
// CloneEntryNode.
//
ppbentry->fPreviewPhoneNumber = FALSE; ppbentry->fSharedPhoneNumbers = FALSE;
// Defaults for DCC (like Phones in this regard) changed per bug
// 230240 and 363809.
//
ppbentry->dwAuthRestrictions = AR_F_TypicalUnsecure; ppbentry->dwTypicalAuth = TA_Unsecure; ppbentry->dwDataEncryption = DE_IfPossible; ppbentry->fIpHeaderCompression = TRUE; // We share file and print by default for dcc
//
ppbentry->fShareMsFilePrint = TRUE;
// Enable File and Print services by default
//
EnableOrDisableNetComponent( ppbentry, TEXT("ms_server"), TRUE); ppbentry->fBindMsNetClient = TRUE;
EnableOrDisableNetComponent( ppbentry, TEXT("ms_msclient"), TRUE); } }
DTLNODE* CreateEntryNode( BOOL fCreateLink )
// Allocates a sized phonebook entry node of type RASET_Phone and fills it
// with default values. See ChangeEntryNodeType routine. 'If
// 'fCreateLink' is true a default node is added the list of links.
// Otherwise, the list of links is empty.
//
// Returns the address of the allocated node if successful, NULL
// otherwise.
//
{ DTLNODE* pdtlnode; PBENTRY* ppbentry;
TRACE( "CreateEntryNode" );
// Allocate the node with built-in PBENTRY.
//
pdtlnode = DtlCreateSizedNode( sizeof(PBENTRY), 0L ); if (!pdtlnode) { return NULL; }
ppbentry = (PBENTRY* )DtlGetData( pdtlnode ); ASSERT( ppbentry );
// Create the list of links with a default link node or no link nodes as
// chosen by caller.
//
ppbentry->pdtllistLinks = DtlCreateList( 0 ); if (!ppbentry->pdtllistLinks) { DestroyEntryNode( pdtlnode ); return NULL; }
if (fCreateLink) { DTLNODE* pLinkNode;
pLinkNode = CreateLinkNode(); if (!pLinkNode) { DestroyEntryNode( pdtlnode ); return NULL; }
DtlAddNodeLast( ppbentry->pdtllistLinks, pLinkNode ); }
// Set fields to defaults.
//
ppbentry->pszEntryName = NULL; ppbentry->dwType = RASET_Phone;
// General page fields.
//
ppbentry->pszPrerequisiteEntry = NULL; ppbentry->pszPrerequisitePbk = NULL; ppbentry->fSharedPhoneNumbers = TRUE; ppbentry->fGlobalDeviceSettings = FALSE; ppbentry->fShowMonitorIconInTaskBar = TRUE; ppbentry->pszPreferredDevice = NULL; ppbentry->pszPreferredPort = NULL; //For .Net 639551 Add preferred info for Modem settings
ppbentry->dwPreferredBps = 0; ppbentry->fPreferredHwFlow = 0; ppbentry->fPreferredEc = 0; ppbentry->fPreferredEcc = 0; ppbentry->fPreferredSpeaker = 0; ppbentry->dwPreferredModemProtocol=0; //For whislter bug 402522
// Options page fields.
//
ppbentry->fShowDialingProgress = TRUE; ppbentry->fPreviewPhoneNumber = TRUE; ppbentry->fPreviewUserPw = TRUE; ppbentry->fPreviewDomain = FALSE; // See bug 281673
ppbentry->dwDialMode = RASEDM_DialAll; ppbentry->dwDialPercent = 75; ppbentry->dwDialSeconds = 120; ppbentry->dwHangUpPercent = 10; ppbentry->dwHangUpSeconds = 120;
ppbentry->dwfOverridePref = RASOR_RedialAttempts | RASOR_RedialSeconds | RASOR_IdleDisconnectSeconds | RASOR_RedialOnLinkFailure;
ppbentry->lIdleDisconnectSeconds = 0; ppbentry->dwRedialAttempts = 3; ppbentry->dwRedialSeconds = 60; ppbentry->fRedialOnLinkFailure = FALSE;
// Security page fields.
//
ppbentry->dwAuthRestrictions = AR_F_TypicalUnsecure; ppbentry->dwTypicalAuth = TA_Unsecure; ppbentry->dwDataEncryption = DE_IfPossible; ppbentry->fAutoLogon = FALSE; ppbentry->fUseRasCredentials = TRUE;
ppbentry->dwCustomAuthKey = (DWORD )-1; ppbentry->pCustomAuthData = NULL; ppbentry->cbCustomAuthData = 0;
ppbentry->fScriptAfterTerminal = FALSE; ppbentry->fScriptAfter = FALSE; ppbentry->pszScriptAfter = NULL;
ppbentry->pszX25Network = NULL; ppbentry->pszX25Address = NULL; ppbentry->pszX25UserData = NULL; ppbentry->pszX25Facilities = NULL;
// Use is unknown
//
ppbentry->dwUseFlags = 0; //IP Security Dialog box
//
ppbentry->dwIpSecFlags = 0;
// Network page fields.
//
ppbentry->dwBaseProtocol = BP_Ppp; ppbentry->dwVpnStrategy = VS_Default; ppbentry->dwfExcludedProtocols = 0; ppbentry->fLcpExtensions = TRUE; ppbentry->fSkipNwcWarning = FALSE; ppbentry->fSkipDownLevelDialog = FALSE; ppbentry->fSkipDoubleDialDialog = FALSE; ppbentry->fSwCompression = TRUE;
// (shaunco) Gibbs and QOS guys want this on by default.
// for whislter bug 385842 gangz
// we cut this functionality, so set the default to be FALSE
//
ppbentry->fNegotiateMultilinkAlways = FALSE;
// Create the list of links with a default link node or no link nodes as
// chosen by caller.
//
ppbentry->pdtllistNetComponents = DtlCreateList( 0 ); if (!ppbentry->pdtllistNetComponents) { DestroyEntryNode( pdtlnode ); return NULL; }
#ifdef AMB
ppbentry->dwAuthentication = (DWORD )AS_Default; #endif
ppbentry->fIpPrioritizeRemote = TRUE; ppbentry->fIpHeaderCompression = TRUE; ppbentry->pszIpAddress = NULL; ppbentry->pszIpDnsAddress = NULL; ppbentry->pszIpDns2Address = NULL; ppbentry->pszIpWinsAddress = NULL; ppbentry->pszIpWins2Address = NULL; ppbentry->dwIpAddressSource = ASRC_ServerAssigned; ppbentry->dwIpNameSource = ASRC_ServerAssigned; ppbentry->dwFrameSize = 1006;
//Changed Vivekk - BugId: 105777
if ( !IsServerOS() ) ppbentry->dwIpDnsFlags = 0; else ppbentry->dwIpDnsFlags = DNS_RegDefault;
ppbentry->dwIpNbtFlags = PBK_ENTRY_IP_NBT_Enable;
// Whistler bug 300933. 0=default
//
ppbentry->dwTcpWindowSize = 0; ppbentry->pszIpDnsSuffix = NULL;
// Router page fields.
//
ppbentry->dwCallbackMode = CBM_No; ppbentry->fAuthenticateServer = FALSE;
// Other fields not shown in UI.
//
ppbentry->pszCustomDialDll = NULL; ppbentry->pszCustomDialFunc = NULL;
ppbentry->pszCustomDialerName = NULL;
ppbentry->dwDialParamsUID = GetTickCount();
ppbentry->pGuid = Malloc( sizeof(GUID) ); if (ppbentry->pGuid) { if(UuidCreate( (UUID* )(ppbentry->pGuid) )) { } }
ppbentry->pszOldUser = NULL; ppbentry->pszOldDomain = NULL;
// Status flags. 'fDirty' is set when the entry has changed so as to
// differ from the phonebook file on disk. 'fCustom' is set when the
// entry contains at least one MEDIA and DEVICE (so RASAPI is able to read
// it) but was not created by us. When 'fCustom' is set only 'pszEntry'
// is guaranteed valid and the entry cannot be edited.
//
ppbentry->fDirty = FALSE; ppbentry->fCustom = FALSE;
return pdtlnode; }
DTLNODE* CreateLinkNode( void )
// Allocates a sized phonebook entry link node and fills it with default
// values.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pdtlnode; PBLINK* ppblink;
TRACE( "CreateLinkNode" );
pdtlnode = DtlCreateSizedNode( sizeof(PBLINK), 0L ); if (!pdtlnode) { return NULL; }
ppblink = (PBLINK* )DtlGetData( pdtlnode ); ASSERT( ppblink );
CopyToPbport( &ppblink->pbport, NULL );
ppblink->dwBps = 0; ppblink->fHwFlow = TRUE; ppblink->fEc = TRUE; ppblink->fEcc = TRUE; ppblink->fSpeaker = TRUE; ppblink->dwModemProtocol = 0;
ppblink->fProprietaryIsdn = FALSE; ppblink->lLineType = 0; ppblink->fFallback = TRUE; ppblink->fCompression = TRUE; ppblink->lChannels = 1;
ppblink->pTapiBlob = NULL; ppblink->cbTapiBlob = 0;
ppblink->iLastSelectedPhone = 0; ppblink->fPromoteAlternates = FALSE; ppblink->fTryNextAlternateOnFail = TRUE;
ppblink->fEnabled = TRUE;
// The list of phone number blocks is created but left empty.
//
ppblink->pdtllistPhones = DtlCreateList( 0 ); if (!ppblink->pdtllistPhones) { Free( ppblink ); return NULL; }
return pdtlnode; }
VOID GetCountryCodeAndID( IN PBPHONE* pPhone )
// Get TAPI�s country ID for the current location. This is needed because
// it�s needed for lineGetCountry.
//
{ static BOOLEAN fAlreadyQueried = FALSE; static DWORD dwPreviousCountryCode = 1; static DWORD dwPreviousCountryID = 1; LPLINETRANSLATECAPS lpTranslateCaps = NULL; LPLINELOCATIONENTRY lpLocationList = NULL; DWORD dwErr = 0; DWORD dwNeededSize = 0; DWORD dwLocationIndex = 0;
TRACE("GetCountryCodeAndID"); ASSERT(pPhone != NULL);
// Check to see if we've done this already so we don't have to do it again.
//
if (fAlreadyQueried) { pPhone->dwCountryCode = dwPreviousCountryCode; pPhone->dwCountryID = dwPreviousCountryID; return; }
// It's okay to set fAlreadyQueried since the defaults are set up to valid
// values.
//
fAlreadyQueried = TRUE;
// Setup the defaults in case something fails.
//
pPhone->dwCountryCode = 1; pPhone->dwCountryID = 1;
lpTranslateCaps = Malloc(sizeof(LINETRANSLATECAPS)); if (lpTranslateCaps == NULL) { return; }
// Query lineGetTranslateCaps to find out how big our LINETRANSLATECAPS
// structure needs to be.
//
lpTranslateCaps->dwTotalSize = sizeof(LINETRANSLATECAPS); dwErr = lineGetTranslateCaps(0, TAPI_CURRENT_VERSION, lpTranslateCaps); if (dwErr != 0) { Free(lpTranslateCaps); return; }
// Make our LINETRANSLATECAPS structure big enough.
//
dwNeededSize = lpTranslateCaps->dwNeededSize; Free(lpTranslateCaps); lpTranslateCaps = Malloc(dwNeededSize); if (lpTranslateCaps == NULL) { return; }
// Now we can actually go and get the locations.
//
lpTranslateCaps->dwTotalSize = dwNeededSize; dwErr = lineGetTranslateCaps(0, TAPI_CURRENT_VERSION, lpTranslateCaps); if (dwErr != 0) { Free(lpTranslateCaps); return; }
// Walk through the locations, looking for the current location.
//
lpLocationList = (LPLINELOCATIONENTRY) ( ((LPSTR)lpTranslateCaps) + lpTranslateCaps->dwLocationListOffset ); for ( dwLocationIndex=0; dwLocationIndex < lpTranslateCaps->dwNumLocations; dwLocationIndex++ ) { if (lpLocationList[dwLocationIndex].dwPermanentLocationID == lpTranslateCaps->dwCurrentLocationID) { break; } }
// If we found the current location, we know which country�s ID to use for dialing rules.
//
if (dwLocationIndex < lpTranslateCaps->dwNumLocations) { pPhone->dwCountryCode = lpLocationList[dwLocationIndex].dwCountryCode; pPhone->dwCountryID = lpLocationList[dwLocationIndex].dwCountryID;
// Save the values in case we're called again.
//
dwPreviousCountryCode = pPhone->dwCountryCode; dwPreviousCountryID = pPhone->dwCountryID; }
Free(lpTranslateCaps); }
DTLNODE* CreatePhoneNode( void )
// Allocates a sized phone number node and fills it with default values.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pNode; PBPHONE* pPhone;
TRACE( "CreatePhoneNode" );
pNode = DtlCreateSizedNode( sizeof(PBPHONE), 0L ); if (!pNode) { return NULL; }
pPhone = (PBPHONE* )DtlGetData( pNode ); ASSERT( pPhone );
GetCountryCodeAndID( pPhone );
pPhone->fUseDialingRules = FALSE;
return pNode; }
DTLNODE* CreatePortNode( void )
// Allocates a sized port node and fills it with default values.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pdtlnode; PBPORT* ppbport;
TRACE( "CreatePortNode" );
pdtlnode = DtlCreateSizedNode( sizeof(PBPORT), 0L ); if (!pdtlnode) { return NULL; }
ppbport = (PBPORT* )DtlGetData( pdtlnode ); ASSERT( ppbport );
CopyToPbport( ppbport, NULL );
return pdtlnode; }
VOID DestroyPort( PBPORT* pPort) { Free0( pPort->pszDevice ); Free0( pPort->pszMedia ); Free0( pPort->pszPort ); Free0( pPort->pszScriptBefore );
// pmay: 228565
// Clean up the list of available protocols
// if any.
//
if ( pPort->pListProtocols ) { DtlDestroyList( pPort->pListProtocols, NULL ); } }
VOID DestroyEntryTypeNode( IN DTLNODE *pdtlnode) { DtlDestroyNode(pdtlnode); }
VOID DestroyEntryNode( IN DTLNODE* pdtlnode )
// Release all memory associated with phonebook entry node 'pdtlnode'.
// See DtlDestroyList.
//
{ PBENTRY* ppbentry;
TRACE( "DestroyEntryNode" );
ASSERT( pdtlnode ); ppbentry = (PBENTRY* )DtlGetData( pdtlnode ); ASSERT( ppbentry );
Free0( ppbentry->pszEntryName ); Free0( ppbentry->pszPrerequisiteEntry ); Free0( ppbentry->pszPrerequisitePbk ); Free0( ppbentry->pszPreferredPort ); Free0( ppbentry->pszPreferredDevice );
Free0( ppbentry->pCustomAuthData );
Free0( ppbentry->pszScriptAfter ); Free0( ppbentry->pszX25Network ); Free0( ppbentry->pszX25Address ); Free0( ppbentry->pszX25UserData ); Free0( ppbentry->pszX25Facilities );
Free0( ppbentry->pszIpAddress ); Free0( ppbentry->pszIpDnsAddress ); Free0( ppbentry->pszIpDns2Address ); Free0( ppbentry->pszIpWinsAddress ); Free0( ppbentry->pszIpWins2Address ); Free0( ppbentry->pszIpDnsSuffix );
Free0( ppbentry->pszCustomDialDll ); Free0( ppbentry->pszCustomDialFunc ); Free0( ppbentry->pszCustomDialerName);
Free0( ppbentry->pszOldUser ); Free0( ppbentry->pszOldDomain );
Free0( ppbentry->pGuid );
DtlDestroyList( ppbentry->pdtllistLinks, DestroyLinkNode ); DtlDestroyList( ppbentry->pdtllistNetComponents, DestroyKvNode );
DtlDestroyNode( pdtlnode ); }
VOID DestroyLinkNode( IN DTLNODE* pdtlnode )
// Release all memory associated with phonebook entry link node
// 'pdtlnode'. See DtlDestroyList.
//
{ PBLINK* ppblink;
TRACE( "DestroyLinkNode" );
ASSERT( pdtlnode ); ppblink = (PBLINK* )DtlGetData( pdtlnode ); ASSERT( ppblink );
DestroyPort(&(ppblink->pbport)); Free0( ppblink->pTapiBlob ); DtlDestroyList( ppblink->pdtllistPhones, DestroyPhoneNode );
DtlDestroyNode( pdtlnode ); }
VOID DestroyPhoneNode( IN DTLNODE* pdtlnode )
// Release memory associated with PBPHONE node 'pdtlnode'. See
// DtlDestroyList.
//
{ PBPHONE* pPhone;
TRACE( "DestroyPhoneNode" );
ASSERT( pdtlnode ); pPhone = (PBPHONE* )DtlGetData( pdtlnode ); ASSERT( pPhone );
Free0( pPhone->pszAreaCode ); Free0( pPhone->pszPhoneNumber ); Free0( pPhone->pszComment );
DtlDestroyNode( pdtlnode ); }
VOID DestroyPortNode( IN DTLNODE* pdtlnode )
// Release memory associated with PBPORT node 'pdtlnode'. See
// DtlDestroyList.
//
{ PBPORT* pPort;
TRACE( "DestroyPortNode" );
ASSERT( pdtlnode ); pPort = (PBPORT* )DtlGetData( pdtlnode ); ASSERT( pPort );
DestroyPort(pPort);
DtlDestroyNode( pdtlnode ); }
DTLNODE* DuplicateEntryNode( DTLNODE* pdtlnodeSrc )
// Duplicates phonebook entry node 'pdtlnodeSrc'. See CloneEntryNode and
// DtlDuplicateList.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pdtlnodeDst; PBENTRY* ppbentrySrc; PBENTRY* ppbentryDst; BOOL fDone;
TRACE( "DuplicateEntryNode" );
pdtlnodeDst = DtlCreateSizedNode( sizeof(PBENTRY), 0L ); if (!pdtlnodeDst) { return NULL; }
ppbentrySrc = (PBENTRY* )DtlGetData( pdtlnodeSrc ); ppbentryDst = (PBENTRY* )DtlGetData( pdtlnodeDst ); fDone = FALSE;
CopyMemory( ppbentryDst, ppbentrySrc, sizeof(PBENTRY) );
ppbentryDst->pszEntryName = NULL; ppbentryDst->pdtllistLinks = NULL; ppbentryDst->pszPrerequisiteEntry = NULL; ppbentryDst->pszPrerequisitePbk = NULL; ppbentryDst->pszPreferredPort = NULL; ppbentryDst->pszPreferredDevice = NULL;
//For .Net 639551 Add preferred info for Modem settings
ppbentryDst->dwPreferredBps = 0; ppbentryDst->fPreferredHwFlow = 0; ppbentryDst->fPreferredEc = 0; ppbentryDst->fPreferredEcc = 0; ppbentryDst->fPreferredSpeaker = 0; ppbentryDst->dwPreferredModemProtocol = 0;
ppbentryDst->pCustomAuthData = NULL;
ppbentryDst->pszScriptAfter = NULL; ppbentryDst->pszX25Network = NULL; ppbentryDst->pszX25Address = NULL; ppbentryDst->pszX25UserData = NULL; ppbentryDst->pszX25Facilities = NULL;
ppbentryDst->pdtllistNetComponents = NULL;
ppbentryDst->pszIpAddress = NULL; ppbentryDst->pszIpDnsAddress = NULL; ppbentryDst->pszIpDns2Address = NULL; ppbentryDst->pszIpWinsAddress = NULL; ppbentryDst->pszIpWins2Address = NULL; ppbentryDst->pszIpDnsSuffix = NULL;
ppbentryDst->pszCustomDialDll = NULL; ppbentryDst->pszCustomDialFunc = NULL; ppbentryDst->pszCustomDialerName = NULL;
ppbentryDst->pGuid = NULL;
ppbentryDst->pszOldUser = NULL; ppbentryDst->pszOldDomain = NULL;
do { // Duplicate strings.
//
if (ppbentrySrc->pszEntryName && (!(ppbentryDst->pszEntryName = StrDup( ppbentrySrc->pszEntryName )))) { break; }
if (ppbentrySrc->pszPrerequisiteEntry && (!(ppbentryDst->pszPrerequisiteEntry = StrDup( ppbentrySrc->pszPrerequisiteEntry )))) { break; }
if (ppbentrySrc->pszPrerequisitePbk && (!(ppbentryDst->pszPrerequisitePbk = StrDup( ppbentrySrc->pszPrerequisitePbk )))) { break; }
if (ppbentrySrc->pszPreferredPort && (!(ppbentryDst->pszPreferredPort = StrDup( ppbentrySrc->pszPreferredPort )))) { break; }
ppbentryDst->dwPreferredModemProtocol = ppbentrySrc->dwPreferredModemProtocol;
//For .Net 639551 Add preferred info for Modem settings
ppbentryDst->dwPreferredBps = ppbentrySrc->dwPreferredBps; ppbentryDst->fPreferredHwFlow = ppbentrySrc->fPreferredHwFlow; ppbentryDst->fPreferredEc = ppbentrySrc->fPreferredEc; ppbentryDst->fPreferredEcc = ppbentrySrc->fPreferredEcc ; ppbentryDst->fPreferredSpeaker = ppbentrySrc->fPreferredSpeaker; if (ppbentrySrc->pszPreferredDevice && (!(ppbentryDst->pszPreferredDevice = StrDup( ppbentrySrc->pszPreferredDevice )))) { break; }
if (ppbentrySrc->cbCustomAuthData && ppbentrySrc->pCustomAuthData) { ppbentryDst->pCustomAuthData = Malloc( ppbentrySrc->cbCustomAuthData ); if (!ppbentryDst->pCustomAuthData) { break; } CopyMemory( ppbentryDst->pCustomAuthData, ppbentrySrc->pCustomAuthData, ppbentrySrc->cbCustomAuthData); ppbentryDst->cbCustomAuthData = ppbentrySrc->cbCustomAuthData; }
if (ppbentrySrc->pszIpAddress && (!(ppbentryDst->pszIpAddress = StrDup( ppbentrySrc->pszIpAddress )))) { break; }
if (ppbentrySrc->pszIpDnsAddress && (!(ppbentryDst->pszIpDnsAddress = StrDup( ppbentrySrc->pszIpDnsAddress )))) { break; }
if (ppbentrySrc->pszIpDns2Address && (!(ppbentryDst->pszIpDns2Address = StrDup( ppbentrySrc->pszIpDns2Address )))) { break; }
if (ppbentrySrc->pszIpWinsAddress && (!(ppbentryDst->pszIpWinsAddress = StrDup( ppbentrySrc->pszIpWinsAddress )))) { break; }
if (ppbentrySrc->pszIpWins2Address && (!(ppbentryDst->pszIpWins2Address = StrDup( ppbentrySrc->pszIpWins2Address )))) { break; }
if (ppbentrySrc->pszIpDnsSuffix && (!(ppbentryDst->pszIpDnsSuffix = StrDup( ppbentrySrc->pszIpDnsSuffix )))) { break; }
if (ppbentrySrc->pszScriptAfter && (!(ppbentryDst->pszScriptAfter = StrDup( ppbentrySrc->pszScriptAfter )))) { break; }
if (ppbentrySrc->pszX25Network && (!(ppbentryDst->pszX25Network = StrDup( ppbentrySrc->pszX25Network )))) { break; }
if (ppbentrySrc->pszX25Address && (!(ppbentryDst->pszX25Address = StrDup( ppbentrySrc->pszX25Address )))) { break; }
if (ppbentrySrc->pszX25UserData && (!(ppbentryDst->pszX25UserData = StrDup( ppbentrySrc->pszX25UserData )))) { break; }
if (ppbentrySrc->pszX25Facilities && (!(ppbentryDst->pszX25Facilities = StrDup( ppbentrySrc->pszX25Facilities )))) { break; }
if (ppbentrySrc->pszCustomDialDll && (!(ppbentryDst->pszCustomDialDll = StrDup( ppbentrySrc->pszCustomDialDll )))) { break; }
if (ppbentrySrc->pszCustomDialFunc && (!(ppbentryDst->pszCustomDialFunc = StrDup( ppbentrySrc->pszCustomDialFunc )))) { break; }
if (ppbentrySrc->pszCustomDialerName && (!(ppbentryDst->pszCustomDialerName = StrDup( ppbentrySrc->pszCustomDialerName)))) { break; }
if (ppbentrySrc->pszOldUser && (!(ppbentryDst->pszOldUser = StrDup( ppbentrySrc->pszOldUser )))) { break; }
if (ppbentrySrc->pszOldDomain && (!(ppbentryDst->pszOldDomain = StrDup( ppbentrySrc->pszOldDomain )))) { break; }
// Duplicate GUID.
//
if (ppbentrySrc->pGuid) { ppbentryDst->pGuid = Malloc( sizeof( GUID ) ); if (!ppbentryDst->pGuid) { break; }
*ppbentryDst->pGuid = *ppbentrySrc->pGuid; }
// Duplicate net component list information.
//
if (ppbentrySrc->pdtllistNetComponents && (!(ppbentryDst->pdtllistNetComponents = DtlDuplicateList( ppbentrySrc->pdtllistNetComponents, DuplicateKvNode, DestroyKvNode )))) { break; }
// Duplicate list of link information.
//
if (ppbentrySrc->pdtllistLinks && (!(ppbentryDst->pdtllistLinks = DtlDuplicateList( ppbentrySrc->pdtllistLinks, DuplicateLinkNode, DestroyLinkNode )))) { break; }
fDone = TRUE; } while (FALSE);
if (!fDone) { DestroyEntryNode( pdtlnodeDst ); return NULL; }
// Since the copy is "new" it is inherently dirty relative to the
// phonebook file.
//
ppbentryDst->fDirty = TRUE;
return pdtlnodeDst; }
DTLNODE* DuplicateLinkNode( IN DTLNODE* pdtlnodeSrc )
// Duplicates phonebook entry link node 'pdtlnodeSrc'. See
// DtlDuplicateList.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pdtlnodeDst; PBLINK* ppblinkSrc; PBLINK* ppblinkDst; BOOL fDone;
TRACE( "DuplicateLinkNode" );
pdtlnodeDst = DtlCreateSizedNode( sizeof(PBLINK), 0L ); if (!pdtlnodeDst) { return NULL; }
ppblinkSrc = (PBLINK* )DtlGetData( pdtlnodeSrc ); ppblinkDst = (PBLINK* )DtlGetData( pdtlnodeDst ); fDone = FALSE;
CopyMemory( ppblinkDst, ppblinkSrc, sizeof(PBLINK) );
ppblinkDst->pbport.pszDevice = NULL; ppblinkDst->pbport.pszMedia = NULL; ppblinkDst->pbport.pszPort = NULL; ppblinkDst->pbport.pszScriptBefore = NULL; ppblinkDst->pbport.pListProtocols = NULL; ppblinkDst->pTapiBlob = NULL; ppblinkDst->pdtllistPhones = NULL;
do { // Duplicate strings.
//
if (ppblinkSrc->pbport.pszDevice && (!(ppblinkDst->pbport.pszDevice = StrDup( ppblinkSrc->pbport.pszDevice )))) { break; }
if (ppblinkSrc->pbport.pszMedia && (!(ppblinkDst->pbport.pszMedia = StrDup( ppblinkSrc->pbport.pszMedia )))) { break; }
if (ppblinkSrc->pbport.pszPort && (!(ppblinkDst->pbport.pszPort = StrDup( ppblinkSrc->pbport.pszPort )))) { break; }
if (ppblinkSrc->pbport.pszScriptBefore && (!(ppblinkDst->pbport.pszScriptBefore = StrDup( ppblinkSrc->pbport.pszScriptBefore )))) { break; }
// Duplicate TAPI blob.
//
if (ppblinkSrc->pTapiBlob) { VOID* pTapiBlobDst;
ppblinkDst->pTapiBlob = (VOID* )Malloc( ppblinkSrc->cbTapiBlob ); if (!ppblinkDst->pTapiBlob) break;
CopyMemory( ppblinkDst->pTapiBlob, ppblinkSrc->pTapiBlob, ppblinkSrc->cbTapiBlob ); }
// Duplicate list of phone numbers.
//
if (ppblinkSrc->pdtllistPhones && (!(ppblinkDst->pdtllistPhones = DtlDuplicateList( ppblinkSrc->pdtllistPhones, DuplicatePhoneNode, DestroyPhoneNode )))) { break; }
//For whistler bug 398438 gangz
//If the pListProtocls is not duplicated, then in EuFree() which calls
// DestoryEntryNode() to free EINFO->pNode, ClosePhonebookFile() to
// free EINFO->pFile, both of them will eventually free this
// pListProtocols, then an AV will occur.
//
if (ppblinkSrc->pbport.pListProtocols && ( !(ppblinkDst->pbport.pListProtocols = DtlDuplicateList( ppblinkSrc->pbport.pListProtocols, DuplicateProtocolNode, DestroyProtocolNode)))) { break; } fDone = TRUE; } while (FALSE);
if (!fDone) { DestroyLinkNode( pdtlnodeDst ); return NULL; }
return pdtlnodeDst; }
//For whistler bug 398438 gangz
//
DTLNODE* DuplicateProtocolNode( IN DTLNODE* pdtlnodeSrc ) { DTLNODE* pdtlnodeDst = NULL; BOOL fDone = FALSE; PVOID pNameSrc = NULL;
TRACE( "DuplicateProtocolNode" );
pdtlnodeDst = DtlCreateSizedNode( sizeof(DTLNODE), 0L ); if ( !pdtlnodeDst ) { return NULL; }
do { pNameSrc = DtlGetData( pdtlnodeSrc ); if(pNameSrc && ( !(pdtlnodeDst->pData = StrDup(pNameSrc) )) ) { break; }
pdtlnodeDst->lNodeId = pdtlnodeSrc->lNodeId; fDone = TRUE; } while(FALSE);
if (!fDone) { DestroyProtocolNode(pdtlnodeDst); return NULL; }
return pdtlnodeDst; }
VOID DestroyProtocolNode( IN DTLNODE* pdtlnode )
// Release memory associated with PBPHONE node 'pdtlnode'. See
// DtlDestroyList.
//
{ TRACE( "DestroyProtocolNode" );
DtlDestroyNode( pdtlnode ); }
DTLNODE* DuplicatePhoneNode( IN DTLNODE* pdtlnodeSrc )
// Duplicates phone number set node 'pdtlnodeSrc'. See DtlDuplicateList.
//
// Returns the address of the allocated node if successful, NULL
// otherwise. It's the caller's responsibility to free the block.
//
{ DTLNODE* pdtlnodeDst; PBPHONE* pPhoneSrc; PBPHONE* pPhoneDst; BOOL fDone;
TRACE( "DuplicatePhoneNode" );
pdtlnodeDst = DtlCreateSizedNode( sizeof(PBPHONE), 0L ); if (!pdtlnodeDst) { return NULL; }
pPhoneSrc = (PBPHONE* )DtlGetData( pdtlnodeSrc ); pPhoneDst = (PBPHONE* )DtlGetData( pdtlnodeDst ); fDone = FALSE;
CopyMemory( pPhoneDst, pPhoneSrc, sizeof(PBPHONE) );
pPhoneDst->pszPhoneNumber = NULL; pPhoneDst->pszAreaCode = NULL; pPhoneDst->pszComment = NULL;
do { // Duplicate strings.
//
if (pPhoneSrc->pszPhoneNumber && (!(pPhoneDst->pszPhoneNumber = StrDup( pPhoneSrc->pszPhoneNumber )))) { break; }
if (pPhoneSrc->pszAreaCode && (!(pPhoneDst->pszAreaCode = StrDup( pPhoneSrc->pszAreaCode )))) { break; }
if (pPhoneSrc->pszComment && (!(pPhoneDst->pszComment = StrDup( pPhoneSrc->pszComment )))) { break; }
fDone = TRUE; } while (FALSE);
if (!fDone) { DestroyPhoneNode( pdtlnodeDst ); return NULL; }
return pdtlnodeDst; }
VOID EnableOrDisableNetComponent( IN PBENTRY* pEntry, IN LPCTSTR pszComponent, IN BOOL fEnable) { KEYVALUE* pKv; BOOL fIsEnabled;
static const TCHAR c_pszDisabledValue[] = TEXT("0"); static const TCHAR c_pszEnabledValue [] = TEXT("1");
ASSERT (pEntry); ASSERT (pszComponent);
// If the component already exists in the list, update its value.
//
if (FIsNetComponentListed (pEntry, pszComponent, &fIsEnabled, &pKv)) { LPCTSTR pszNewValue = NULL;
// If we need to change the value, do so, otherwise, we don't have
// any work to do. (Use a logical XOR here instead of == because
// there are many values of TRUE.
//
if (fEnable && !fIsEnabled) { pszNewValue = c_pszEnabledValue; } else if (!fEnable && fIsEnabled) { pszNewValue = c_pszDisabledValue; }
if (pszNewValue) { Free0 (pKv->pszValue); pKv->pszValue = StrDup(pszNewValue); } }
// If the component does not exist in the list, we need to add it.
//
else { LPCTSTR pszValue; DTLNODE* pdtlnode;
pszValue = (fEnable) ? c_pszEnabledValue : c_pszDisabledValue; pdtlnode = CreateKvNode (pszComponent, pszValue); if (pdtlnode) { ASSERT( DtlGetData(pdtlnode) ); DtlAddNodeLast (pEntry->pdtllistNetComponents, pdtlnode); } } }
BOOL FIsNetComponentListed( IN PBENTRY* pEntry, IN LPCTSTR pszComponent, OUT BOOL* pfEnabled, OUT KEYVALUE** ppKv)
// Returns TRUE if the pszComponent exists as the key of the NETCOMPONENTs
// KEYVALUE pairs in pEntry. If TRUE is returned, *pfEnabled is the
// BOOL form of the value part of the pair. This represents whether the
// component is 'checked' in the property UI on the networking page.
// ppKv is an optional output parameter. If ppKv is specfied, and the
// function returns TRUE, it will point to the KEYVALUE in the DTLLIST
// of NETCOMPONENTS.
{ DTLNODE* pdtlnode; BOOL fPresent = FALSE;
ASSERT (pEntry); ASSERT (pEntry->pdtllistNetComponents); ASSERT (pszComponent); ASSERT (pfEnabled);
// Initialize the output parameters.
//
*pfEnabled = FALSE; if (ppKv) { *ppKv = NULL; }
// Look for pszComponent in the list.
//
for (pdtlnode = DtlGetFirstNode (pEntry->pdtllistNetComponents); pdtlnode; pdtlnode = DtlGetNextNode (pdtlnode)) { KEYVALUE* pKv = (KEYVALUE* )DtlGetData (pdtlnode); ASSERT (pKv);
if (0 == lstrcmp(pszComponent, pKv->pszKey)) { // If we found the component, get its value (as a BOOL)
// and return the KEYVALUE pointer if requested.
//
LONG lValue = _ttol (pKv->pszValue); *pfEnabled = !!lValue;
fPresent = TRUE;
if (ppKv) { *ppKv = pKv; }
break; } }
return fPresent; }
DTLNODE* EntryNodeFromName( IN DTLLIST* pdtllistEntries, IN LPCTSTR pszName )
// Returns the address of the node in the global phonebook entries list
// whose Entry Name matches 'pszName' or NULL if none.
//
{ DTLNODE* pdtlnode;
for (pdtlnode = DtlGetFirstNode( pdtllistEntries ); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { PBENTRY* ppbentry = (PBENTRY* )DtlGetData( pdtlnode );
if (lstrcmpi( ppbentry->pszEntryName, pszName ) == 0) { return pdtlnode; } }
return NULL; }
DWORD EntryTypeFromPbport( IN PBPORT* ppbport )
// Returns the RASET_* entry type associated with the 'ppbport' port type.
//
{ DWORD dwType;
// Default is phone type
//
dwType = RASET_Phone;
if ((ppbport->pbdevicetype == PBDT_Null) || (ppbport->dwFlags & PBP_F_NullModem) || (ppbport->pbdevicetype == PBDT_Irda) || (ppbport->pbdevicetype == PBDT_Parallel)) { dwType = RASET_Direct; } else if (ppbport->pbdevicetype == PBDT_Vpn) { dwType = RASET_Vpn; } else if (ppbport->pbdevicetype == PBDT_PPPoE) { dwType = RASET_Broadband; } else if (ppbport->pszPort) { TCHAR achPort[ 3 + 1 ];
lstrcpyn( achPort, ppbport->pszPort, 3 + 1 );
if (lstrcmp( achPort, TEXT("VPN") ) == 0) { dwType = RASET_Vpn; } }
return dwType; }
DWORD GetOverridableParam( IN PBUSER* pUser, IN PBENTRY* pEntry, IN DWORD dwfRasorBit )
// Return the value of the parameter identified by RASOR_* the single bit
// in bitmask 'dwfRasorBit', retrieving the value from the 'pUser' or
// 'pEntry' based on the override mask in 'pEntry'.
//
{ switch (dwfRasorBit) { case RASOR_RedialAttempts: { if (pEntry->dwfOverridePref & RASOR_RedialAttempts) { return pEntry->dwRedialAttempts; } else { return pUser->dwRedialAttempts; } }
case RASOR_RedialSeconds: { if (pEntry->dwfOverridePref & RASOR_RedialSeconds) { return pEntry->dwRedialSeconds; } else { return pUser->dwRedialSeconds; } }
case RASOR_IdleDisconnectSeconds: { if (pEntry->dwfOverridePref & RASOR_IdleDisconnectSeconds) { return (DWORD )pEntry->lIdleDisconnectSeconds; } else { return pUser->dwIdleDisconnectSeconds; } }
case RASOR_RedialOnLinkFailure: { if (pEntry->dwfOverridePref & RASOR_RedialOnLinkFailure) { return pEntry->fRedialOnLinkFailure; } else { return pUser->fRedialOnLinkFailure; } }
case RASOR_PopupOnTopWhenRedialing: { if (pEntry->dwfOverridePref & RASOR_PopupOnTopWhenRedialing) { #if 0
return pEntry->fPopupOnTopWhenRedialing; #else
return (DWORD )TRUE; #endif
} else { return pUser->fPopupOnTopWhenRedialing; } }
case RASOR_CallbackMode: { if (pEntry->dwfOverridePref & RASOR_CallbackMode) { return pEntry->dwCallbackMode; } else { return pUser->dwCallbackMode; } } }
return 0; }
DWORD PbkPathInfoInit( IN PbkPathInfo* pInfo) { DWORD dwErr = NO_ERROR; ZeroMemory(pInfo, sizeof(PbkPathInfo));
//Add try...except blocck for bug 763057
__try { InitializeCriticalSection(&(pInfo->csLock)); } __except(EXCEPTION_EXECUTE_HANDLER) { dwErr = ERROR_NOT_ENOUGH_MEMORY; }
return dwErr; } DWORD PbkPathInfoReset( OUT PbkPathInfo* pInfo) { if (pInfo) { if (pInfo->hSwapiDll) { FreeLibrary(pInfo->hSwapiDll); } Free0(pInfo->pszAllUsers); Free0(pInfo->pszSysRas);
pInfo->fLoaded = FALSE; pInfo->hSwapiDll = NULL; pInfo->pPathCanonicalize = NULL; pInfo->pPathRemoveFileSpec = NULL; pInfo->pszAllUsers = NULL; pInfo->pszSysRas = NULL; }
return NO_ERROR; }
DWORD PbkPathInfoLoad( OUT PbkPathInfo* pInfo) { DWORD dwErr = NO_ERROR; BOOL fOk; TCHAR* pszTemp = NULL; EnterCriticalSection(&pInfo->csLock); do { if (pInfo->fLoaded) { dwErr = NO_ERROR; break; }
pInfo->pszAllUsers = Malloc( (MAX_PATH + 1) * sizeof(TCHAR) ); pInfo->pszSysRas = Malloc( (MAX_PATH + 1) * sizeof(TCHAR) ); pszTemp = Malloc( (MAX_PATH + 1) * sizeof(TCHAR) ); if ((!pInfo->pszAllUsers) || (!pInfo->pszSysRas) || (!pszTemp)) { dwErr = ERROR_NOT_ENOUGH_MEMORY; break; } pInfo->hSwapiDll= LoadLibrary(TEXT("shlwapi.dll")); if (pInfo->hSwapiDll == NULL) { dwErr = GetLastError(); break; } pInfo->pPathCanonicalize = GetProcAddress(pInfo->hSwapiDll, SZ_PathCanonicalize); pInfo->pPathRemoveFileSpec = GetProcAddress(pInfo->hSwapiDll, SZ_PathRemoveFileSpec);
fOk = GetPhonebookDirectory(PBM_System, pszTemp); if (!fOk) { dwErr = ERROR_CAN_NOT_COMPLETE; break; } // Canonicalize the path and remove any trailing \ //
pInfo->pPathCanonicalize(pInfo->pszAllUsers, pszTemp); if(TEXT('\\') == *(pInfo->pszAllUsers + lstrlen(pInfo->pszAllUsers) - 1)) { *(pInfo->pszAllUsers + lstrlen(pInfo->pszAllUsers) - 1) = TEXT('\0'); }
fOk = GetSystemWindowsDirectory( pInfo->pszSysRas, MAX_PATH - S_SYSRASDIR_LENGTH); if (!fOk) { dwErr = ERROR_CAN_NOT_COMPLETE; break; } lstrcat(pInfo->pszSysRas, S_SYSRASDIR); pInfo->fLoaded = TRUE; } while (FALSE);
// Cleanup
//
{ if (dwErr != NO_ERROR) { PbkPathInfoReset(pInfo); } Free0(pszTemp); }
LeaveCriticalSection(&pInfo->csLock);
return dwErr; }
DWORD PbkPathInfoClear( OUT PbkPathInfo* pInfo) { PbkPathInfoReset(pInfo); DeleteCriticalSection(&(pInfo->csLock)); ZeroMemory(pInfo, sizeof(PbkPathInfo));
return NO_ERROR; }
BOOL IsPublicPhonebook( IN LPCTSTR pszPhonebookPath )
// Returns TRUE if the given phonebook is in the 'All Users' directory
// and hence is a shared phonebook; returns FALSE otherwise
//
{ BOOL bPublic = FALSE; TCHAR* pszPhonebook = NULL; DWORD dwErr = NO_ERROR;
do { pszPhonebook = Malloc( (MAX_PATH + 1) * sizeof(TCHAR) ); if ( !pszPhonebook ) { break; }
dwErr = PbkPathInfoLoad(&g_PbkPathInfo); if (dwErr != NO_ERROR) { TRACE1( "IsPublicPhonebook: Unable to load pbk path info %x", dwErr); break; }
g_PbkPathInfo.pPathCanonicalize(pszPhonebook, pszPhonebookPath); g_PbkPathInfo.pPathRemoveFileSpec(pszPhonebook);
if (!lstrcmpi(pszPhonebook, g_PbkPathInfo.pszAllUsers)) { bPublic = TRUE; } else { bPublic = (lstrcmpi(pszPhonebook, g_PbkPathInfo.pszSysRas) == 0); }
} while ( FALSE );
// Clean up
//
Free0 ( pszPhonebook );
TRACE1( "IsPublicPhonebook=%u", bPublic); return bPublic; }
DWORD LoadPadsList( OUT DTLLIST** ppdtllistPads )
// Build a list of all X.25 PAD devices in '*ppdtllistPads'.
//
// Returns 0 if successful, otherwise a non-zero error code. It is
// caller's responsibility to DtlDestroyList the list when done.
//
{ INT i; DWORD dwErr; RASMAN_DEVICE* pDevices; DWORD dwDevices;
TRACE( "LoadPadsList" );
*ppdtllistPads = NULL;
dwErr = GetRasPads( &pDevices, &dwDevices ); if (dwErr != 0) { return dwErr; }
*ppdtllistPads = DtlCreateList( 0L ); if (!*ppdtllistPads) { Free( pDevices ); return ERROR_NOT_ENOUGH_MEMORY; }
qsort( (VOID* )pDevices, (size_t )dwDevices, sizeof(RASMAN_DEVICE), CompareDevices );
for (i = 0; i < (INT )dwDevices; ++i) { TCHAR* pszDup;
pszDup = StrDupTFromA( pDevices[ i ].D_Name ); dwErr = AppendStringToList( *ppdtllistPads, pszDup ); Free0( pszDup );
if (dwErr != 0) { Free( pDevices ); DtlDestroyList( *ppdtllistPads, NULL ); *ppdtllistPads = NULL; return dwErr; } }
Free( pDevices );
TRACE( "LoadPadsList=0" ); return 0; }
DWORD LoadPortsList( OUT DTLLIST** ppdtllistPorts )
// Build a sorted list of all RAS ports in '*ppdtllistPorts'.
//
// Returns 0 if successful, otherwise a non-zero error code. It is
// caller's responsibility to DtlDestroyList the list when done.
//
{ return LoadPortsList2( NULL, ppdtllistPorts, FALSE ); }
DWORD LoadPortsList2( IN HANDLE hConnection, OUT DTLLIST** ppdtllistPorts, IN BOOL fRouter)
// Build a sorted list of all RAS ports in '*ppdtllistPorts'. 'FRouter'
// indicates only ports with "router" usage should be returned.
// Otherwise, only dialout ports are returned.
//
// Returns 0 if successful, otherwise a non-zero error code. It is
// caller's responsibility to DtlDestroyList the list when done.
//
{ INT i; DWORD dwErr; RASMAN_PORT* pPorts; RASMAN_PORT* pPort; DWORD dwPorts;
TRACE( "LoadPortsList2" );
*ppdtllistPorts = NULL;
dwErr = GetRasPorts( hConnection, &pPorts, &dwPorts ); if (dwErr != 0) { return dwErr; }
*ppdtllistPorts = DtlCreateList( 0L ); if (!*ppdtllistPorts) { return ERROR_NOT_ENOUGH_MEMORY; }
qsort( (VOID* )pPorts, (size_t )dwPorts, sizeof(RASMAN_PORT), ComparePorts );
for (i = 0, pPort = pPorts; i < (INT )dwPorts; ++i, ++pPort) { if (fRouter) { // We're only interested in router ports.
//
//Add this CALL_OUTBOUND_ROUTER for bug 349087 345068
//
if (!(pPort->P_ConfiguredUsage & CALL_ROUTER) && !(pPort->P_ConfiguredUsage &CALL_OUTBOUND_ROUTER) ) { continue; } } else { // We're only interested in ports you can dial-out on.
//
if (!(pPort->P_ConfiguredUsage & CALL_OUT)) { continue; } }
dwErr = AppendPbportToList( hConnection, *ppdtllistPorts, pPort ); if (dwErr != 0) { Free( pPorts ); DtlDestroyList( *ppdtllistPorts, NULL ); *ppdtllistPorts = NULL; return dwErr; } }
Free( pPorts );
TRACE( "LoadPortsList=0" ); return 0; }
DWORD LoadScriptsList( HANDLE hConnection, OUT DTLLIST** ppdtllistScripts )
// Build a sorted list of all RAS switch devices in '*ppdtllistPorts'.
//
// Returns 0 if successful, otherwise a non-zero error code. It is
// caller's responsibility to DtlDestroyList the list when done.
//
{ INT i; DWORD dwErr; RASMAN_DEVICE* pDevices; DWORD dwDevices;
TRACE( "LoadScriptsList" );
*ppdtllistScripts = NULL;
dwErr = GetRasSwitches( hConnection, &pDevices, &dwDevices ); if (dwErr != 0) { return dwErr; }
*ppdtllistScripts = DtlCreateList( 0L ); if (!*ppdtllistScripts) { Free( pDevices ); return ERROR_NOT_ENOUGH_MEMORY; }
qsort( (VOID* )pDevices, (size_t )dwDevices, sizeof(RASMAN_DEVICE), CompareDevices );
for (i = 0; i < (INT )dwDevices; ++i) { TCHAR* pszDup;
pszDup = StrDupTFromA( pDevices[ i ].D_Name );
if(NULL == pszDup) { return E_OUTOFMEMORY; } dwErr = AppendStringToList( *ppdtllistScripts, pszDup ); Free( pszDup );
if (dwErr != 0) { Free( pDevices ); DtlDestroyList( *ppdtllistScripts, NULL ); *ppdtllistScripts = NULL; return dwErr; } }
Free( pDevices );
TRACE( "LoadScriptsList=0" ); return 0; }
#if 0
TCHAR* NameFromIndex( IN DTLLIST* pdtllist, IN INT iToFind )
// Returns the name associated with 0-based index 'iToFind' in the linked
// list of strings, 'pdtllist', or NULL if not found.
//
{ DTLNODE* pdtlnode;
if (!pdtllist) { return NULL; }
pdtlnode = DtlGetFirstNode( pdtllist );
if (iToFind < 0) { return NULL; }
while (pdtlnode && iToFind--) { pdtlnode = DtlGetNextNode( pdtlnode ); }
return (pdtlnode) ? (TCHAR* )DtlGetData( pdtlnode ) : NULL; } #endif
PBDEVICETYPE PbdevicetypeFromPszType( IN TCHAR* pszDeviceType )
// Returns the device type corresponding to the device type string,
// 'pszDeviceType'.
//
{ CHAR* pszA; PBDEVICETYPE pbdt;
pbdt = PBDT_None; pszA = StrDupAFromT( pszDeviceType ); if (pszA) { pbdt = PbdevicetypeFromPszTypeA( pszA ); Free( pszA ); } return pbdt; }
PBDEVICETYPE PbdevicetypeFromPszTypeA( IN CHAR* pszDeviceTypeA )
// Returns the device type corresponding to the ANSI device type string,
// 'pszDeviceType'.
//
{ PBDEVICETYPE pbdt; TCHAR *pszDeviceType = StrDupTFromA(pszDeviceTypeA);
if(NULL == pszDeviceType) { return PBDT_None; } if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Modem, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Modem; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, TEXT("null"), -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Null; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Parallel, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Parallel; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Irda, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Irda; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Pad, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Pad; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, TEXT("switch"), -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Switch; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Isdn, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Isdn; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_X25, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_X25; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Vpn, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Vpn; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Atm, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Atm; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Serial, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Serial; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_FrameRelay, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_FrameRelay; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_Sonet, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Sonet; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_SW56, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_Sw56; } else if( CSTR_EQUAL == CompareString( LOCALE_INVARIANT, NORM_IGNORECASE, RASDT_PPPoE, -1, pszDeviceType, -1 ) ) { pbdt = PBDT_PPPoE; } else { pbdt = PBDT_Other; } if(pszDeviceType) { Free(pszDeviceType); }
return pbdt; }
CHAR* PbMedia( IN PBDEVICETYPE pbdt, IN CHAR* pszMedia )
// The media names stored in the phonebook are not exactly the same as
// those returned by RASMAN. This translates a RASMAN media name to
// equivalent phonebook media names given the device type. The reason for
// this is historical and obscure.
//
{ if (pbdt == PBDT_Isdn) { return ISDN_TXT; } else if (pbdt == PBDT_X25) { return X25_TXT; } else if ( pbdt == PBDT_Other || pbdt == PBDT_Vpn || pbdt == PBDT_Irda || pbdt == PBDT_Serial || pbdt == PBDT_Atm || pbdt == PBDT_Parallel || pbdt == PBDT_Sonet || pbdt == PBDT_Sw56 || pbdt == PBDT_FrameRelay || pbdt == PBDT_PPPoE) { return pszMedia; } else { return SERIAL_TXT; } }
PBPORT* PpbportFromPortAndDeviceName( IN DTLLIST* pdtllistPorts, IN TCHAR* pszPort, IN TCHAR* pszDevice )
// Return port with port name 'pszPort' and device name 'pszDevice' in
// list of ports 'pdtllistPorts' or NULL if not found. 'PszPort' may be
// an old-style name such as PcImacISDN1, in which case it will match
// ISDN1. 'PszDevice' may be NULL in which case any device name is
// assumed to match.
//
{ DTLNODE* pdtlnode;
TCHAR szPort[MAX_PORT_NAME+1];
if (!pszPort) { return NULL; }
for (pdtlnode = DtlGetFirstNode( pdtllistPorts ); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { PBPORT* ppbport = (PBPORT* )DtlGetData( pdtlnode );
if ((ppbport->pszPort && lstrcmp( ppbport->pszPort, pszPort ) == 0) && (!ppbport->pszDevice || !pszDevice || lstrcmp( ppbport->pszDevice, pszDevice ) == 0)) { return ppbport; } }
// No match. Look for the old port name format.
//
for (pdtlnode = DtlGetFirstNode( pdtllistPorts ); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { TCHAR szBuf[ MAX_DEVICE_NAME + MAX_DEVICETYPE_NAME + 10 + 1 ]; PBPORT* ppbport;
ppbport = (PBPORT* )DtlGetData( pdtlnode );
// Skip modems (COM ports) and unconfigured ports, since they do not
// follow the same port name formatting rules as other ports.
//
if (!ppbport->pszDevice || ppbport->pbdevicetype == PBDT_Modem) { continue; }
lstrcpy( szBuf, ppbport->pszDevice ); lstrcat( szBuf, ppbport->pszPort );
if (lstrcmp( szBuf, pszPort ) == 0) { return ppbport; } }
return NULL; }
PBPORT* PpbportFromNT4PortandDevice( IN DTLLIST* pdtllistPorts, IN TCHAR* pszPort, IN TCHAR* pszDevice ) // This function is called when we couldn't
// find a port that matches the one in the
// phonebook. This will take care of the case
// where the port is pre-nt5 type of port. Since
// the portnames have changed in nt5 for isdn
// and vpn, this routine will try to find a
// port with the same type.
{ PBPORT *ppbport; PBPORT *ppbportRet = NULL; DTLNODE *pdtlnode; TCHAR szPort[MAX_PORT_NAME+1];
if(NULL == pszPort) { return NULL; }
ZeroMemory(szPort, sizeof(szPort));
lstrcpyn(szPort, pszPort, MAX_PORT_NAME);
szPort[lstrlen(TEXT("VPN"))] = TEXT('\0');
if(0 == lstrcmp(szPort, TEXT("VPN"))) { for (pdtlnode = DtlGetFirstNode( pdtllistPorts ); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { ppbport = (PBPORT *) DtlGetData(pdtlnode);
if(PBDT_Vpn == ppbport->pbdevicetype) { ppbportRet = ppbport; break; } }
return ppbportRet; }
return NULL; }
PBPORT* PpbportFromNullModem( IN DTLLIST* pdtllistPorts, IN TCHAR* pszPort, IN TCHAR* pszDevice )
//
// pmay: 226594
//
// Added this function because sometimes we just need to
// match a given port to a null modem
//
// Will attempt to match the ports, but returns any
// NULL modem it finds if it can't match ports.
//
{ DTLNODE* pdtlnode; PBPORT * pRet = NULL;
for (pdtlnode = DtlGetFirstNode( pdtllistPorts ); pdtlnode; pdtlnode = DtlGetNextNode( pdtlnode )) { PBPORT* ppbport = (PBPORT* )DtlGetData( pdtlnode );
if ((ppbport->dwFlags & PBP_F_NullModem) && (pRet == NULL)) { pRet = ppbport; }
if ((ppbport->pszPort) && (pszPort) && (lstrcmpi( ppbport->pszPort, pszPort ) == 0) ) { pRet = ppbport; break; } }
return pRet; }
BOOL PbportTypeMatchesEntryType( IN PBPORT * pPort, IN PBENTRY* pEntry)
// Returns whether the given port has a type that's compatible
// with the type of the given entry.
{ if (!pPort || !pEntry) { return TRUE; }
if ( ( pEntry->dwType == RASET_Phone ) ) { if ( ( pPort->pbdevicetype == PBDT_Null ) || ( pPort->pbdevicetype == PBDT_Parallel ) || ( pPort->pbdevicetype == PBDT_Irda ) || ( pPort->dwFlags & PBP_F_NullModem ) || ( pPort->pbdevicetype == PBDT_Vpn ) || ( pPort->pbdevicetype == PBDT_PPPoE ) ) { return FALSE; } }
return TRUE; }
BOOL SetDefaultModemSettings( IN PBLINK* pLink )
// Set the MXS modem settings for link 'pLink' to the defaults.
//
// Returns true if something changed, false otherwise.
//
{ BOOL fChange;
fChange = FALSE;
if (pLink->fHwFlow != pLink->pbport.fHwFlowDefault) { fChange = TRUE; pLink->fHwFlow = pLink->pbport.fHwFlowDefault; }
if (pLink->fEc != pLink->pbport.fEcDefault) { fChange = TRUE; pLink->fEc = pLink->pbport.fEcDefault; }
if (pLink->fEcc != pLink->pbport.fEccDefault) { fChange = TRUE; pLink->fEcc = pLink->pbport.fEccDefault; }
if (pLink->fSpeaker != pLink->pbport.fSpeakerDefault) { fChange = TRUE; pLink->fSpeaker = pLink->pbport.fSpeakerDefault; }
if (pLink->dwBps != pLink->pbport.dwBpsDefault) { fChange = TRUE; pLink->dwBps = pLink->pbport.dwBpsDefault; }
// For whistler bug 402522 gangz
// Add preferred modem protocol
// pmay: 228565
// Add the default modem protocol
if (pLink->dwModemProtocol != pLink->pbport.dwModemProtDefault) { fChange = TRUE; pLink->dwModemProtocol = pLink->pbport.dwModemProtDefault; }
TRACE2( "SetDefaultModemSettings(bps=%d)=%d", pLink->dwBps, fChange ); return fChange; }
BOOL ValidateAreaCode( IN OUT TCHAR* pszAreaCode )
// Checks that area code consists of decimal digits only. If the area
// code is all white characters it is reduced to empty string. Returns
// true if 'pszAreaCode' is a valid area code, false if not.
//
{ if (IsAllWhite( pszAreaCode )) { *pszAreaCode = TEXT('\0'); return TRUE; }
if (lstrlen( pszAreaCode ) > RAS_MaxAreaCode) { return FALSE; }
while (*pszAreaCode != TEXT('\0')) { if (*pszAreaCode < TEXT('0') || *pszAreaCode > TEXT('9')) { return FALSE; }
++pszAreaCode; }
return TRUE; }
BOOL ValidateEntryName( IN LPCTSTR pszEntry )
// Returns true if 'pszEntry' is a valid phonebook entry name, false if
// not.
//
{ INT nLen = lstrlen( pszEntry );
if (nLen <= 0 || nLen > RAS_MaxEntryName || IsAllWhite( pszEntry ) || pszEntry[ 0 ] == TEXT('.')) { return FALSE; }
return TRUE; }
|