📄 nua_params.c
字号:
/* NUTAG_ALLOW_EVENTS(allow_events) */ /* SIPTAG_ALLOW_EVENTS_STR(allow_events) */ /* SIPTAG_ALLOW_EVENTS(allow_events) */ else if (tag == nutag_allow_events || tag == siptag_allow_events_str || tag == siptag_allow_events) { int ok; sip_allow_events_t *allow_events = NULL; ok = nhp_merge_lists(home, sip_allow_events_class, &allow_events, nhp->nhp_allow_events, NHP_ISSET(nhp, allow_events), /* already set */ tag == siptag_allow_events, /* dup it, don't make */ tag == nutag_allow_events, /* merge with old value */ t->t_value); if (ok < 0) return -1; else if (ok) NHP_SET(nhp, allow_events, allow_events); } /* NUTAG_APPL_METHOD(appl_method) */ else if (tag == nutag_appl_method) { if (t->t_value == 0) { NHP_SET(nhp, appl_method, NULL); } else { int ok; msg_list_t *appl_method = NULL; ok = nhp_merge_lists(home, sip_allow_class, &appl_method, (msg_list_t const *)nhp->nhp_appl_method, /* already set by tags? */ NHP_ISSET(nhp, appl_method), 0, /* dup it, don't make */ 1, /* merge with old value */ t->t_value); if (ok < 0) return -1; else if (ok) NHP_SET(nhp, appl_method, (sip_allow_t *)appl_method); } } else if (tag == nutag_initial_route || tag == nutag_initial_route_str) {#define next_route(r) (&(r)->r_next) NHP_APPEND_HEADER(nhp, initial_route, route, (tag == nutag_initial_route_str), next_route, t->t_value); sip_route_fix(nhp->nhp_initial_route); } /* SIPTAG_USER_AGENT(user_agent) */ else if (tag == siptag_user_agent) { NHP_SET_STR_BY_HEADER(nhp, user_agent, value); } /* SIPTAG_USER_AGENT_STR(user_agent_str) */ else if (tag == siptag_user_agent_str && value != 0) { if (value == -1) value = 0; NHP_SET_STR(nhp, user_agent, value); } /* NUTAG_USER_AGENT(ua_name) */ else if (tag == nutag_user_agent) { /* Add contents of NUTAG_USER_AGENT() to our distribution name */ char const *str = (void *)value, *ua; if (str && !already_contains_package_name(str)) ua = su_sprintf(home, "%s %s", str, NHP_USER_AGENT); else if (str) ua = su_strdup(home, str); else ua = su_strdup(home, NHP_USER_AGENT); NHP_SET(nhp, user_agent, ua); } /* SIPTAG_ORGANIZATION(organization) */ else if (tag == siptag_organization) { NHP_SET_STR_BY_HEADER(nhp, organization, value); } /* SIPTAG_ORGANIZATION_STR(organization_str) */ else if (tag == siptag_organization_str) { if (value == -1) value = 0; NHP_SET_STR(nhp, organization, value); } /* NUTAG_REGISTRAR(registrar) */ else if (tag == nutag_registrar) { NHP_SET_STR_BY_URL(nhp, char, registrar, value); if (NHP_ISSET(nhp, registrar) && !str0cmp(nhp->nhp_registrar, "*")) NHP_SET_STR(nhp, registrar, 0); } /* NUTAG_INSTANCE(instance) */ else if (tag == nutag_instance) { NHP_SET_STR(nhp, instance, value); } /* NUTAG_M_DISPLAY(m_display) */ else if (tag == nutag_m_display) { NHP_SET_STR(nhp, m_display, value); } /* NUTAG_M_USERNAME(m_username) */ else if (tag == nutag_m_username) { NHP_SET_STR(nhp, m_username, value); } /* NUTAG_M_PARAMS(m_params) */ else if (tag == nutag_m_params) { NHP_SET_STR(nhp, m_params, value); } /* NUTAG_M_FEATURES(m_features) */ else if (tag == nutag_m_features) { NHP_SET_STR(nhp, m_features, value); } /* NUTAG_OUTBOUND(outbound) */ else if (tag == nutag_outbound) { NHP_SET_STR(nhp, outbound, value); } /* NUTAG_PROXY() (aka NTATAG_DEFAULT_PROXY()) */ else if (tag == ntatag_default_proxy) { NHP_SET_STR_BY_URL(nhp, url_string_t, proxy, value); } /* NUTAG_DETECT_NETWORK_UPDATES(detect_network_updates) */ else if (ngp && tag == nutag_detect_network_updates) { int detector = (int)value; if (detector < NUA_NW_DETECT_NOTHING) detector = NUA_NW_DETECT_NOTHING; else if (detector > NUA_NW_DETECT_TRY_FULL) detector = NUA_NW_DETECT_TRY_FULL; ngp->ngp_detect_network_updates = detector; ngp->ngp_set.ngp_detect_network_updates = 1; } /* NUTAG_SHUTDOWN_EVENTS() */ else if (ngp && tag == nutag_shutdown_events) { ngp->ngp_shutdown_events = value != 0; ngp->ngp_set.ngp_shutdown_events = 1; } } return 0;}/** Merge (when needed) new values with old values. */static int nhp_merge_lists(su_home_t *home, msg_hclass_t *hc, msg_list_t **return_new_list, msg_list_t const *old_list, int already_set, int already_parsed, int always_merge, tag_value_t value){ msg_list_t *list, *elems; if (value == -1) { *return_new_list = NULL; return 1; } if (value == 0) { if (!already_set && !always_merge) { *return_new_list = NULL; return 1; } return 0; } if (already_parsed) elems = (void *)msg_header_dup_as(home, hc, (msg_header_t *)value); else elems = (void *)msg_header_make(home, hc, (char const *)value); if (!elems) return -1; list = (msg_list_t *)old_list; if (!already_set) { if (always_merge && list) { list = (void *)msg_header_dup_as(home, hc, (void *)old_list); if (!list) return -1; } else list = NULL; } if (!list) { *return_new_list = elems; return 1; } /* Add contents to the new list to the old list */ if (msg_params_join(home, (msg_param_t **)&list->k_items, elems->k_items, 2 /* prune */, 0 /* don't dup */) < 0) return -1; *return_new_list = (msg_list_t *)msg_header_dup_as(home, hc, (msg_header_t *)list); if (!*return_new_list) return -1; msg_header_free(home, (msg_header_t *)list); msg_header_free(home, (msg_header_t *)elems); return 1;}/** Save parameters in @a gtmp and @a tmp. * * @retval 1 - parameters were changed * @retval 0 - no changes in parameters * @retval -1 - an error */static int nhp_save_params(nua_handle_t *nh, su_home_t *tmphome, nua_global_preferences_t *gsrc, nua_handle_preferences_t *src){ su_home_t *home = nh->nh_home; nua_t *nua = nh->nh_nua; nua_handle_t *dnh = nua->nua_dhandle; nua_handle_preferences_t *dst = nh->nh_prefs, old[1]; if (gsrc) { *nua->nua_prefs = *gsrc; /* No pointers this far */ } if (!NHP_IS_ANY_SET(src)) return 0; if (nh == dnh || nh->nh_prefs != dnh->nh_prefs) { dst = nh->nh_prefs, *old = *dst; } else { dst = su_zalloc(home, sizeof *dst), memset(old, 0, sizeof *old); if (!dst) return -1; } /* Move allocations from tmphome to home */ su_home_move(nh->nh_home, tmphome); /* Copy parameters that are set from src to dst */ nhp_or_set(dst, src); /* Handle pointer items. Free changed ones and zap unset ones. */ /* Note that pointer items where !NHP_ISSET(old, pref) are not freed (because they were just on loan from the default preference set) */#define NHP_ZAP_OVERRIDEN(old, dst, free, pref) \ (((NHP_ISSET(old, pref) && \ (old)->nhp_##pref && (old)->nhp_##pref != (dst)->nhp_##pref) \ ? (free)(home, (void *)(old)->nhp_##pref) : (void)0), \ (void)(!(dst)->nhp_set.nhb_##pref ? (dst)->nhp_##pref = NULL : NULL)) NHP_ZAP_OVERRIDEN(old, dst, su_free, soa_name); NHP_ZAP_OVERRIDEN(old, dst, su_free, registrar); NHP_ZAP_OVERRIDEN(old, dst, msg_header_free, allow); NHP_ZAP_OVERRIDEN(old, dst, msg_header_free, supported); NHP_ZAP_OVERRIDEN(old, dst, msg_header_free, allow_events); NHP_ZAP_OVERRIDEN(old, dst, su_free, user_agent); NHP_ZAP_OVERRIDEN(old, dst, su_free, organization); NHP_ZAP_OVERRIDEN(old, dst, su_free, m_display); NHP_ZAP_OVERRIDEN(old, dst, su_free, m_username); NHP_ZAP_OVERRIDEN(old, dst, su_free, m_params); NHP_ZAP_OVERRIDEN(old, dst, su_free, m_features); NHP_ZAP_OVERRIDEN(old, dst, su_free, instance); NHP_ZAP_OVERRIDEN(old, dst, su_free, outbound); NHP_ZAP_OVERRIDEN(old, dst, msg_header_free, appl_method); NHP_ZAP_OVERRIDEN(old, dst, msg_header_free, initial_route); nh->nh_prefs = dst; return memcmp(dst, old, sizeof *dst) != 0;}static int nua_handle_tags_filter(tagi_t const *f, tagi_t const *t);static int nua_handle_param_filter(tagi_t const *f, tagi_t const *t);/** Save taglist to a handle */int nua_handle_save_tags(nua_handle_t *nh, tagi_t *tags){ /* Initialization parameters */ url_string_t const *url = NULL; sip_to_t const *p_to = NULL; char const *to_str = NULL; sip_from_t const *p_from = NULL; char const *from_str = NULL; nua_handle_t *identity = NULL; tagi_t const *t; su_home_t tmphome[SU_HOME_AUTO_SIZE(1024)]; int error;#if HAVE_OPEN_C /* Nice. An old symbian compiler */ tagi_t tagfilter[2]; tagi_t paramfilter[2]; tagfilter[0].t_tag = tag_filter; tagfilter[0].t_value = tag_filter_v(nua_handle_tags_filter); tagfilter[1].t_tag = (tag_type_t)0; tagfilter[1].t_value = (tag_value_t)0; paramfilter[0].t_tag = tag_filter; paramfilter[0].t_value = tag_filter_v(nua_handle_param_filter); paramfilter[1].t_tag = (tag_type_t)0; paramfilter[1].t_value = (tag_value_t)0;#else tagi_t const tagfilter[] = { { TAG_FILTER(nua_handle_tags_filter) }, { TAG_NULL() } }; tagi_t const paramfilter[] = { { TAG_FILTER(nua_handle_param_filter) }, { TAG_NULL() } };#endif for (t = tags; t; t = tl_next(t)) { if (t->t_tag == NULL) break; /* SIPTAG_FROM_REF(p_from) */ else if (t->t_tag == siptag_from) { p_from = (sip_from_t *)t->t_value, from_str = NULL; } /* SIPTAG_FROM_STR_REF(from_str) */ else if (t->t_tag == siptag_from_str) { from_str = (char const *)t->t_value, p_from = NULL; } /* SIPTAG_TO_REF(p_to) */ else if (t->t_tag == siptag_to) { p_to = (sip_to_t *)t->t_value, to_str = NULL; } /* SIPTAG_TO_STR_REF(to_str) */ else if (t->t_tag == siptag_to_str) { to_str = (char const *)t->t_value, p_to = NULL; } /* NUTAG_IDENTITY_REF(identity) */ else if (t->t_tag == nutag_identity) { identity = (nua_handle_t *)t->t_value; } /* NUTAG_URL_REF(url) */ else if (t->t_tag == nutag_url) { url = (url_string_t *)t->t_value; } /* NUTAG_SIPS_URL_REF(url) */ else if (t->t_tag == nutag_sips_url) { url = (url_string_t *)t->t_value; } } su_home_auto(tmphome, sizeof tmphome); if (p_from) ; else if (from_str) p_from = sip_from_make(tmphome, from_str); else p_from = SIP_NONE; if (p_to) ; else if (to_str) p_to = sip_to_make(tmphome, to_str); else if (url) p_to = sip_to_create(tmphome, url), p_to ? sip_aor_strip((url_t*)p_to->a_url) : 0; else p_to = SIP_NONE; if (p_to == NULL || p_from == NULL) { su_home_deinit(tmphome); return -1; } nh->nh_tags = tl_filtered_tlist(nh->nh_home, tagfilter, TAG_IF(p_from != SIP_NONE, SIPTAG_FROM(p_from)), TAG_IF(p_from != SIP_NONE, TAG_FILTER(nua_handle_tags_filter)), TAG_IF(p_to != SIP_NONE, SIPTAG_TO(p_to)), TAG_IF(p_to != SIP_NONE, TAG_FILTER(nua_handle_tags_filter)), TAG_NEXT(tags)); nh->nh_ptags = tl_filtered_tlist(nh->nh_home, paramfilter, TAG_NEXT(tags)); error = nh->nh_tags == NULL || nh->nh_ptags == NULL; if (!error) tl_gets(nh->nh_tags, /* These does not change while nh lives */ SIPTAG_FROM_REF(nh->nh_ds->ds_local), SIPTAG_TO_REF(nh->nh_ds->ds_remote), TAG_END()); if (nh->nh_ptags && nh->nh_ptags->t_tag == NULL) su_free(nh->nh_home, nh->nh_ptags), nh->nh_ptags = NULL; if (identity) nh->nh_identity = nua_handle_ref(identity); su_home_deinit(tmphome); return -error;}/** Filter tags used for settings. */static int nua_handle_param_filter(tagi_t const *f, tagi_t const *t){ char const *ns; if (!t || !t->t_tag) return 0; if (t->t_tag == nutag_url || t->t_tag == nutag_sips_url || t->t_tag == nutag_identity) return 0; ns = t->t_tag->tt_ns; if (!ns) return 0; return strcmp(ns, "nua") == 0 || strcmp(ns, "soa") == 0;}/** Filter tags stored permanently as taglist. */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -