Index: channels/chan_iax2.c
===================================================================
RCS file: /usr/cvsroot/asterisk/channels/chan_iax2.c,v
retrieving revision 1.245
diff -u -r1.245 chan_iax2.c
--- channels/chan_iax2.c	30 Jan 2005 21:32:26 -0000	1.245
+++ channels/chan_iax2.c	7 Feb 2005 23:03:02 -0000
@@ -207,8 +207,12 @@
 #define IAX_CODEC_USER_FIRST (1 << 14)  /* are we willing to let the other guy choose the codec? */
 #define IAX_CODEC_NOPREFS (1 << 15) /* Force old behaviour by turning off prefs */
 #define IAX_CODEC_NOCAP (1 << 16) /* only consider requested format and ignore capabilities*/
+#define IAX_RTCACHEFRIENDS (1 << 17) /* let realtime stay till your reload */
+#define IAX_RTNOUPDATE (1 << 18) /* Don't send a realtime update */
+#define IAX_RTAUTOCLEAR (1 << 19) /* erase me on expire */ 
 
 static struct iax2_peer *realtime_peer(const char *peername);
+static int reload_config(void);
 
 struct iax2_user {
 	char name[80];
@@ -576,8 +580,15 @@
 static int send_command_immediate(struct chan_iax2_pvt *, char, int, unsigned int, char *, int, int);
 static int send_command_final(struct chan_iax2_pvt *, char, int, unsigned int, char *, int, int);
 static int send_command_transfer(struct chan_iax2_pvt *, char, int, unsigned int, char *, int);
+static struct iax2_user *build_user(const char *name, struct ast_variable *v, int temponly);
+static void destroy_user(struct iax2_user *user);
+static int expire_registry(void *data);
+static int iax2_write(struct ast_channel *c, struct ast_frame *f);
+static int iax2_do_register(struct iax2_registry *reg);
+static void prune_peers(void);
+static int iax2_poke_peer(struct iax2_peer *peer, int heldcall);
+static int iax2_provision(struct sockaddr_in *end, char *dest, const char *template, int force);
 
-static unsigned int calc_timestamp(struct chan_iax2_pvt *p, unsigned int ts, struct ast_frame *f);
 
 static int send_ping(void *data)
 {
@@ -653,7 +664,7 @@
 		return csub;
 }
 
-static struct iax2_peer *find_peer(const char *name) 
+static struct iax2_peer *find_peer(const char *name, int realtime) 
 {
 	struct iax2_peer *peer;
 	ast_mutex_lock(&peerl.lock);
@@ -663,7 +674,7 @@
 		}
 	}
 	ast_mutex_unlock(&peerl.lock);
-	if(!peer)
+	if(!peer && realtime)
 		peer = realtime_peer(name);
 	return peer;
 }
@@ -1623,6 +1634,29 @@
 "to establish the maximum excess jitter buffer that is permitted before the jitter\n"
 "buffer size is reduced.";
 
+static int iax2_prune_realtime(int fd, int argc, char *argv[])
+{
+	struct iax2_peer *peer;
+
+	if (argc != 4)
+        return RESULT_SHOWUSAGE;
+	if (!strcmp(argv[3],"all")) {
+		reload_config();
+		ast_cli(fd, "OK cache is flushed.\n");
+	} else if ((peer = find_peer(argv[3], 0))) {
+		if(ast_test_flag(peer, IAX_RTCACHEFRIENDS)) {
+			ast_set_flag(peer, IAX_RTAUTOCLEAR);
+			expire_registry(peer);
+			ast_cli(fd, "OK peer %s was removed from the cache.\n", argv[3]);
+		} else {
+			ast_cli(fd, "SORRY peer %s is not eligible for this operation.\n", argv[3]);
+		}
+	} else {
+		ast_cli(fd, "SORRY peer %s was not found in the cache.\n", argv[3]);
+	}
+	
+	return RESULT_SUCCESS;
+}
 
 /*--- iax2_show_peer: Show one peer in detail ---*/
 static int iax2_show_peer(int fd, int argc, char *argv[])
@@ -1632,11 +1666,14 @@
 	char iabuf[INET_ADDRSTRLEN];
 	struct iax2_peer *peer;
 	char codec_buf[512];
-	int x = 0, codec = 0;
+	int x = 0, codec = 0, load_realtime = 0;
 
-	if (argc != 4)
+	if (argc < 4)
 		return RESULT_SHOWUSAGE;
-	peer = find_peer(argv[3]);
+
+	load_realtime = (argc == 5 && !strcmp(argv[4], "load")) ? 1 : 0;
+
+	peer = find_peer(argv[3], load_realtime);
 	if (peer) {
 		ast_cli(fd,"\n\n");
 		ast_cli(fd, "  * Name       : %s\n", peer->name);
@@ -1798,6 +1835,10 @@
 "Usage: iax show peer <name>\n"
 "       Display details on specific IAX peer\n";
 
+static char prune_realtime_usage[] =
+"Usage: iax2 prune realtime [<peername>|all]\n"
+"       Prunes object(s) from the cache\n";
+
 static struct ast_cli_entry cli_set_jitter = 
 { { "iax2", "set", "jitter", NULL }, iax2_set_jitter, "Sets IAX jitter buffer", jitter_usage };
 
@@ -1810,6 +1851,9 @@
 static struct ast_cli_entry  cli_show_peer =
 	{ { "iax2", "show", "peer", NULL }, iax2_show_peer, "Show details on specific IAX peer", show_peer_usage, complete_iax2_show_peer };
 
+static struct ast_cli_entry  cli_prune_realtime =
+	{ { "iax2", "prune", "realtime", NULL }, iax2_prune_realtime, "Prune a cached realtime lookup", prune_realtime_usage, complete_iax2_show_peer };
+
 static unsigned int calc_rxstamp(struct chan_iax2_pvt *p, unsigned int offset);
 
 #ifdef BRIDGE_OPTIMIZATION
@@ -2142,6 +2186,7 @@
 static struct iax2_user *build_user(const char *name, struct ast_variable *v, int temponly);
 
 static void destroy_user(struct iax2_user *user);
+static int expire_registry(void *data);
 
 static struct iax2_peer *realtime_peer(const char *peername)
 {
@@ -2153,10 +2198,9 @@
 	var = ast_load_realtime("iaxfriends", "name", peername, NULL);
 	if (var) {
 		/* Make sure it's not a user only... */
-		peer = build_peer(peername, var, 1);
+		peer = build_peer(peername, var, ast_test_flag((&globalflags), IAX_RTCACHEFRIENDS) ? 0 : 1);
+
 		if (peer) {
-			/* Add some finishing touches, addresses, etc */
-			ast_set_flag(peer, IAX_TEMPONLY);	
 			tmp = var;
 			while(tmp) {
 				if (!strcasecmp(tmp->name, "type")) {
@@ -2180,6 +2224,20 @@
 				}
 				tmp = tmp->next;
 			}
+
+			/* Add some finishing touches, addresses, etc */
+		  	if(ast_test_flag((&globalflags), IAX_RTCACHEFRIENDS)) {
+				ast_mutex_lock(&peerl.lock);
+				peer->next = peerl.peers;
+				peerl.peers = peer;
+				ast_mutex_unlock(&peerl.lock);
+				ast_copy_flags(peer, &globalflags, IAX_RTAUTOCLEAR|IAX_RTCACHEFRIENDS);
+				if (ast_test_flag(peer, IAX_RTAUTOCLEAR))
+					peer->expire = ast_sched_add(sched, (peer->expirey + 10) * 1000, expire_registry, (void *)peer);
+			} else {
+		    		ast_set_flag(peer, IAX_TEMPONLY);	
+			}
+
 			if (peer && dynamic) {
 				time(&nowtime);
 				if ((nowtime - regseconds) > IAX_DEFAULT_REG_EXPIRE) {
@@ -2202,10 +2260,18 @@
 	var = ast_load_realtime("iaxfriends", "name", username, NULL);
 	if (var) {
 		/* Make sure it's not a user only... */
-		user = build_user(username, var, 1);
+		user = build_user(username, var, !ast_test_flag((&globalflags), IAX_RTCACHEFRIENDS));
 		if (user) {
 			/* Add some finishing touches, addresses, etc */
-			ast_set_flag(user, IAX_TEMPONLY);	
+		  	if(ast_test_flag((&globalflags), IAX_RTCACHEFRIENDS)) {
+				ast_mutex_lock(&userl.lock);
+				user->next = userl.users;
+				userl.users = user;
+				ast_mutex_unlock(&userl.lock);
+				ast_set_flag(user, IAX_RTCACHEFRIENDS);
+			} else {
+				ast_set_flag(user, IAX_TEMPONLY);	
+			}
 			tmp = var;
 			while(tmp) {
 				if (!strcasecmp(tmp->name, "type")) {
@@ -2259,7 +2325,7 @@
 	if (sockfd)
 		*sockfd = defaultsockfd;
 	sin->sin_family = AF_INET;
-	p = find_peer(peer);
+	p = find_peer(peer, 1);
 	if (p) {
 		found++;
 		if ((p->addr.sin_addr.s_addr || p->defaddr.sin_addr.s_addr) &&
@@ -4344,7 +4410,7 @@
 	/* We release the lock for the call to prevent a deadlock, but it's okay because
 	   only the current thread could possibly make it go away or make changes */
 	ast_mutex_unlock(&iaxsl[callno]);
-	p = find_peer(peer);
+	p = find_peer(peer, 1);
 	ast_mutex_lock(&iaxsl[callno]);
 
 	if (!p) {
@@ -4835,6 +4901,7 @@
 		}
 	}
 }
+static void prune_peers(void);
 
 static int expire_registry(void *data)
 {
@@ -4850,6 +4917,12 @@
 	register_peer_exten(p, 0);
 	if (iax2_regfunk)
 		iax2_regfunk(p->name, 0);
+
+	if (!ast_test_flag(p, IAX_RTAUTOCLEAR)) {
+		ast_set_flag(p, IAX_DELME);
+		prune_peers();
+	}
+
 	return 0;
 }
 
@@ -4904,9 +4977,9 @@
 	char iabuf[INET_ADDRSTRLEN];
 	int version;
 	memset(&ied, 0, sizeof(ied));
-	p = find_peer(name);
+	p = find_peer(name, 1);
 	if (p) {
-		if (ast_test_flag(p, IAX_TEMPONLY))
+		if (!ast_test_flag((&globalflags), IAX_RTNOUPDATE) && (ast_test_flag(p, IAX_TEMPONLY) || ast_test_flag(p, IAX_RTCACHEFRIENDS)))
 			realtime_update_peer(name, sin);
 		if (inaddrcmp(&p->addr, sin)) {
 			if (iax2_regfunk)
@@ -4980,7 +5053,7 @@
 {
 	struct iax_ie_data ied;
 	struct iax2_peer *p;
-	p = find_peer(name);
+	p = find_peer(name, 1);
 	if (p) {
 		memset(&ied, 0, sizeof(ied));
 		iax_ie_append_short(&ied, IAX_IE_AUTHMETHODS, p->authmethods);
@@ -7626,6 +7699,12 @@
 			delayreject = ast_true(v->value);
 		else if (!strcasecmp(v->name, "mailboxdetail"))
 			ast_set2_flag((&globalflags), ast_true(v->value), IAX_MESSAGEDETAIL);	
+		else if (!strcasecmp(v->name, "rtcachefriends"))
+			ast_set2_flag((&globalflags), ast_true(v->value), IAX_RTCACHEFRIENDS);	
+		else if (!strcasecmp(v->name, "rtnoupdate"))
+			ast_set2_flag((&globalflags), ast_true(v->value), IAX_RTNOUPDATE);	
+		else if (!strcasecmp(v->name, "rtautoclear"))
+			ast_set2_flag((&globalflags), ast_true(v->value), IAX_RTAUTOCLEAR);	
 		else if (!strcasecmp(v->name, "trunkfreq")) {
 			trunkfreq = atoi(v->value);
 			if (trunkfreq < 10)
@@ -8151,6 +8230,7 @@
 	ast_cli_unregister(&cli_show_stats);
 	ast_cli_unregister(&cli_show_cache);
 	ast_cli_unregister(&cli_show_peer);
+	ast_cli_unregister(&cli_prune_realtime);
 	ast_unregister_switch(&iax2_switch);
 	ast_channel_unregister(channeltype);
 	delete_users();
@@ -8222,6 +8302,7 @@
 	ast_cli_register(&cli_show_peers);
 	ast_cli_register(&cli_show_firmware);
 	ast_cli_register(&cli_show_registry);
+	ast_cli_register(&cli_prune_realtime);
 	ast_cli_register(&cli_provision);
 	ast_cli_register(&cli_debug);
 	ast_cli_register(&cli_trunk_debug);
Index: channels/chan_sip.c
===================================================================
RCS file: /usr/cvsroot/asterisk/channels/chan_sip.c,v
retrieving revision 1.648
diff -u -r1.648 chan_sip.c
--- channels/chan_sip.c	7 Feb 2005 14:56:43 -0000	1.648
+++ channels/chan_sip.c	7 Feb 2005 23:03:02 -0000
@@ -138,6 +138,7 @@
 static char default_notifymime[AST_MAX_EXTENSION] = DEFAULT_NOTIFYMIME;
 
 static struct ast_flags global_flags = {0};		/* global SIP_ flags */
+static struct ast_flags global_flags_page2 = {0};		/* more global SIP_ flags */
 
 static int srvlookup = 0;		/* SRV Lookup on or off. Default is off, RFC behavior is on */
 
@@ -303,6 +304,10 @@
 #define SIP_OSPAUTH_YES		(1 << 26)
 #define SIP_OSPAUTH_EXCLUSIVE	(2 << 26)
 
+/* a new page of flags */
+#define SIP_PAGE2_RTCACHEFRIENDS 	(1 << 0)
+#define SIP_PAGE2_RTNOUPDATE 		(1 << 1)
+#define SIP_PAGE2_RTAUTOCLEAR 		(1 << 2)
 /* sip_pvt: PVT structures are used for each SIP conversation, ie. a call  */
 static struct sip_pvt {
 	ast_mutex_t lock;			/* Channel private lock */
@@ -470,6 +475,7 @@
 	int lastmsgssent;
 	time_t	lastmsgcheck;		/* Last time we checked for MWI */
 	unsigned int flags;		/* SIP_ flags */	
+	struct ast_flags flags_page2; /* SIP_PAGE2 flags */
 	int expire;			/* Registration expiration */
 	int expiry;
 	int capability;			/* Codec capability */
@@ -587,7 +593,7 @@
 static int update_user_counter(struct sip_pvt *fup, int event);
 static void prune_peers(void);
 static int sip_do_reload(void);
-
+static int expire_register(void *data);
 static int callevents = 0;
 
 /*--- sip_debug_test_addr: See if we pass debug IP filter */
@@ -1110,7 +1116,9 @@
 /*--- update_peer: Update peer data in database (if used) ---*/
 static void update_peer(struct sip_peer *p, int expiry)
 {
-	if (ast_test_flag(p, SIP_REALTIME))
+	if (!ast_test_flag((&global_flags_page2), SIP_PAGE2_RTNOUPDATE) && 
+		(ast_test_flag(p, SIP_REALTIME) || 
+		 ast_test_flag(&(p->flags_page2), SIP_PAGE2_RTCACHEFRIENDS)))
 		realtime_update_peer(p->name, &p->addr, p->username, expiry);
 }
 
@@ -1145,9 +1153,18 @@
 		tmp = tmp->next;
 	}
 
-	peer = build_peer(peername, var, 1);
-	if (peer)
-		ast_set_flag(peer, SIP_REALTIME);
+	peer = build_peer(peername, var, ast_test_flag((&global_flags_page2), SIP_PAGE2_RTCACHEFRIENDS) ? 0 : 1);
+	if (peer) {
+		if(ast_test_flag((&global_flags_page2), SIP_PAGE2_RTCACHEFRIENDS)) {
+			ast_copy_flags((&peer->flags_page2),(&global_flags_page2), SIP_PAGE2_RTAUTOCLEAR|SIP_PAGE2_RTCACHEFRIENDS);
+			if(ast_test_flag((&global_flags_page2), SIP_PAGE2_RTAUTOCLEAR)) {
+				peer->expire = ast_sched_add(sched, (default_expiry) * 1000, expire_register, (void *)peer);
+			}
+			ASTOBJ_CONTAINER_LINK(&peerl,peer);
+		} else {
+			ast_set_flag(peer, SIP_REALTIME);
+		}
+	}
 	ast_variables_destroy(var);
 	return peer;
 }
@@ -1162,7 +1179,7 @@
 }
 
 /*--- find_peer: Locate peer by name or ip address */
-static struct sip_peer *find_peer(const char *peer, struct sockaddr_in *sin)
+static struct sip_peer *find_peer(const char *peer, struct sockaddr_in *sin, int realtime)
 {
 	struct sip_peer *p = NULL;
 
@@ -1171,7 +1188,7 @@
 	else
 		p = ASTOBJ_CONTAINER_FIND_FULL(&peerl,sin,name,sip_addr_hashfunc,1,sip_addrcmp);
 
-	if (!p) {
+	if (!p && realtime) {
 		p = realtime_peer(peer, sin);
 	}
 
@@ -1207,20 +1224,29 @@
 	tmp = var;
 	while (tmp) {
 		if (!strcasecmp(tmp->name, "type") &&
-		    !strcasecmp(tmp->value, "peer")) {
+			!strcasecmp(tmp->value, "peer")) {
 			ast_variables_destroy(var);
 			return NULL;
 		}
 		tmp = tmp->next;
 	}
+	
 
-	user = build_user(username, var, 1);
+
+	user = build_user(username, var, !ast_test_flag((&global_flags_page2), SIP_PAGE2_RTCACHEFRIENDS));
+	
 	if (user) {
-		/* Move counter from s to r... */
-		suserobjs--;
-		ruserobjs++;
 		/* Add some finishing touches, addresses, etc */
-		ast_set_flag(user, SIP_REALTIME);	
+		if(ast_test_flag((&global_flags_page2), SIP_PAGE2_RTCACHEFRIENDS)) {
+			suserobjs++;
+
+            ASTOBJ_CONTAINER_LINK(&userl,user);
+        } else {
+			/* Move counter from s to r... */
+			suserobjs--;
+			ruserobjs++;
+            ast_set_flag(user, SIP_REALTIME);
+        }
 	}
 	ast_variables_destroy(var);
 	return user;
@@ -1259,7 +1285,7 @@
 		port++;
 	}
 	r->sa.sin_family = AF_INET;
-	p = find_peer(peer, NULL);
+	p = find_peer(peer, NULL, 1);
 
 	if (p) {
 		found++;
@@ -4459,7 +4485,7 @@
 	register_peer_exten(p, 0);
 	p->expire = -1;
 	ast_device_state_changed("SIP/%s", p->name);
-	if (ast_test_flag(p, SIP_SELFDESTRUCT)) {
+	if (ast_test_flag(p, SIP_SELFDESTRUCT) || ast_test_flag((&p->flags_page2), SIP_PAGE2_RTAUTOCLEAR)) {
 		ASTOBJ_MARK(p);	
 		prune_peers();
 	}
@@ -5075,7 +5101,7 @@
 		*c = '\0';
 	strncpy(p->exten, name, sizeof(p->exten) - 1);
 	build_contact(p);
-	peer = find_peer(name, NULL);
+	peer = find_peer(name, NULL, 1);
 	if (!(peer && ast_apply_ha(peer->ha, sin))) {
 		if (peer)
 			ASTOBJ_UNREF(peer,sip_destroy_peer);
@@ -5671,7 +5697,7 @@
 		/* If peer is registred from this IP address or have this as a default
 		   IP address, this call is from the peer 
  		*/
-		peer = find_peer(NULL, &p->recv);
+		peer = find_peer(NULL, &p->recv, 1);
 		if (peer) {
 			if (debug)
 				ast_verbose("Found peer '%s'\n", peer->name);
@@ -5864,7 +5890,7 @@
 	regex_t regexbuf;
 	int havepattern = 0;
 
-#define FORMAT  "%-25.25s  %-15.15s  %-15.15s  %-15.15s  %-5.5s%-5.5s\n"
+#define FORMAT  "%-25.25s  %-15.15s  %-15.15s  %-15.15s  %-5.5s%-10.10s\n"
 
 	if (argc > 4)
 		return RESULT_SHOWUSAGE;
@@ -6052,6 +6078,30 @@
 	return "<error>";
 }
 
+static int sip_prune_realtime(int fd, int argc, char *argv[])
+{
+	struct sip_peer *peer;
+
+	if (argc != 4)
+        return RESULT_SHOWUSAGE;
+	if (!strcmp(argv[3],"all")) {
+		sip_do_reload();
+		ast_cli(fd, "OK Cache is flushed.\n");
+	} else if ((peer = find_peer(argv[3], NULL, 0))) {
+		if(ast_test_flag((&peer->flags_page2), SIP_PAGE2_RTCACHEFRIENDS)) {
+			ast_set_flag((&peer->flags_page2), SIP_PAGE2_RTAUTOCLEAR);
+			expire_register(peer);
+			ast_cli(fd, "OK peer %s was removed from the cache.\n", argv[3]);
+		} else {
+			ast_cli(fd, "SORRY peer %s is not eligible for this operation.\n", argv[3]);
+		}
+	} else {
+		ast_cli(fd, "SORRY peer %s was not found in the cache.\n", argv[3]);
+	}
+	
+	return RESULT_SUCCESS;
+}
+
 /*--- sip_show_peer: Show one peer in detail ---*/
 static int sip_show_peer(int fd, int argc, char *argv[])
 {
@@ -6061,11 +6111,13 @@
 	struct sip_peer *peer;
 	char codec_buf[512];
 	struct ast_codec_pref *pref;
-	int x = 0, codec = 0;
+	int x = 0, codec = 0, load_realtime = 0;
 
-	if (argc != 4)
+	if (argc < 4)
 		return RESULT_SHOWUSAGE;
-	peer = find_peer(argv[3], NULL);
+
+	load_realtime = (argc == 5 && !strcmp(argv[4], "load")) ? 1 : 0;
+	peer = find_peer(argv[3], NULL, load_realtime);
 	if (peer) {
 		ast_cli(fd,"\n\n");
 		ast_cli(fd, "  * Name       : %s\n", peer->name);
@@ -6531,7 +6583,7 @@
 	char iabuf[INET_ADDRSTRLEN];
 	if (argc != 4)
 		return RESULT_SHOWUSAGE;
-	peer = find_peer(argv[3], NULL);
+	peer = find_peer(argv[3], NULL, 1);
 	if (peer) {
 		if (peer->addr.sin_addr.s_addr) {
 			debugaddr.sin_family = AF_INET;
@@ -6876,6 +6928,10 @@
 "Usage: sip show peer <peername>\n"
 "       Lists all details on one SIP peer and the current status.\n";
 
+static char prune_realtime_usage[] =
+"Usage: sip prune realtime [<peername>|all]\n"
+"       Prunes object(s) from the cache\n";
+
 static char show_reg_usage[] =
 "Usage: sip show registry\n"
 "       Lists all registration requests and status.\n";
@@ -6914,6 +6970,9 @@
 "Usage: sip show objects\n" 
 "       Shows status of known SIP objects\n";
 
+
+
+
 static struct ast_cli_entry  cli_notify =
 	{ { "sip", "notify", NULL }, sip_notify, "Send a notify packet to a SIP peer", notify_usage, complete_sipnotify };
 static struct ast_cli_entry  cli_show_objects = 
@@ -6936,6 +6995,8 @@
 	{ { "sip", "show", "peer", NULL }, sip_show_peer, "Show details on specific SIP peer", show_peer_usage, complete_sip_show_peer };
 static struct ast_cli_entry  cli_show_peers =
 	{ { "sip", "show", "peers", NULL }, sip_show_peers, "Show defined SIP peers", show_peers_usage };
+static struct ast_cli_entry  cli_prune_realtime =
+	{ { "sip", "prune", "realtime", NULL }, sip_prune_realtime, "Prune a cached realtime lookup", prune_realtime_usage, complete_sip_show_peer };
 static struct ast_cli_entry  cli_inuse_show =
 	{ { "sip", "show", "inuse", NULL }, sip_show_inuse, "List all inuse/limit", show_inuse_usage };
 static struct ast_cli_entry  cli_show_registry =
@@ -8513,7 +8574,7 @@
 		ext = NULL;
 	}
 
-	p = find_peer(host, NULL);
+	p = find_peer(host, NULL, 1);
 	if (p) {
 		found++;
 		res = AST_DEVICE_UNAVAILABLE;
@@ -9132,6 +9193,12 @@
 			strncpy(default_useragent, v->value, sizeof(default_useragent)-1);
 			ast_log(LOG_DEBUG, "Setting User Agent Name to %s\n",
 				default_useragent);
+		} else if (!strcasecmp(v->name, "rtcachefriends")) {
+			ast_set2_flag((&global_flags_page2), ast_true(v->value), SIP_PAGE2_RTCACHEFRIENDS);	
+		} else if (!strcasecmp(v->name, "rtnoupdate")) {
+			ast_set2_flag((&global_flags_page2), ast_true(v->value), SIP_PAGE2_RTNOUPDATE);	
+		} else if (!strcasecmp(v->name, "rtautoclear")) {
+			ast_set2_flag((&global_flags_page2), ast_true(v->value), SIP_PAGE2_RTAUTOCLEAR);
 		} else if (!strcasecmp(v->name, "usereqphone")) {
 			ast_set2_flag((&global_flags), ast_true(v->value), SIP_USEREQPHONE);	
 		} else if (!strcasecmp(v->name, "relaxdtmf")) {
@@ -9705,6 +9772,7 @@
 		ast_cli_register(&cli_show_channels);
 		ast_cli_register(&cli_show_channel);
 		ast_cli_register(&cli_show_history);
+		ast_cli_register(&cli_prune_realtime);
 		ast_cli_register(&cli_show_peer);
 		ast_cli_register(&cli_show_peers);
 		ast_cli_register(&cli_show_registry);
@@ -9744,6 +9812,7 @@
 	ast_cli_unregister(&cli_show_channels);
 	ast_cli_unregister(&cli_show_channel);
 	ast_cli_unregister(&cli_show_history);
+	ast_cli_unregister(&cli_prune_realtime);
 	ast_cli_unregister(&cli_show_peer);
 	ast_cli_unregister(&cli_show_peers);
 	ast_cli_unregister(&cli_show_registry);
