'SIGALRM'에 해당되는 글 1건

  1. 2012.02.23 SOCKET CONNECT TIMEOUT SIGALRM 이용

반응형


/******************************************************************************/

int SocketConnectTimeout(char *sIpAddr, int nPort, int nConnectTimeout)
{
    int                 nRet;
    int                 nSockFd;
    struct sockaddr_in  serv_addr;

    int    nSockOpt=1;
    int    nReUseOpt=1;
    struct linger   lin;

    nSockFd = socket(AF_INET, SOCK_STREAM, 0);
    if( nSockFd < 0 ) {

        fprintf(stderr, "ERROR_SOCKET_FAIL\n");

        return -1;
    }

    memset((char *) &serv_addr, 0x00, sizeof(serv_addr));
    serv_addr.sin_family = AF_INET;
    serv_addr.sin_addr.s_addr = inet_addr(sIpAddr);  /*** 숫자와 점으로 구성된 IP주소를 unsigned long 변수에 집어 넣어 준다 ***/
    serv_addr.sin_port = htons(nPort);  /*** "Host to Network Short"  ***/

    /*** 타임아웃알림시그널 - 아래의 4라인을 signal(SIGALRM,alrm_handler); 로 표현가능 **/
    alrm_action.sa_handler = alrm_handler;
    alrm_action.sa_flags = 0;   /* don't restart */
    sigemptyset(&alrm_action.sa_mask);
    sigaction(SIGALRM, &alrm_action, NULL);

    alarm(nConnectTimeout);

    nRet = connect(nSockFd, (struct sockaddr *) &serv_addr, sizeof(serv_addr));
    if( nRet < 0 ) {

        fprintf(stderr, "ERROR_CONNECT_FAIL\n");

        alarm(0);
        close(nSockFd);

        return -1;
    }

    alarm(0);

    /*** 이부분에서 SOCKET옵션을 설정해줄수 있다 ***/
    if (setsockopt(nSockFd, SOL_SOCKET, SO_KEEPALIVE, (char*)&nSockOpt, sizeof(nSockOpt)) < 0) {
        fprintf(stderr,"ERROR_setsockopt(SO_KEEPALIVE)_FAIL errno[%d][%s]\n", errno, strerror(errno));
        return -1;
    }

    if (setsockopt(nSockFd, SOL_SOCKET, SO_REUSEADDR, (char*)&nReUseOpt, sizeof(nReUseOpt)) < 0) {
        fprintf(stderr,"ERROR_setsockopt(SO_REUSEADDR)_FAIL errno[%d][%s]\n", errno, strerror(errno));
        return -1;
    }

    lin.l_onoff  = 1;
    lin.l_linger = 0;

    if (setsockopt(nSockFd, SOL_SOCKET, SO_LINGER, (char*)&lin, sizeof(lin)) < 0) {
        fprintf(stderr,"ERROR_setsockopt(SO_LINGER)_FAIL errno[%d][%s]\n", errno, strerror(errno));
        return -1;
    }

    return nSockFd;
}

/******************************************************************************/

void alrm_handler(int signo)
{
    fprintf(stderr, "socket_connect_alrm_handler occur...\n");

    return;
}

/******************************************************************************/


 

반응형
Posted by 공간사랑
,