2009-12-08 217 views
13

我已经开始编写一个使用套接字的ActiveX控件。是否有可能判断WSAStartup是否在进程中被调用?

使用此控件的应用程序可能也可能不会使用套接字。 我的控件可以告诉WSAStartup是否已被调用?

如果没有,请调用它。一个小小的测试表明,多次调用WSAStartup会受到惩罚。 但是,如果请求不同的winsock版本,会发生什么?这会破坏应用程序的其他部分吗?

回答

26

是的,这是可能的。

这是它是如何完成的。

bool WinsockInitialized() 
{ 
    SOCKET s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); 
    if (s == INVALID_SOCKET && WSAGetLastError() == WSANOTINITIALISED){ 
     return false; 
    } 

    closesocket(s) 
    return true; 
} 

int main() 
{ 
    //... 
    if (!WinsockInitialized()) 
     // Init winsock here... 

    // Carry on as normal. 
    // ...   
} 

但这并不是真的有必要这样做。随时调用WSAStartup是相当安全的。通过与WSACleanup()的匹配调用来结束对WSAStartup()的每次成功调用也是安全的。

例如

// socket calls here would be an error, not initialized 
WSAStartup(...) 
// socket calls here OK 

WSAStartup(...) 
// more socket calls OK 

WSACleanup() 
// socket calls OK 

WSACleanup() 

// more socket calls error, not initialized 
+6

如果'socket()'在WinsockInitialized()中成功,请不要忘记调用'closesocket()',否则你有泄漏。 – 2014-05-05 21:42:54

+1

好点!固定的。 – Matt 2015-01-27 18:18:47

+0

随时调用WSAStartup是不安全的。从MSDN:“WSAStartup函数通常会导致协议特定的帮助程序DLL被加载,因此WSAStartup函数不应该从应用程序DLL中的DllMain函数中调用,这可能会导致死锁” – czz 2015-07-07 02:02:55

2
  • 不,不知道WSAStartup()是否已被调用。

  • 是的,WSAStartup()可以在单个进程中多次调用,只要WinSock DLL支持所请求的版本即可。致电WSAStartup()WSACleanup()必须平衡。

  • WinSock初始化是一个协商过程;您有责任验证WSAStartup()返回的信息,以确保它符合您应用的要求。

  • 现有套接字不受后续WSAStartup()调用的影响。

  • 允许使用不同WinSock版本的多个套接字。

查看the WSAStartup() documentation了解更多信息。

+0

除此之外,我发现,只要WSACleanup调用的数量匹配成功地调用WSAStartup调用的次数,然后再调用WSACleanup不会影响到其他套接字调用。当然,你不会多次调用WSACleanup。 – Matt 2009-12-09 03:07:44

相关问题