⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 nta.c

📁 this is simple sip stack.
💻 C
📖 第 1 页 / 共 5 页
字号:
    m = tport_set_params(tport, TAG_NEXT(tags));  }  if (n == 0 || m == -1)    return m;  n += m;  if (aliases != NONE) {    sip_contact_t const *m, *m_next;    m = agent->sa_aliases;    agent->sa_aliases = sip_contact_dup(home, aliases);    for (; m; m = m_next) {	/* Free old aliases */      m_next = m->m_next;      su_free(home, (void *)m);    }  }  if (proxy != NONE) {    url_t *dp = url_hdup(home, proxy->us_url);    url_sanitize(dp);    if (dp == NULL || dp->url_type == url_sip || dp->url_type == url_sips) {      if (agent->sa_default_proxy)	su_free(home, agent->sa_default_proxy);      agent->sa_default_proxy = dp;    }    else      n = -1;  }  if (algorithm != NONE)    agent->sa_algorithm = su_strdup(home, algorithm);  if (str0cmp(sigcomp, agent->sa_sigcomp_options)) {    int msg_avlist_d(su_home_t *home, char **ss, msg_param_t const **pparams);    char const * const *l = NULL;    char *s = su_strdup(home, sigcomp);    char *s1 = su_strdup(home, s), *s2 = s1;    if (s && s2 && msg_avlist_d(home, &s2, &l) == 0 && *s2 == '\0') {      su_free(home, (void *)agent->sa_sigcomp_options);      su_free(home, (void *)agent->sa_sigcomp_option_list);      agent->sa_sigcomp_options = s;      agent->sa_sigcomp_option_free = s1;      agent->sa_sigcomp_option_list = l;    } else {      su_free(home, s);      su_free(home, s1);      su_free(home, (void *)l);      n = -1;    }  }  if (maxsize == 0) maxsize = 2 * 1024 * 1024;  if (maxsize > NTA_TIME_MAX) maxsize = NTA_TIME_MAX;  agent->sa_maxsize = maxsize;  if (udp_mtu == 0) udp_mtu = 1300;  if (udp_mtu > 65535) udp_mtu = 65535;  if (agent->sa_udp_mtu != udp_mtu)    agent_set_udp_params(agent, udp_mtu);  if (sip_t1 == 0) sip_t1 = NTA_SIP_T1;  if (sip_t1 > NTA_TIME_MAX) sip_t1 = NTA_TIME_MAX;  agent->sa_t1 = sip_t1;  if (sip_t2 == 0) sip_t2 = NTA_SIP_T2;  if (sip_t2 > NTA_TIME_MAX) sip_t2 = NTA_TIME_MAX;  agent->sa_t2 = sip_t2;  if (sip_t4 == 0) sip_t4 = NTA_SIP_T4;  if (sip_t4 > NTA_TIME_MAX) sip_t4 = NTA_TIME_MAX;  if (agent->sa_t4 != sip_t4) {    incoming_queue_adjust(agent, agent->sa_in.inv_confirmed, sip_t4);    outgoing_queue_adjust(agent, agent->sa_out.completed, sip_t4);  }  agent->sa_t4 = sip_t4;  if (sip_t1x64 == 0) sip_t1x64 = NTA_SIP_T1 * 64;  if (sip_t1x64 > NTA_TIME_MAX) sip_t1x64 = NTA_TIME_MAX;  if (agent->sa_t1x64 != sip_t1x64) {    incoming_queue_adjust(agent, agent->sa_in.preliminary, sip_t1x64);    incoming_queue_adjust(agent, agent->sa_in.completed, sip_t1x64);    incoming_queue_adjust(agent, agent->sa_in.inv_completed, sip_t1x64);    outgoing_queue_adjust(agent, agent->sa_out.trying, sip_t1x64);    outgoing_queue_adjust(agent, agent->sa_out.inv_calling, sip_t1x64);  }  agent->sa_t1x64 = sip_t1x64;  agent->sa_blacklist = blacklist;  if (progress == 0)    progress = 60 * 1000;  agent->sa_progress = progress;  agent->sa_bad_req_mask = bad_req_mask;  agent->sa_bad_resp_mask = bad_resp_mask;  agent->sa_is_a_uas = ua != 0;  agent->sa_is_stateless = stateless != 0;  agent->sa_drop_prob = drop_prob < 1000 ? drop_prob : 1000;  agent->sa_user_via = user_via != 0;  agent->sa_extra_100 = extra_100 != 0;  agent->sa_pass_100 = pass_100 != 0;  agent->sa_timeout_408 = timeout_408 != 0;  agent->sa_pass_408 = pass_408 != 0;  agent->sa_merge_482 = merge_482 != 0;  agent->sa_cancel_2543 = cancel_2543 != 0;  agent->sa_cancel_487 = cancel_487 != 0;  agent->sa_invite_100rel = invite_100rel != 0;  agent->sa_timestamp = use_timestamp != 0;  agent->sa_use_naptr = use_naptr != 0;  agent->sa_use_srv = use_srv != 0;  agent->sa_smime = smime;  agent->sa_flags = flags & MSG_FLG_USERMASK;  agent->sa_rport = rport != 0;  agent->sa_server_rport = server_rport != 0;  agent->sa_tcp_rport = tcp_rport != 0;  agent->sa_preload = preload;  agent->sa_tport_threadpool = threadpool;  return n;}static void agent_set_udp_params(nta_agent_t *self, unsigned udp_mtu){  tport_t *tp;  self->sa_udp_mtu = udp_mtu;  /* Set via fields for the tports */  for (tp = tport_primaries(self->sa_tports); tp; tp = tport_next(tp)) {    if (tport_is_udp(tp))      tport_set_params(tp,		       TPTAG_TIMEOUT(2 * self->sa_t1x64),		       TPTAG_MTU(self->sa_udp_mtu),		       TAG_END());  }}/**Get NTA Parameters. * * The nta_agent_get_params() function retrieves the stack parameters. The * parameters determine the way NTA handles the retransmissions, how long * NTA keeps transactions alive, does NTA apply proxy or user-agent logic to * INVITE transactions, or how the @b Via headers are generated. * * @TAGS * NTATAG_ALIASES_REF(), NTATAG_CANCEL_2543_REF(), NTATAG_CANCEL_487_REF(), * NTATAG_CONTACT_REF(), NTATAG_DEBUG_DROP_PROB_REF(), * NTATAG_DEFAULT_PROXY_REF(), NTATAG_EXTRA_100_REF(), NTATAG_MAXSIZE_REF(), * NTATAG_MERGE_482_REF(), NTATAG_PASS_100_REF(), NTATAG_PRELOAD_REF(), * NTATAG_REL100_REF(), NTATAG_RPORT_REF(), NTATAG_SIPFLAGS_REF(), * NTATAG_SIP_T1X64_REF(), NTATAG_SIP_T1_REF(), NTATAG_SIP_T2_REF(), * NTATAG_SIP_T4_REF(), NTATAG_SMIME_REF(), NTATAG_STATELESS_REF(), * NTATAG_TAG_3261_REF(), NTATAG_TIMEOUT_408_REF(), NTATAG_PASS_408_REF(), * NTATAG_UA_REF(), NTATAG_USER_VIA_REF(), and NTATAG_USE_TIMESTAMP_REF(). * */int nta_agent_get_params(nta_agent_t *agent,			 tag_type_t tag, tag_value_t value, ...){  int n;  ta_list ta;  if (agent) {    ta_start(ta, tag, value);    n = agent_get_params(agent, ta_args(ta));    ta_end(ta);  } else {    su_seterrno(EINVAL);    n = -1;  }  return n;}/** Get NTA parameters */staticint agent_get_params(nta_agent_t *agent, tagi_t *tags){  return    tl_tgets(tags,	     NTATAG_MCLASS(agent->sa_mclass),	     NTATAG_CONTACT(agent->sa_contact),	     NTATAG_ALIASES(agent->sa_aliases),	     NTATAG_UA(agent->sa_is_a_uas),	     NTATAG_STATELESS(agent->sa_is_stateless),	     NTATAG_MAXSIZE(agent->sa_maxsize),	     NTATAG_UDP_MTU(agent->sa_udp_mtu),	     NTATAG_SIP_T1(agent->sa_t1),	     NTATAG_SIP_T2(agent->sa_t2),	     NTATAG_SIP_T4(agent->sa_t4),	     NTATAG_SIP_T1X64(agent->sa_t1x64),	     NTATAG_BLACKLIST(agent->sa_blacklist),	     NTATAG_DEBUG_DROP_PROB(agent->sa_drop_prob),	     NTATAG_USER_VIA(agent->sa_user_via),	     NTATAG_EXTRA_100(agent->sa_extra_100),	     NTATAG_PASS_100(agent->sa_pass_100),	     NTATAG_TIMEOUT_408(agent->sa_timeout_408),	     NTATAG_PASS_408(agent->sa_pass_408),	     NTATAG_MERGE_482(agent->sa_merge_482),	     NTATAG_DEFAULT_PROXY(agent->sa_default_proxy),	     NTATAG_CANCEL_2543(agent->sa_cancel_2543),	     NTATAG_CANCEL_487(agent->sa_cancel_487),	     NTATAG_TAG_3261(1),	     NTATAG_REL100(agent->sa_invite_100rel),	     NTATAG_USE_TIMESTAMP(agent->sa_timestamp),	     NTATAG_USE_NAPTR(agent->sa_use_naptr),	     NTATAG_USE_SRV(agent->sa_use_srv),#if HAVE_SOFIA_SMIME	     NTATAG_SMIME(agent->sa_smime),#else	     NTATAG_SMIME(NULL),#endif	     NTATAG_SIPFLAGS(agent->sa_flags),	     NTATAG_RPORT(agent->sa_rport),	     NTATAG_PRELOAD(agent->sa_preload),	     NTATAG_SIGCOMP_ALGORITHM(agent->sa_algorithm),	     NTATAG_SIGCOMP_OPTIONS(agent->sa_sigcomp_options ?				    agent->sa_sigcomp_options :				    "sip"),	     TAG_END());}/**Get NTA statistics. * * The nta_agent_get_stats() function retrieves the stack statistics. * * @TAGS * @TAG NTATAG_S_* * */int nta_agent_get_stats(nta_agent_t *agent,			tag_type_t tag, tag_value_t value, ...){  int n;  ta_list ta;  if (!agent)    return su_seterrno(EINVAL), -1;  ta_start(ta, tag, value);  n = tl_tgets(ta_args(ta),	       NTATAG_S_IRQ_HASH(agent->sa_incoming->iht_size),	       NTATAG_S_ORQ_HASH(agent->sa_outgoing->oht_size),	       NTATAG_S_LEG_HASH(agent->sa_dialogs->lht_size),	       NTATAG_S_IRQ_HASH_USED(agent->sa_incoming->iht_used),	       NTATAG_S_ORQ_HASH_USED(agent->sa_outgoing->oht_used),	       NTATAG_S_LEG_HASH_USED(agent->sa_dialogs->lht_used),	       NTATAG_S_RECV_MSG(agent->sa_stats->as_recv_msg),	       NTATAG_S_RECV_REQUEST(agent->sa_stats->as_recv_request),	       NTATAG_S_RECV_RESPONSE(agent->sa_stats->as_recv_response),	       NTATAG_S_BAD_MESSAGE(agent->sa_stats->as_bad_message),	       NTATAG_S_BAD_REQUEST(agent->sa_stats->as_bad_request),	       NTATAG_S_BAD_RESPONSE(agent->sa_stats->as_bad_response),	       NTATAG_S_DROP_REQUEST(agent->sa_stats->as_drop_request),	       NTATAG_S_DROP_RESPONSE(agent->sa_stats->as_drop_response),	       NTATAG_S_CLIENT_TR(agent->sa_stats->as_client_tr),	       NTATAG_S_SERVER_TR(agent->sa_stats->as_server_tr),	       NTATAG_S_DIALOG_TR(agent->sa_stats->as_dialog_tr),	       NTATAG_S_ACKED_TR(agent->sa_stats->as_acked_tr),	       NTATAG_S_CANCELED_TR(agent->sa_stats->as_canceled_tr),	       NTATAG_S_TRLESS_REQUEST(agent->sa_stats->as_trless_request),	       NTATAG_S_TRLESS_TO_TR(agent->sa_stats->as_trless_to_tr),	       NTATAG_S_TRLESS_RESPONSE(agent->sa_stats->as_trless_response),	       NTATAG_S_TRLESS_200(agent->sa_stats->as_trless_200),	       NTATAG_S_MERGED_REQUEST(agent->sa_stats->as_merged_request),	       NTATAG_S_SENT_MSG(agent->sa_stats->as_sent_msg),	       NTATAG_S_SENT_REQUEST(agent->sa_stats->as_sent_request),	       NTATAG_S_SENT_RESPONSE(agent->sa_stats->as_sent_response),	       NTATAG_S_RETRY_REQUEST(agent->sa_stats->as_retry_request),	       NTATAG_S_RETRY_RESPONSE(agent->sa_stats->as_retry_response),	       NTATAG_S_RECV_RETRY(agent->sa_stats->as_recv_retry),	       NTATAG_S_TOUT_REQUEST(agent->sa_stats->as_tout_request),	       NTATAG_S_TOUT_RESPONSE(agent->sa_stats->as_tout_response),	       TAG_END());  ta_end(ta);  return n;}/**Calculate a new unique tag. * * This function generates a series of 2**64 unique tags for @b From or @b To * headers. The start of the tag series is derived from the NTP time the NTA * agent was initialized. * */char const *nta_agent_newtag(su_home_t *home, char const *fmt, nta_agent_t *sa){  char tag[(8 * 8 + 4)/ 5 + 1];  if (sa == NULL)    return su_seterrno(EINVAL), NULL;  /* XXX - use a cryptographically safe func here? */  sa->sa_tags += NTA_TAG_PRIME;  msg_random_token(tag, sizeof(tag) - 1, &sa->sa_tags, sizeof(sa->sa_tags));  if (fmt && fmt[0])    return su_sprintf(home, fmt, tag);  else    return su_strdup(home, tag);}/** * Calculate branch value. */static char const *stateful_branch(su_home_t *home, nta_agent_t *sa){  char branch[(8 * 8 + 4)/ 5 + 1];  /* XXX - use a cryptographically safe func here? */  sa->sa_branch += NTA_BRANCH_PRIME;  msg_random_token(branch, sizeof(branch) - 1, 		   &sa->sa_branch, sizeof(sa->sa_branch));  return su_sprintf(home, "branch=z9hG4bK%s", branch);}#include <sofia-sip/su_md5.h>/** * Calculate branch value for stateless operation. *  * XXX - should include HMAC of previous Via line. */staticchar const *stateless_branch(nta_agent_t *sa, 			     msg_t *msg,			     sip_t const *sip, 			     tp_name_t const *tpn){  su_md5_t md5[1];  uint8_t digest[SU_MD5_DIGEST_SIZE];  char branch[(SU_MD5_DIGEST_SIZE * 8 + 4)/ 5 + 1];  sip_route_t const *r;  assert(sip->sip_request);  if (!sip->sip_via)    return stateful_branch(msg_home(msg), sa);  su_md5_init(md5);  su_md5_str0update(md5, tpn->tpn_host);  su_md5_str0update(md5, tpn->tpn_port);  url_update(md5, sip->sip_request->rq_url);  if (sip->sip_call_id) {    su_md5_str0update(md5, sip->sip_call_id->i_id);  }  if (sip->sip_from) {    url_update(md5, sip->sip_from->a_url);    su_md5_stri0update(md5, sip->sip_from->a_tag);  }  if (sip->sip_to) {    url_update(md5, sip->sip_to->a_url);    /* XXX - some broken implementations include To tag in CANCEL */    /* su_md5_str0update(md5, sip->sip_to->a_tag); */  }  if (sip->sip_cseq) {    uint32_t cseq = htonl(sip->sip_cseq->cs_seq);    su_md5_update(md5, &cseq, sizeof(cseq));  }  for (r = sip->sip_route; r; r = r->r_next)    url_update(md5, r->r_url);  su_md5_digest(md5, digest);  msg_random_token(branch, sizeof(branch) - 1, digest, sizeof(digest));  return su_sprintf(msg_home(msg), "branch=z9hG4bK.%s", branch);}/* ====================================================================== *//* 2) Transport interface *//* Local prototypes */static int agent_create_master_transport(nta_agent_t *self, tagi_t *tags);static int agent_init_via(nta_agent_t *self, tport_t *primaries, int use_maddr);static int agent_init_contact(nta_agent_t *self);static void agent_recv_message(nta_agent_t *agent,			       tport_t *tport,			       msg_t *msg,			       sip_via_t *tport_via,			       su_time_t now);static void agent_tp_error(nta_agent_t *agent,			   tport_t *tport,			   int errcode,			   char const *remote);static void agent_update_tport(nta_agent_t *agent, tport_t *);/**For each transport, we have name used by tport module, SRV prefixes used * for resolving, and NAPTR service/conversion. */static struct sipdns_tport {  char name[6];			/**< Named used by tport module */  char port[6];			/**< Default port number */  char prefix[14];		/**< Prefix for SRV domains */  char service[10];		/**< NAPTR service */}#define SIPDNS_TRANSPORTS (4)const sipdns_tports[SIPDNS_TRANSPORTS] = {  { "udp",  "5060", "_sip._udp.",  "SIP+D2U"  },  { "tcp",  "5060", "_sip._tcp.",  "SIP+D2T"  },  { "sctp", "5060", "_sip._sctp.", "SIP+D2S" },  { "tls",  "5061", "_sips._tcp.", "SIPS+D2T"  },};static char const * const tports_sip[] =  {    "udp", "tcp", "sctp", NULL  };static char const * const tports_sips[] =  {    "tls", NULL  };static tport_stack_class_t nta_agent_class[1] =  {{    sizeof(nta_agent_class),    agent_recv_message,    agent_tp_error,    (void *)nta_msg_create_for_transport,    agent_update_tport,  }};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -