windows-nt/Source/XPSP1/NT/net/homenet/beacon/server/cwanpppconnectionservice.cpp
2020-09-26 16:20:57 +08:00

268 lines
8 KiB
C++

#include "pch.h"
#pragma hdrstop
#include "CWANPPPConnectionService.h"
#include "ndispnp.h"
#include "ras.h"
#include "rasuip.h"
#include "util.h"
#include "raserror.h"
#include "rasdlg.h"
CWANPPPConnectionService::CWANPPPConnectionService()
{
m_dwLastConnectionError = 0;
}
HRESULT CWANPPPConnectionService::get_LastConnectionError(BSTR *pLastConnectionError)
{
HRESULT hr = S_OK;
LPOLESTR pszError = NULL;
switch(m_dwLastConnectionError)
{
case 0:
pszError = L"ERROR_NONE";
break;
case ERROR_PPP_TIMEOUT:
case ERROR_REQUEST_TIMEOUT:
pszError = L"ERROR_ISP_TIME_OUT";
break;
// case : // no mapping
// pszError = L"ERROR_COMMAND_ABORTED";
// break;
// case : // no mapping
// pszError = L"ERROR_NOT_ENABLED_FOR_INTERNET";
// break;
case ERROR_BAD_PHONE_NUMBER:
pszError = L"ERROR_BAD_PHONE_NUMBER";
break;
case ERROR_USER_DISCONNECTION:
pszError = L"ERROR_USER_DISCONNECT";
break;
case ERROR_REMOTE_DISCONNECTION:
pszError = L"ERROR_ISP_DISCONNECT";
break;
// case : // no mapping
// pszError = L"ERROR_IDLE_DISCONNECT";
// break;
// case : // no mapping
// pszError = L"ERROR_FORCED_DISCONNECT";
// break;
case ERROR_SERVER_OUT_OF_RESOURCES:
pszError = L"ERROR_SERVER_OUT_OF_RESOURCES";
break;
case ERROR_RESTRICTED_LOGON_HOURS:
pszError = L"ERROR_RESTRICTED_LOGON_HOURS";
break;
case ERROR_ACCT_DISABLED:
pszError = L"ERROR_ACCOUNT_DISABLED";
break;
case ERROR_ACCT_EXPIRED:
pszError = L"ERROR_ACCOUNT_EXPIRED";
break;
case ERROR_PASSWD_EXPIRED:
pszError = L"ERROR_PASSWORD_EXPIRED";
break;
case ERROR_AUTHENTICATION_FAILURE:
pszError = L"ERROR_AUTHENTICATION_FAILURE";
break;
case ERROR_NO_DIALTONE:
pszError = L"ERROR_NO_DIALTONE";
break;
case ERROR_NO_CARRIER:
pszError = L"ERROR_NO_CARRIER";
break;
case ERROR_NO_ANSWER:
pszError = L"ERROR_NO_ANSWER";
break;
case ERROR_LINE_BUSY:
pszError = L"ERROR_LINE_BUSY";
break;
case ERROR_UNSUPPORTED_BPS:
pszError = L"ERROR_UNSUPPORTED_BITSPERSECOND";
break;
case ERROR_TOO_MANY_LINE_ERRORS:
pszError = L"ERROR_TOO_MANY_LINE_ERRORS";
break;
case ERROR_IP_CONFIGURATION:
pszError = L"ERROR_IP_CONFIGURATION";
break;
default:
pszError = L"ERROR_UNKNOWN";
break;
}
*pLastConnectionError = SysAllocString(pszError);
if(NULL == *pLastConnectionError)
{
hr = E_OUTOFMEMORY;
}
return hr;
}
HRESULT CWANPPPConnectionService::RequestConnection(void)
{
HRESULT hr = S_OK;
m_dwLastConnectionError = 0;
hr = ControlEnabled();
if(SUCCEEDED(hr))
{
DWORD dwErr;
RASSHARECONN rsc;
dwErr = RasQuerySharedConnection(&rsc);
if(NO_ERROR == dwErr)
{
RASCREDENTIALSW rc;
rc.dwSize = sizeof(rc);
rc.dwMask = RASCM_UserName | RASCM_Password | RASCM_Domain | RASCM_DefaultCreds;
dwErr = RasGetCredentials(rsc.name.szPhonebookPath, rsc.name.szEntryName, &rc);
if (NO_ERROR == dwErr)
{
RASDIALEXTENSIONS rde;
RASDIALPARAMSW rdp;
ZeroMemory(&rde, sizeof(rde));
rde.dwSize = sizeof(rde);
rde.dwfOptions = RDEOPT_NoUser;
ZeroMemory(&rdp, sizeof(rdp));
rdp.dwSize = sizeof(rdp);
lstrcpyW(rdp.szEntryName, rsc.name.szEntryName);
lstrcpyW(rdp.szUserName, rc.szUserName);
lstrcpyW(rdp.szDomain, rc.szDomain);
lstrcpyW(rdp.szPassword, rc.szPassword);
ZeroMemory(&rc, sizeof(rc)); // zero crendentials
HRASCONN hrasconn = NULL;
dwErr = RasDial(&rde, rsc.name.szPhonebookPath, &rdp, 0, NULL, &hrasconn);
ZeroMemory(&rdp, sizeof(rdp)); // zero credentials
if (E_NOTIMPL == dwErr)
{
//
// This is possibly a Connection Manager connection since it's returning E_NOTIMPL,
// we should check the phonebook entry for the type and then call the RasDialDlg
// with the RASDDFLAG_NoPrompt flag.
//
RASDIALDLG info;
BOOL fRetVal = FALSE;
RASENTRY re;
DWORD dwRasEntrySize;
DWORD dwIgnore;
HINSTANCE hRasDlgDll = NULL;
FARPROC lpfnRasDialDlg = NULL;
typedef BOOL (*lpfnRasDialDlgFunc)(LPWSTR, LPWSTR, LPWSTR, LPRASDIALDLG);
ZeroMemory(&info, sizeof(info));
info.dwSize = sizeof(info);
ZeroMemory(&re, sizeof(re));
dwRasEntrySize = sizeof(re);
re.dwSize = dwRasEntrySize;
dwErr = RasGetEntryProperties(
rsc.name.szPhonebookPath,
rsc.name.szEntryName,
&re,
&dwRasEntrySize,
NULL,
&dwIgnore);
if (ERROR_SUCCESS == dwErr)
{
dwErr = ERROR_NOT_SUPPORTED;
//
// Check if this is a Connection Manager entry
//
if (RASET_Internet == re.dwType)
{
//
// Prevent the DialerDialog
//
info.dwFlags |= RASDDFLAG_NoPrompt;
hRasDlgDll = LoadLibrary(L"RASDLG.DLL");
if (hRasDlgDll)
{
lpfnRasDialDlgFunc lpfnRasDialDlg = (lpfnRasDialDlgFunc)GetProcAddress(hRasDlgDll, "RasDialDlgW");
if (lpfnRasDialDlg)
{
fRetVal = (BOOL)(lpfnRasDialDlg)(rsc.name.szPhonebookPath, rsc.name.szEntryName, NULL, &info );
if (fRetVal)
{
dwErr = NO_ERROR;
}
}
FreeLibrary(hRasDlgDll);
hRasDlgDll = NULL;
}
}
}
}
m_dwLastConnectionError = dwErr;
if(NO_ERROR != dwErr)
{
hr = E_FAIL;
if(NULL != hrasconn)
{
RasHangUp(hrasconn);
}
}
}
else
{
hr = E_FAIL;
}
}
else
{
hr = E_FAIL;
}
if(FAILED(hr))
{
SetUPnPError(DCP_ERROR_CONNECTIONSETUPFAILED);
}
}
else
{
SetUPnPError(DCP_CUSTOM_ERROR_ACCESSDENIED);
}
return hr;
}
HRESULT CWANPPPConnectionService::ForceTermination(void)
{
HRESULT hr = S_OK;
hr = ControlEnabled();
if(SUCCEEDED(hr))
{
INetConnection* pNetConnection;
hr = m_pHomenetConnection->GetINetConnection(&pNetConnection);
if(SUCCEEDED(hr))
{
hr = pNetConnection->Disconnect();
pNetConnection->Release();
}
}
else
{
SetUPnPError(DCP_CUSTOM_ERROR_ACCESSDENIED);
}
return hr;
}