static int datagram_loop_test() { enum { LOOP = 8 }; pjsip_transport *loop; int i, pkt_lost; pj_sockaddr_in addr; pj_status_t status; long ref_cnt; int rtt[LOOP], min_rtt; PJ_LOG(3,(THIS_FILE, "testing datagram loop transport")); /* Test acquire transport. */ status = pjsip_endpt_acquire_transport( endpt, PJSIP_TRANSPORT_LOOP_DGRAM, &addr, sizeof(addr), NULL, &loop); if (status != PJ_SUCCESS) { app_perror(" error: loop transport is not configured", status); return -20; } /* Get initial reference counter */ ref_cnt = pj_atomic_get(loop->ref_cnt); /* Test basic transport attributes */ status = generic_transport_test(loop); if (status != PJ_SUCCESS) return status; /* Basic transport's send/receive loopback test. */ for (i=0; i<LOOP; ++i) { status = transport_send_recv_test(PJSIP_TRANSPORT_LOOP_DGRAM, loop, "sip:[email protected];transport=loop-dgram", &rtt[i]); if (status != 0) return status; } min_rtt = 0xFFFFFFF; for (i=0; i<LOOP; ++i) if (rtt[i] < min_rtt) min_rtt = rtt[i]; report_ival("loop-rtt-usec", min_rtt, "usec", "Best Loopback transport round trip time, in microseconds " "(time from sending request until response is received. " "Tests were performed on local machine only)"); /* Multi-threaded round-trip test. */ status = transport_rt_test(PJSIP_TRANSPORT_LOOP_DGRAM, loop, "sip:[email protected];transport=loop-dgram", &pkt_lost); if (status != 0) return status; if (pkt_lost != 0) { PJ_LOG(3,(THIS_FILE, " error: %d packet(s) was lost", pkt_lost)); return -40; } /* Put delay. */ PJ_LOG(3,(THIS_FILE," setting network delay to 10 ms")); pjsip_loop_set_delay(loop, 10); /* Multi-threaded round-trip test. */ status = transport_rt_test(PJSIP_TRANSPORT_LOOP_DGRAM, loop, "sip:[email protected];transport=loop-dgram", &pkt_lost); if (status != 0) return status; if (pkt_lost != 0) { PJ_LOG(3,(THIS_FILE, " error: %d packet(s) was lost", pkt_lost)); return -50; } /* Restore delay. */ pjsip_loop_set_delay(loop, 0); /* Check reference counter. */ if (pj_atomic_get(loop->ref_cnt) != ref_cnt) { PJ_LOG(3,(THIS_FILE, " error: ref counter is not %d (%d)", ref_cnt, pj_atomic_get(loop->ref_cnt))); return -51; } /* Decrement reference. */ pjsip_transport_dec_ref(loop); return 0; }
/* * UDP transport test. */ int transport_udp_test(void) { enum { SEND_RECV_LOOP = 8 }; pjsip_transport *udp_tp, *tp; pj_sockaddr_in addr, rem_addr; pj_str_t s; pj_status_t status; int rtt[SEND_RECV_LOOP], min_rtt; int i, pkt_lost; pj_sockaddr_in_init(&addr, NULL, TEST_UDP_PORT); /* Start UDP transport. */ status = pjsip_udp_transport_start( endpt, &addr, NULL, 1, &udp_tp); if (status != PJ_SUCCESS) { app_perror(" Error: unable to start UDP transport", status); return -10; } /* UDP transport must have initial reference counter set to 1. */ if (pj_atomic_get(udp_tp->ref_cnt) != 1) return -20; /* Test basic transport attributes */ status = generic_transport_test(udp_tp); if (status != PJ_SUCCESS) return status; /* Test that transport manager is returning the correct * transport. */ pj_sockaddr_in_init(&rem_addr, pj_cstr(&s, "1.1.1.1"), 80); status = pjsip_endpt_acquire_transport(endpt, PJSIP_TRANSPORT_UDP, &rem_addr, sizeof(rem_addr), NULL, &tp); if (status != PJ_SUCCESS) return -50; if (tp != udp_tp) return -60; /* pjsip_endpt_acquire_transport() adds reference, so we need * to decrement it. */ pjsip_transport_dec_ref(tp); /* Check again that reference counter is 1. */ if (pj_atomic_get(udp_tp->ref_cnt) != 1) return -70; /* Basic transport's send/receive loopback test. */ pj_sockaddr_in_init(&rem_addr, pj_cstr(&s, "127.0.0.1"), TEST_UDP_PORT); for (i=0; i<SEND_RECV_LOOP; ++i) { status = transport_send_recv_test(PJSIP_TRANSPORT_UDP, tp, "sip:[email protected]:"TEST_UDP_PORT_STR, &rtt[i]); if (status != 0) return status; } min_rtt = 0xFFFFFFF; for (i=0; i<SEND_RECV_LOOP; ++i) if (rtt[i] < min_rtt) min_rtt = rtt[i]; report_ival("udp-rtt-usec", min_rtt, "usec", "Best UDP transport round trip time, in microseconds " "(time from sending request until response is received. " "Tests were performed on local machine only)"); /* Multi-threaded round-trip test. */ status = transport_rt_test(PJSIP_TRANSPORT_UDP, tp, "sip:[email protected]:"TEST_UDP_PORT_STR, &pkt_lost); if (status != 0) return status; if (pkt_lost != 0) PJ_LOG(3,(THIS_FILE, " note: %d packet(s) was lost", pkt_lost)); /* Check again that reference counter is 1. */ if (pj_atomic_get(udp_tp->ref_cnt) != 1) return -80; /* Destroy this transport. */ pjsip_transport_dec_ref(udp_tp); /* Force destroy this transport. */ status = pjsip_transport_destroy(udp_tp); if (status != PJ_SUCCESS) return -90; /* Flush events. */ PJ_LOG(3,(THIS_FILE, " Flushing events, 1 second...")); flush_events(1000); /* Done */ return 0; }
int transport_tcp_test(void) { enum { SEND_RECV_LOOP = 8 }; pjsip_tpfactory *tpfactory; pjsip_transport *tcp; pj_sockaddr_in rem_addr; pj_status_t status; char url[PJSIP_MAX_URL_SIZE]; int rtt[SEND_RECV_LOOP], min_rtt; int i, pkt_lost; /* Start TCP listener on arbitrary port. */ status = pjsip_tcp_transport_start(endpt, NULL, 1, &tpfactory); if (status != PJ_SUCCESS) { app_perror(" Error: unable to start TCP transport", status); return -10; } /* Get the listener address */ status = pj_sockaddr_in_init(&rem_addr, &tpfactory->addr_name.host, (pj_uint16_t)tpfactory->addr_name.port); if (status != PJ_SUCCESS) { app_perror(" Error: possibly invalid TCP address name", status); return -14; } pj_ansi_sprintf(url, "sip:alice@%s:%d;transport=tcp", pj_inet_ntoa(rem_addr.sin_addr), pj_ntohs(rem_addr.sin_port)); /* Acquire one TCP transport. */ status = pjsip_endpt_acquire_transport(endpt, PJSIP_TRANSPORT_TCP, &rem_addr, sizeof(rem_addr), NULL, &tcp); if (status != PJ_SUCCESS || tcp == NULL) { app_perror(" Error: unable to acquire TCP transport", status); return -17; } /* After pjsip_endpt_acquire_transport, TCP transport must have * reference counter 1. */ if (pj_atomic_get(tcp->ref_cnt) != 1) return -20; /* Test basic transport attributes */ status = generic_transport_test(tcp); if (status != PJ_SUCCESS) return status; /* Check again that reference counter is 1. */ if (pj_atomic_get(tcp->ref_cnt) != 1) return -40; /* Load test */ if (transport_load_test(url) != 0) return -60; /* Basic transport's send/receive loopback test. */ for (i=0; i<SEND_RECV_LOOP; ++i) { status = transport_send_recv_test(PJSIP_TRANSPORT_TCP, tcp, url, &rtt[i]); if (status != 0) { pjsip_transport_dec_ref(tcp); flush_events(500); return -72; } } min_rtt = 0xFFFFFFF; for (i=0; i<SEND_RECV_LOOP; ++i) if (rtt[i] < min_rtt) min_rtt = rtt[i]; report_ival("tcp-rtt-usec", min_rtt, "usec", "Best TCP transport round trip time, in microseconds " "(time from sending request until response is received. " "Tests were performed on local machine only, and after " "TCP socket has been established by previous test)"); /* Multi-threaded round-trip test. */ status = transport_rt_test(PJSIP_TRANSPORT_TCP, tcp, url, &pkt_lost); if (status != 0) { pjsip_transport_dec_ref(tcp); return status; } if (pkt_lost != 0) PJ_LOG(3,(THIS_FILE, " note: %d packet(s) was lost", pkt_lost)); /* Check again that reference counter is still 1. */ if (pj_atomic_get(tcp->ref_cnt) != 1) return -80; /* Destroy this transport. */ pjsip_transport_dec_ref(tcp); /* Force destroy this transport. */ status = pjsip_transport_destroy(tcp); if (status != PJ_SUCCESS) return -90; /* Unregister factory */ status = pjsip_tpmgr_unregister_tpfactory(pjsip_endpt_get_tpmgr(endpt), tpfactory); if (status != PJ_SUCCESS) return -95; /* Flush events. */ PJ_LOG(3,(THIS_FILE, " Flushing events, 1 second...")); flush_events(1000); /* Done */ return 0; }