将虚拟网卡设置为私有共享,个别电脑会出现拒绝访问,但是第二遍执行又能成功,没搞懂原因,我就for循环了三遍测试二三两遍都会成功
//第一个参数位com接口,第二个是网卡名称
HRESULT shareNetPRIVATE(INetSharingManager* pNSM, const char* dstName)
{
INetConnection* pNC = NULL;
INetSharingConfiguration* pNSC = NULL;
IEnumVARIANT* pEV = NULL;
IUnknown* pUnk = NULL;
INetSharingEveryConnectionCollection* pNSECC = NULL;
HRESULT hr = pNSM->get_EnumEveryConnection(&pNSECC);
VARIANT v;
VariantInit(&v);
if (!pNSECC)
{
printf("failed to get EveryConnectionCollection!\r\n");
return NULL;
}
hr = pNSECC->get__NewEnum(&pUnk);
if (pUnk)
{
hr = pUnk->QueryInterface(__uuidof(IEnumVARIANT), (void**)&pEV);
pUnk->Release();
}
printf("\r\n----------------------------------------------------------\r\n");
while (S_OK == pEV->Next(1, &v, NULL))
{
if (V_VT(&v) == VT_UNKNOWN)
{
V_UNKNOWN(&v)->QueryInterface(__uuidof(INetConnection), (void**)&pNC);
if (pNC)
{
NETCON_PROPERTIES* pNP = NULL;
pNC->GetProperties(&pNP);
setlocale(LC_ALL, "chs");
//if (pNP->Status != NCS_CONNECTED) continue;
std::string tmpName = WcharToChar(pNP->pszwName);
hr = pNSM->get_INetSharingConfigurationForINetConnection(pNC, &pNSC);
if (hr != S_OK)
{
printf("***********get_INetSharingConfigurationForINetConnection设置失败\r\n");
}
if (!strcmp(tmpName.c_str(), (char*)dstName))
{
hr = pNSC->DisableSharing();
Sleep(1000);
if (hr != S_OK)
{
printf("***********DisableSharing设置失败\r\n");
}
printf("***********Sleep(1000);\r\n");
//hr = pNSC->EnableSharing(ICSSHARINGTYPE_PRIVATE);//0x80070005 E_ACCESSDENIED
for (int i =0;i<3;i++)
{
//SHARINGCONNECTIONTYPE
hr = pNSC->EnableSharing(ICSSHARINGTYPE_PRIVATE);
if (hr == S_OK)
{
printf("***********ICSSHARINGTYPE_PRIVATE设置成功\r\n");
}
else
{
printf("***********ICSSHARINGTYPE_PRIVATE设置失败:%0x\r\n", hr);
}
Sleep(500);
}
}
pNSC->Release();
}
}
}
return hr;
}
将以太网设置为公有共享,要先设置私有共享不然他没有共享的目标会出现(错误代码是0x80040201,它解析为:"一个事件无法调用任何订阅者." ),与上面代码基本上相似,但是需要拆分开写,因为循环时是有可能先循环到以太网的,这样就会先设置以太网位共有共享。
//第一个参数位com接口,第二个是网卡名称
HRESULT shareNetPUBLIC(INetSharingManager* pNSM, const char* srcName)
{
INetConnection* pNC = NULL;
INetSharingConfiguration* pNSC = NULL;
IEnumVARIANT* pEV = NULL;
IUnknown* pUnk = NULL;
INetSharingEveryConnectionCollection* pNSECC = NULL;
HRESULT hr = pNSM->get_EnumEveryConnection(&pNSECC);
VARIANT v;
VariantInit(&v);
if (!pNSECC)
{
printf("failed to get EveryConnectionCollection!\r\n");
return NULL;
}
hr = pNSECC->get__NewEnum(&pUnk);
if (pUnk)
{
hr = pUnk->QueryInterface(__uuidof(IEnumVARIANT), (void**)&pEV);
pUnk->Release();
}
printf("\r\n----------------------------------------------------------\r\n");
while (S_OK == pEV->Next(1, &v, NULL))
{
if (V_VT(&v) == VT_UNKNOWN)
{
V_UNKNOWN(&v)->QueryInterface(__uuidof(INetConnection), (void**)&pNC);
if (pNC)
{
NETCON_PROPERTIES* pNP = NULL;
pNC->GetProperties(&pNP);
setlocale(LC_ALL, "chs");
//if (pNP->Status != NCS_CONNECTED) continue;
std::string tmpName = WcharToChar(pNP->pszwName);
hr = pNSM->get_INetSharingConfigurationForINetConnection(pNC, &pNSC);
if (hr != S_OK)
{
printf("***********get_INetSharingConfigurationForINetConnection设置失败\r\n");
}
if (!strcmp(tmpName.c_str(), (char*)srcName))
{
hr = pNSC->DisableSharing();
Sleep(1000);
if (hr != S_OK)
{
printf("***********DisableSharing设置失败\r\n");
}
printf("\r\n***********Sleep(1000);\r\n");
hr = pNSC->EnableSharing(ICSSHARINGTYPE_PUBLIC);
if (hr == S_OK)
{
printf("***********ICSSHARINGTYPE_PUBLIC设置成功\r\n");
}
else
{
printf("***********ICSSHARINGTYPE_PUBLIC设置失败:%0xd\r\n", hr);
}
}
pNSC->Release();
}
}
}
return hr;
}
保护进程,并创建com类,调用上面两个函数 pszShare:用来判断是否共享网络
void Ethernet_Share_OpenVPN(char* pszShare)
{
if (strcmp(pszShare, "Share") == 0)
{
CoInitialize(NULL);
// 保护线程安全
CoInitializeSecurity(NULL, -1, NULL, NULL, RPC_C_AUTHN_LEVEL_PKT, RPC_C_IMP_LEVEL_IMPERSONATE, NULL, EOAC_NONE, NULL);
//创建一个Com对象
INetSharingManager* pNSM = NULL;
HRESULT hr = ::CoCreateInstance(__uuidof(NetSharingManager), NULL, CLSCTX_ALL, __uuidof(INetSharingManager), (void**)&pNSM);
if (!pNSM)
{
printf("创建netshareingmanager对象失败\r\n");
}
else
{
printf("\r\n本地网卡:%s \r\n openVPN虚拟网卡:%s\r\n", g_strENameValue, g_strOVNameValue);
shareNetPRIVATE(pNSM, g_strOVNameValue);
shareNetPUBLIC(pNSM, g_strENameValue);
AutoIP();//自动获取IP
}
pNSM->Release();
}
else if (strcmp(pszShare, "NoShare") == 0)
{
printf("不设置共享网络!\r\n");
return;
}
}