Ignore:
Timestamp:
Dec 1, 2007 8:59:25 AM (16 years ago)
Author:
bennylp
Message:

Ticket #421: initial IPv6 support: UDP transport

File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/trunk/pjsip/src/pjsua-lib/pjsua_core.c

    r1571 r1602  
    11831183 
    11841184/* 
     1185 * Tools to get address string. 
     1186 */ 
     1187static const char *addr_string(const pj_sockaddr_t *addr) 
     1188{ 
     1189    static char str[128]; 
     1190    str[0] = '\0'; 
     1191    pj_inet_ntop(((const pj_sockaddr*)addr)->addr.sa_family,  
     1192                 pj_sockaddr_get_addr(addr), 
     1193                 str, sizeof(str)); 
     1194    return str; 
     1195} 
     1196 
     1197/* 
    11851198 * Create and initialize SIP socket (and possibly resolve public 
    11861199 * address via STUN, depending on config). 
    11871200 */ 
    1188 static pj_status_t create_sip_udp_sock(pj_in_addr bound_addr, 
     1201static pj_status_t create_sip_udp_sock(int af, 
     1202                                       const pj_str_t *bind_param, 
    11891203                                       int port, 
    11901204                                       pj_sock_t *p_sock, 
    1191                                        pj_sockaddr_in *p_pub_addr) 
    1192 { 
    1193     char ip_addr[32]; 
     1205                                       pj_sockaddr *p_pub_addr) 
     1206{ 
     1207    char stun_ip_addr[PJ_INET6_ADDRSTRLEN]; 
    11941208    pj_str_t stun_srv; 
    11951209    pj_sock_t sock; 
     1210    pj_sockaddr bind_addr; 
    11961211    pj_status_t status; 
    11971212 
     
    12031218    } 
    12041219 
    1205     status = pj_sock_socket(pj_AF_INET(), pj_SOCK_DGRAM(), 0, &sock); 
     1220    /* Initialize bound address */ 
     1221    if (bind_param->slen) { 
     1222        status = pj_sockaddr_init(af, &bind_addr, bind_param,  
     1223                                  (pj_uint16_t)port); 
     1224        if (status != PJ_SUCCESS) { 
     1225            pjsua_perror(THIS_FILE,  
     1226                         "Unable to resolve transport bound address",  
     1227                         status); 
     1228            return status; 
     1229        } 
     1230    } else { 
     1231        pj_sockaddr_init(af, &bind_addr, NULL, (pj_uint16_t)port); 
     1232    } 
     1233 
     1234    status = pj_sock_socket(af, pj_SOCK_DGRAM(), 0, &sock); 
    12061235    if (status != PJ_SUCCESS) { 
    12071236        pjsua_perror(THIS_FILE, "socket() error", status); 
     
    12091238    } 
    12101239 
    1211     status = pj_sock_bind_in(sock, pj_ntohl(bound_addr.s_addr),  
    1212                              (pj_uint16_t)port); 
     1240    status = pj_sock_bind(sock, &bind_addr, sizeof(bind_addr)); 
    12131241    if (status != PJ_SUCCESS) { 
    12141242        pjsua_perror(THIS_FILE, "bind() error", status); 
     
    12191247    /* If port is zero, get the bound port */ 
    12201248    if (port == 0) { 
    1221         pj_sockaddr_in bound_addr; 
     1249        pj_sockaddr bound_addr; 
    12221250        int namelen = sizeof(bound_addr); 
    12231251        status = pj_sock_getsockname(sock, &bound_addr, &namelen); 
     
    12281256        } 
    12291257 
    1230         port = pj_ntohs(bound_addr.sin_port); 
     1258        port = pj_sockaddr_get_port(&bound_addr); 
    12311259    } 
    12321260 
    12331261    if (pjsua_var.stun_srv.addr.sa_family != 0) { 
    1234         pj_ansi_strcpy(ip_addr,pj_inet_ntoa(pjsua_var.stun_srv.ipv4.sin_addr)); 
    1235         stun_srv = pj_str(ip_addr); 
     1262        pj_ansi_strcpy(stun_ip_addr,pj_inet_ntoa(pjsua_var.stun_srv.ipv4.sin_addr)); 
     1263        stun_srv = pj_str(stun_ip_addr); 
    12361264    } else { 
    12371265        stun_srv.slen = 0; 
     
    12411269     * the name of local host. 
    12421270     */ 
    1243     if (p_pub_addr->sin_addr.s_addr != 0) { 
     1271    if (pj_sockaddr_has_addr(p_pub_addr)) { 
    12441272        /* 
    12451273         * Public address is already specified, no need to resolve the  
    12461274         * address, only set the port. 
    12471275         */ 
    1248         if (p_pub_addr->sin_port == 0) 
    1249             p_pub_addr->sin_port = pj_htons((pj_uint16_t)port); 
     1276        if (pj_sockaddr_get_port(p_pub_addr) == 0) 
     1277            pj_sockaddr_set_port(p_pub_addr, (pj_uint16_t)port); 
    12501278 
    12511279    } else if (stun_srv.slen) { 
     
    12531281         * STUN is specified, resolve the address with STUN. 
    12541282         */ 
     1283        if (af != pj_AF_INET()) { 
     1284            pjsua_perror(THIS_FILE, "Cannot use STUN", PJ_EAFNOTSUP); 
     1285            pj_sock_close(sock); 
     1286            return PJ_EAFNOTSUP; 
     1287        } 
     1288 
    12551289        status = pjstun_get_mapped_addr(&pjsua_var.cp.factory, 1, &sock, 
    12561290                                         &stun_srv, pj_ntohs(pjsua_var.stun_srv.ipv4.sin_port), 
    12571291                                         &stun_srv, pj_ntohs(pjsua_var.stun_srv.ipv4.sin_port), 
    1258                                          p_pub_addr); 
     1292                                         &p_pub_addr->ipv4); 
    12591293        if (status != PJ_SUCCESS) { 
    12601294            pjsua_perror(THIS_FILE, "Error contacting STUN server", status); 
     
    12641298 
    12651299    } else { 
    1266  
    1267         pj_bzero(p_pub_addr, sizeof(pj_sockaddr_in)); 
    1268  
    1269         status = pj_gethostip(&p_pub_addr->sin_addr); 
     1300        pj_bzero(p_pub_addr, sizeof(pj_sockaddr)); 
     1301 
     1302        status = pj_gethostip(af, p_pub_addr); 
    12701303        if (status != PJ_SUCCESS) { 
    12711304            pjsua_perror(THIS_FILE, "Unable to get local host IP", status); 
     
    12741307        } 
    12751308 
    1276         p_pub_addr->sin_family = pj_AF_INET(); 
    1277         p_pub_addr->sin_port = pj_htons((pj_uint16_t)port); 
     1309        p_pub_addr->addr.sa_family = (pj_uint16_t)af; 
     1310        pj_sockaddr_set_port(p_pub_addr, (pj_uint16_t)port); 
    12781311    } 
    12791312 
     
    12811314 
    12821315    PJ_LOG(4,(THIS_FILE, "SIP UDP socket reachable at %s:%d", 
    1283               pj_inet_ntoa(p_pub_addr->sin_addr), 
    1284               (int)pj_ntohs(p_pub_addr->sin_port))); 
     1316              addr_string(p_pub_addr), 
     1317              (int)pj_sockaddr_get_port(p_pub_addr))); 
    12851318 
    12861319    return PJ_SUCCESS; 
     
    13141347 
    13151348    /* Create the transport */ 
    1316     if (type == PJSIP_TRANSPORT_UDP) { 
     1349    if (type & PJSIP_TRANSPORT_UDP) { 
    13171350        /* 
    1318          * Create UDP transport. 
     1351         * Create UDP transport (IPv4 or IPv6). 
    13191352         */ 
    13201353        pjsua_transport_config config; 
     1354        char hostbuf[PJ_INET6_ADDRSTRLEN]; 
    13211355        pj_sock_t sock = PJ_INVALID_SOCKET; 
    1322         pj_sockaddr_in bound_addr; 
    1323         pj_sockaddr_in pub_addr; 
     1356        pj_sockaddr pub_addr; 
    13241357        pjsip_host_port addr_name; 
    13251358 
     
    13301363        } 
    13311364 
    1332         /* Initialize bound address, if any */ 
    1333         bound_addr.sin_addr.s_addr = PJ_INADDR_ANY; 
    1334         if (cfg->bound_addr.slen) { 
    1335             status = pj_sockaddr_in_set_str_addr(&bound_addr,&cfg->bound_addr); 
    1336             if (status != PJ_SUCCESS) { 
    1337                 pjsua_perror(THIS_FILE,  
    1338                              "Unable to resolve transport bound address",  
    1339                              status); 
    1340                 goto on_return; 
    1341             } 
    1342         } 
    1343  
    13441365        /* Initialize the public address from the config, if any */ 
    1345         pj_sockaddr_in_init(&pub_addr, NULL, (pj_uint16_t)cfg->port); 
     1366        pj_sockaddr_init(pjsip_transport_type_get_af(type), &pub_addr,  
     1367                         NULL, (pj_uint16_t)cfg->port); 
    13461368        if (cfg->public_addr.slen) { 
    1347             status = pj_sockaddr_in_set_str_addr(&pub_addr, &cfg->public_addr); 
     1369            status = pj_sockaddr_set_str_addr(pjsip_transport_type_get_af(type), 
     1370                                              &pub_addr, &cfg->public_addr); 
    13481371            if (status != PJ_SUCCESS) { 
    13491372                pjsua_perror(THIS_FILE,  
     
    13571380         * (only when public address is not specified). 
    13581381         */ 
    1359         status = create_sip_udp_sock(bound_addr.sin_addr, cfg->port,  
     1382        status = create_sip_udp_sock(pjsip_transport_type_get_af(type), 
     1383                                     &cfg->bound_addr, cfg->port, 
    13601384                                     &sock, &pub_addr); 
    13611385        if (status != PJ_SUCCESS) 
    13621386            goto on_return; 
    13631387 
    1364         addr_name.host = pj_str(pj_inet_ntoa(pub_addr.sin_addr)); 
    1365         addr_name.port = pj_ntohs(pub_addr.sin_port); 
     1388        pj_ansi_strcpy(hostbuf, addr_string(&pub_addr)); 
     1389        addr_name.host = pj_str(hostbuf); 
     1390        addr_name.port = pj_sockaddr_get_port(&pub_addr); 
    13661391 
    13671392        /* Create UDP transport */ 
    1368         status = pjsip_udp_transport_attach( pjsua_var.endpt, sock, 
    1369                                              &addr_name, 1,  
    1370                                              &tp); 
     1393        status = pjsip_udp_transport_attach2(pjsua_var.endpt, type, sock, 
     1394                                             &addr_name, 1, &tp); 
    13711395        if (status != PJ_SUCCESS) { 
    13721396            pjsua_perror(THIS_FILE, "Error creating SIP UDP transport",  
Note: See TracChangeset for help on using the changeset viewer.