2

我正在创建一个 BSD 套接字,socket然后尝试listen使用它。当防火墙处于活动状态时,调用 会listen导致应用程序防火墙对话框出现,但它消失得太快,用户无法与之交互。我发现调用 to 的任何延迟listen,例如在调试器中添加断点或调用 to sleep,在调用之后socket都会导致对话框出现并保持足够长的时间让用户与之交互。如果在用户可以选择任何内容之前对话框消失了,防火墙会拒绝该应用程序的所有后续传入请求。

有谁知道是什么导致对话框消失,以及是否有比调用更合适的方法来防止它sleep

如果有人想尝试重现此问题,我将在下面附上导致此行为的代码。如果waitForUserInput为真,对话框将出现并一直持续到套接字关闭。如果不是真的,对话会在一瞬间消失。如果您在测试的行上添加断点,waitForUserInput即使该变量是 .它也会显示 5 秒的对话框NO。在所有这些情况下,调用listen不会返回错误。我正在使用 OS X 10.7.4 和 Xcode 4.2 。

#import <sys/socket.h>
#import <netdb.h>

static void firewallDialog(BOOL waitForUserInput){
    struct addrinfo *res, *p, host;

    memset(&host, 0, sizeof host);
    host.ai_family = AF_UNSPEC; // no preference for IP4/6
    host.ai_socktype = SOCK_STREAM; // TCP
    host.ai_flags = AI_PASSIVE; // local IP address

    if(-1 != (getaddrinfo(NULL,"1234",&host,&res))){
        int sock = -1;

        for(p = res; p != NULL; sock = -1, p = p->ai_next) {
            // make a socket
            if(-1 == (sock = socket(p->ai_family, p->ai_socktype, p->ai_protocol))){
                continue;
            }

            if(p->ai_family == PF_INET6){
                ((struct sockaddr_in6*)p->ai_addr)->sin6_addr = in6addr_any;
            }
            if(-1 == bind(sock, p->ai_family == PF_INET ? INADDR_ANY : p->ai_addr, p->ai_addrlen)){
                close(sock);
                continue;
            }

            break;
        }

        freeaddrinfo(res);

        if(-1 != sock){
            if(waitForUserInput){ sleep(1); }

            if(-1 == listen(sock, 20)){
                close(sock);
            }else{
                NSLog(@"Call to listen was successful");
                sleep(5);
                close(sock);
            }
        }
    }
}
4

0 回答 0