Index: channels/chan_sip.c =================================================================== --- channels/chan_sip.c (revision 37046) +++ channels/chan_sip.c (working copy) @@ -1348,7 +1348,7 @@ /*--- Device object handling */ static struct sip_peer *temp_peer(const char *name); -static struct sip_peer *build_peer(const char *name, struct ast_variable *v, int realtime); +static struct sip_peer *build_peer(const char *name, struct ast_variable *v, struct ast_variable *v2, int realtime); static struct sip_user *build_user(const char *name, struct ast_variable *v, int realtime); static int update_call_counter(struct sip_pvt *fup, int event); static void sip_destroy_peer(struct sip_peer *peer); @@ -2191,12 +2191,21 @@ char port[10]; char ipaddr[20]; char regseconds[20]; + char *tablename = NULL; char *sysname = ast_config_AST_SYSTEM_NAME; char *syslabel = NULL; time_t nowtime = time(NULL) + expirey; const char *fc = fullcontact ? "fullcontact" : NULL; + + int realtimeregs; + + realtimeregs = ast_check_realtime("sipregs"); + if (realtimeregs) + tablename = "sipregs"; + else + tablename = "sippeers"; snprintf(regseconds, sizeof(regseconds), "%d", (int)nowtime); /* Expiration time */ ast_inet_ntoa(ipaddr, sizeof(ipaddr), sin->sin_addr); @@ -2208,11 +2217,11 @@ syslabel = "regserver"; if (fc) - ast_update_realtime("sippeers", "name", peername, "ipaddr", ipaddr, + ast_update_realtime(tablename, "name", peername, "ipaddr", ipaddr, "port", port, "regseconds", regseconds, "username", username, fc, fullcontact, syslabel, sysname, NULL); /* note fc and syslabel _can_ be NULL */ else - ast_update_realtime("sippeers", "name", peername, "ipaddr", ipaddr, + ast_update_realtime(tablename, "name", peername, "ipaddr", ipaddr, "port", port, "regseconds", regseconds, "username", username, syslabel, sysname, NULL); /* note syslabel _can_ be NULL */ } @@ -2299,6 +2308,7 @@ /*! \brief realtime_peer: Get peer from realtime storage * Checks the "sippeers" realtime family from extconfig.conf + * Checks the "sipregs" realtime family from extconfig.conf if it's configured. * \todo Consider adding check of port address when matching here to follow the same * algorithm as for static peers. Will we break anything by adding that? */ @@ -2306,18 +2316,44 @@ { struct sip_peer *peer; struct ast_variable *var = NULL; + struct ast_variable *varregs = NULL; struct ast_variable *tmp; char iabuf[80]; + int realtimeregs; + realtimeregs = ast_check_realtime("sipregs"); + /* First check on peer name */ - if (newpeername) + if (newpeername) { var = ast_load_realtime("sippeers", "name", newpeername, NULL); - else if (sin) { /* Then check on IP address for dynamic peers */ + if (realtimeregs) + varregs = ast_load_realtime("sipregs", "name", newpeername, NULL); + } else if (sin) { /* Then check on IP address for dynamic peers */ ast_inet_ntoa(iabuf, sizeof(iabuf), sin->sin_addr); var = ast_load_realtime("sippeers", "host", iabuf, NULL); /* First check for fixed IP hosts */ - if (!var) - var = ast_load_realtime("sippeers", "ipaddr", iabuf, NULL); /* Then check for registred hosts */ - + if (var && realtimeregs) { + tmp = var; + while (tmp) + if (!newpeername && !strcasecmp(tmp->name, "name")) { + newpeername = tmp->value; + tmp = tmp->next; + } + varregs = ast_load_realtime("sipregs", "name", newpeername, NULL); + } else { + if (realtimeregs) + varregs = ast_load_realtime("sipregs", "ipaddr", iabuf, NULL); /* Then check for registered hosts */ + else + var = ast_load_realtime("sippeers", "ipaddr", iabuf, NULL); /* Then check for registered hosts */ + if (varregs) { + tmp = varregs; + while (tmp) { + if (!newpeername && !strcasecmp(tmp->name, "name")) + newpeername = tmp->value; + tmp = tmp->next; + } + var = ast_load_realtime("sippeers", "name", newpeername, NULL); + } + } } if (!var) @@ -2328,6 +2364,7 @@ if (!strcasecmp(tmp->name, "type") && !strcasecmp(tmp->value, "user")) { ast_variables_destroy(var); + ast_variables_destroy(varregs); return NULL; } else if (!newpeername && !strcasecmp(tmp->name, "name")) { newpeername = tmp->value; @@ -2337,13 +2374,15 @@ if (!newpeername) { /* Did not find peer in realtime */ ast_log(LOG_WARNING, "Cannot Determine peer name ip=%s\n", iabuf); ast_variables_destroy(var); + ast_variables_destroy(varregs); return NULL; } /* Peer found in realtime, now build it in memory */ - peer = build_peer(newpeername, var, !ast_test_flag(&global_flags[1], SIP_PAGE2_RTCACHEFRIENDS)); + peer = build_peer(newpeername, var, varregs, !ast_test_flag(&global_flags[1], SIP_PAGE2_RTCACHEFRIENDS)); if (!peer) { ast_variables_destroy(var); + ast_variables_destroy(varregs); return NULL; } @@ -2361,6 +2400,7 @@ ast_set_flag(&peer->flags[0], SIP_REALTIME); } ast_variables_destroy(var); + ast_variables_destroy(varregs); return peer; } @@ -7166,9 +7206,16 @@ /*! \brief Remove registration data from realtime database or AST/DB when registration expires */ static void destroy_association(struct sip_peer *peer) { + int realtimeregs; + char *tablename; + realtimeregs = ast_check_realtime("sipregs"); + if (realtimeregs) + tablename = "sipregs"; + else + tablename = "sippeers"; if (!ast_test_flag(&global_flags[1], SIP_PAGE2_IGNOREREGEXPIRE)) { if (ast_test_flag(&peer->flags[1], SIP_PAGE2_RT_FROMCONTACT)) - ast_update_realtime("sippeers", "name", peer->name, "fullcontact", "", "ipaddr", "", "port", "", "regseconds", "0", "username", "", "regserver", "", NULL); + ast_update_realtime(tablename, "name", peer->name, "fullcontact", "", "ipaddr", "", "port", "", "regseconds", "0", "username", "", "regserver", "", NULL); else ast_db_del("SIP/Registry", peer->name); } @@ -9875,9 +9922,11 @@ char tmp[BUFSIZ]; int realtimepeers; int realtimeusers; + int realtimeregs; realtimepeers = ast_check_realtime("sippeers"); realtimeusers = ast_check_realtime("sipusers"); + realtimeregs = ast_check_realtime("sipregs"); if (argc != 3) return RESULT_SHOWUSAGE; @@ -9910,7 +9959,7 @@ ast_cli(fd, " T38 fax pt UDPTL: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_T38SUPPORT_UDPTL) ? "Yes" : "No"); ast_cli(fd, " T38 fax pt RTP: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_T38SUPPORT_RTP) ? "Yes" : "No"); ast_cli(fd, " T38 fax pt TCP: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_T38SUPPORT_TCP) ? "Yes" : "No"); - if (!realtimepeers && !realtimeusers) + if (!realtimepeers && !realtimeusers && !realtimeregs) ast_cli(fd, " SIP realtime: Disabled\n" ); else ast_cli(fd, " SIP realtime: Enabled\n" ); @@ -9949,11 +9998,12 @@ ast_cli(fd, " Voice Mail Extension: %s\n", default_vmexten); - if (realtimepeers || realtimeusers) { + if (realtimepeers || realtimeusers || realtimeregs) { ast_cli(fd, "\nRealtime SIP Settings:\n"); ast_cli(fd, "----------------------\n"); ast_cli(fd, " Realtime Peers: %s\n", realtimepeers ? "Yes" : "No"); ast_cli(fd, " Realtime Users: %s\n", realtimeusers ? "Yes" : "No"); + ast_cli(fd, " Realtime Regs: %s\n", realtimeregs ? "Yes" : "No"); ast_cli(fd, " Cache Friends: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_RTCACHEFRIENDS) ? "Yes" : "No"); ast_cli(fd, " Update: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_RTUPDATE) ? "Yes" : "No"); ast_cli(fd, " Ignore Reg. Expire: %s\n", ast_test_flag(&global_flags[1], SIP_PAGE2_IGNOREREGEXPIRE) ? "Yes" : "No"); @@ -15161,7 +15211,7 @@ } /*! \brief Build peer from configuration (file or realtime static/dynamic) */ -static struct sip_peer *build_peer(const char *name, struct ast_variable *v, int realtime) +static struct sip_peer *build_peer(const char *name, struct ast_variable *v, struct ast_variable *v2, int realtime) { struct sip_peer *peer = NULL; struct ast_ha *oldha = NULL; @@ -15387,6 +15437,24 @@ ast_clear_flag(&peer->flags[1], SIP_PAGE2_T38SUPPORT_TCP); } } + for (; v2; v2 = v2->next) { + if (handle_common_options(&peerflags[0], &mask[0], v2)) + continue; + if (realtime && !strcasecmp(v2->name, "fullcontact")) { + ast_copy_string(peer->fullcontact, v2->value, sizeof(peer->fullcontact)); + ast_set_flag(&peer->flags[1], SIP_PAGE2_RT_FROMCONTACT); + } else if (realtime && !strcasecmp(v2->name, "ipaddr") && !ast_strlen_zero(v2->value)) + inet_aton(v2->value, &(peer->addr.sin_addr)); + else if (!strcasecmp(v2->name, "port")) { + if (!realtime && ast_test_flag(&peer->flags[1], SIP_PAGE2_DYNAMIC)) + peer->defaddr.sin_port = htons(atoi(v2->value)); + else + peer->addr.sin_port = htons(atoi(v2->value)); + } else if (realtime && !strcasecmp(v2->name, "regseconds")) + ast_get_time_t(v2->value, ®seconds, 0, NULL); + else if (!strcasecmp(v2->name, "username")) + ast_copy_string(peer->username, v2->value, sizeof(peer->username)); + } if (!ast_test_flag(&global_flags[1], SIP_PAGE2_IGNOREREGEXPIRE) && ast_test_flag(&peer->flags[1], SIP_PAGE2_DYNAMIC) && realtime) { time_t nowtime = time(NULL); @@ -15806,7 +15874,7 @@ } } if (is_peer) { - peer = build_peer(cat, ast_variable_browse(cfg, cat), 0); + peer = build_peer(cat, ast_variable_browse(cfg, cat), NULL, 0); if (peer) { ASTOBJ_CONTAINER_LINK(&peerl,peer); ASTOBJ_UNREF(peer, sip_destroy_peer);