[svn-commits] mmichelson: branch group/CCSS_Monitor_Restructure r242810 - /team/group/CCSS_...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Mon Jan 25 10:01:16 CST 2010


Author: mmichelson
Date: Mon Jan 25 10:01:11 2010
New Revision: 242810

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=242810
Log:
Make monitors refcounted for safety reasons.

Most importantly are the ast_cc_get_monitor_by_recall_core_id
and the scheduler interaction.

My next step is to fix up chan_sip so that it conforms to the
new restructuring. After that will be a lot of testing.


Modified:
    team/group/CCSS_Monitor_Restructure/main/ccss.c

Modified: team/group/CCSS_Monitor_Restructure/main/ccss.c
URL: http://svnview.digium.com/svn/asterisk/team/group/CCSS_Monitor_Restructure/main/ccss.c?view=diff&rev=242810&r1=242809&r2=242810
==============================================================================
--- team/group/CCSS_Monitor_Restructure/main/ccss.c (original)
+++ team/group/CCSS_Monitor_Restructure/main/ccss.c Mon Jan 25 10:01:11 2010
@@ -1056,7 +1056,7 @@
 		ast_get_ccnr_available_timer(monitor->interface->config_params);
 
 	*available_timer_id = ast_sched_thread_add(cc_sched_thread, when * 1000,
-			ast_cc_available_timer_expire, monitor);
+			ast_cc_available_timer_expire, cc_ref(monitor, "Give the scheduler a monitor reference"));
 	cc_unref(generic_list, "Finished with monitor instance reference in request cc callback");
 	return 0;
 }
@@ -1169,8 +1169,9 @@
 	ast_cc_config_params_destroy(interface->config_params);
 }
 
-static void cc_monitor_destroy(struct ast_cc_monitor *monitor)
-{
+static void cc_monitor_destroy(void *data)
+{
+	struct ast_cc_monitor *monitor = data;
 	/* During the monitor creation process, it is possible for this
 	 * function to be called prior to when callbacks are assigned
 	 * to the monitor. Also, extension monitors do not have callbacks
@@ -1183,7 +1184,6 @@
 	}
 	cc_unref(monitor->interface, "Unreffing tree's reference to interface");
 	ast_free(monitor->dialable_name);
-	ast_free(monitor);
 }
 
 static void cc_interface_tree_destroy(void *data)
@@ -1191,7 +1191,7 @@
 	struct ast_cc_interface_tree *cc_interface_tree = data;
 	struct ast_cc_monitor *monitor;
 	while ((monitor = AST_DLLIST_REMOVE_HEAD(cc_interface_tree, next))) {
-		cc_monitor_destroy(monitor);
+		cc_unref(monitor, "Destroying all monitors");
 	}
 	AST_DLLIST_HEAD_DESTROY(cc_interface_tree);
 }
@@ -1371,7 +1371,7 @@
 		return NULL;
 	}
 
-	if (!(monitor = ast_calloc(1, sizeof(*monitor)))) {
+	if (!(monitor = ao2_alloc(sizeof(*monitor), cc_monitor_destroy))) {
 		ao2_t_ref(cc_interface, -1, "failed to allocate the tree item, so unref the interface");
 		return NULL;
 	}
@@ -1428,7 +1428,7 @@
 	}
 
 	if (!(dial_cc_datastore = ast_datastore_alloc(&dialed_cc_interfaces_info, NULL))) {
-		cc_monitor_destroy(monitor);
+		cc_unref(monitor, "Could not allocate the dialed interfaces datastore. Unreffing monitor");
 		ast_free(interfaces);
 		return -1;
 	}
@@ -1436,7 +1436,7 @@
 	if (!(interfaces->interface_tree = ao2_t_alloc(sizeof(*interfaces->interface_tree), cc_interface_tree_destroy,
 					"Allocate interface tree"))) {
 		ast_datastore_free(dial_cc_datastore);
-		cc_monitor_destroy(monitor);
+		cc_unref(monitor, "Could not allocate interface tree on dialed interfaces datastore. Unreffing monitor");
 		ast_free(interfaces);
 		return -1;
 	}
@@ -1444,6 +1444,7 @@
 	/* Finally, all that allocation is done... */
 	AST_DLLIST_HEAD_INIT(interfaces->interface_tree);
 	AST_DLLIST_INSERT_TAIL(interfaces->interface_tree, monitor, next);
+	cc_ref(monitor, "List's reference to extension monitor");
 	dial_cc_datastore->data = interfaces;
 	dial_cc_datastore->inheritance = DATASTORE_INHERIT_FOREVER;
 	interfaces->dial_parent_id = monitor->id;
@@ -1452,6 +1453,7 @@
 	ast_channel_lock(chan);
 	ast_channel_datastore_add(chan, dial_cc_datastore);
 	ast_channel_unlock(chan);
+	cc_unref(monitor, "Unreffing allocation's reference");
 	return 0;
 }
 
@@ -1532,7 +1534,7 @@
 		return NULL;
 	}
 
-	if (!(monitor = ast_calloc(1, sizeof(*monitor)))) {
+	if (!(monitor = ao2_alloc(sizeof(*monitor), cc_monitor_destroy))) {
 		ao2_t_ref(cc_interface, -1, "Failed to allocate tree item, unref interface");
 		call_destructor_with_no_monitor(cc_data->monitor_type, cc_data->private_data);
 		return NULL;
@@ -1540,14 +1542,14 @@
 
 	if (!(monitor->dialable_name = ast_strdup(dialable_name))) {
 		ao2_t_ref(cc_interface, -1, "Failed to copy dialable name");
-		cc_monitor_destroy(monitor);
+		cc_unref(monitor, "Failed to copy dialable name. Unref monitor");
 		call_destructor_with_no_monitor(cc_data->monitor_type, cc_data->private_data);
 		return NULL;
 	}
 
 	if (!(monitor->callbacks = find_monitor_callbacks(cc_data->monitor_type))) {
 		ao2_t_ref(cc_interface, -1, "Failed to find monitor callbacks\n");
-		cc_monitor_destroy(monitor);
+		cc_unref(monitor, "Failed to find monitor callbacks. Unref monitor");
 		call_destructor_with_no_monitor(cc_data->monitor_type, cc_data->private_data);
 		return NULL;
 	}
@@ -1664,6 +1666,7 @@
 
 	AST_DLLIST_LOCK(cc_interfaces->interface_tree);
 	AST_DLLIST_INSERT_TAIL(cc_interfaces->interface_tree, monitor, next);
+	cc_ref(monitor, "Interface tree's reference to the monitor");
 	AST_DLLIST_UNLOCK(cc_interfaces->interface_tree);
 
 	manager_event(EVENT_FLAG_CC, "CCAvailable",
@@ -1674,6 +1677,7 @@
 	);
 
 	cc_unref(core_instance, "Done with core_instance after handling CC control frame");
+	cc_unref(monitor, "Unref reference from allocating monitor");
 }
 
 int ast_cc_call_init(struct ast_channel *chan, int *ignore_cc)
@@ -1738,8 +1742,10 @@
 	monitor->dialable_name = ast_strdup(interfaces->current_extension_dialable_name);
 	AST_DLLIST_LOCK(interfaces->interface_tree);
 	AST_DLLIST_INSERT_TAIL(interfaces->interface_tree, monitor, next);
+	cc_ref(monitor, "Interface tree's reference to the monitor");
 	AST_DLLIST_UNLOCK(interfaces->interface_tree);
 	interfaces->dial_parent_id = monitor->id;
+	cc_unref(monitor, "Unref monitor's allocation reference");
 	return 0;
 }
 
@@ -2297,7 +2303,8 @@
 		if (monitor_iter->interface->monitor_class == AST_CC_DEVICE_MONITOR) {
 			if (monitor_iter->callbacks->request_cc(monitor_iter, &monitor_iter->available_timer_id)) {
 				AST_DLLIST_REMOVE_CURRENT(next);
-				cc_monitor_destroy(monitor_iter);
+				cc_unref(monitor_iter, "request_cc failed. Unref list's reference to monitor");
+				cc_unref(monitor_iter, "request_cc failed. Unref local reference to monitor");
 			} else {
 				manager_event(EVENT_FLAG_CC, "CCRequestSent",
 					"CoreID: %d\r\n"
@@ -2307,7 +2314,8 @@
 			}
 		} else if (!has_children(monitor_iter)) {
 			AST_DLLIST_REMOVE_CURRENT(next);
-			cc_monitor_destroy(monitor_iter);
+			cc_unref(monitor_iter, "request_cc failed on all children. Unref list's reference to monitor");
+			cc_unref(monitor_iter, "request_cc failed on all children. Unref local reference to monitor");
 		}
 	}
 	AST_DLLIST_TRAVERSE_BACKWARDS_SAFE_END;
@@ -2343,11 +2351,13 @@
 		if (monitor_iter->interface->monitor_class == AST_CC_DEVICE_MONITOR) {
 			if (monitor_iter->callbacks->unsuspend(monitor_iter)) {
 				AST_DLLIST_REMOVE_CURRENT(next);
-				cc_monitor_destroy(monitor_iter);
+				cc_unref(monitor_iter, "unsuspend failed. Unref list's reference to monitor");
+				cc_unref(monitor_iter, "unsuspend failed. Unref local reference to monitor");
 			}
 		} else if (!has_children(monitor_iter)) {
 			AST_DLLIST_REMOVE_CURRENT(next);
-			cc_monitor_destroy(monitor_iter);
+			cc_unref(monitor_iter, "unsuspend failed on all children. Unref list's reference to monitor");
+			cc_unref(monitor_iter, "unsuspend failed on all children. Unref local reference to monitor");
 		}
 	}
 	AST_DLLIST_TRAVERSE_BACKWARDS_SAFE_END;
@@ -2394,13 +2404,15 @@
 		if (monitor_iter->interface->monitor_class == AST_CC_DEVICE_MONITOR) {
 			if (monitor_iter->callbacks->suspend(monitor_iter)) {
 				AST_DLLIST_REMOVE_CURRENT(next);
-				cc_monitor_destroy(monitor_iter);
+				cc_unref(monitor_iter, "suspend failed. Unref list's reference to monitor");
+				cc_unref(monitor_iter, "suspend failed. Unref local reference to monitor");
 			} else {
 				monitor_iter->is_suspended = 1;
 			}
 		} else if (!has_children(monitor_iter)) {
 			AST_DLLIST_REMOVE_CURRENT(next);
-			cc_monitor_destroy(monitor_iter);
+			cc_unref(monitor_iter, "suspend failed on all children. Unref list's reference to monitor");
+			cc_unref(monitor_iter, "suspend failed on all children. Unref local reference to monitor");
 		}
 	}
 	AST_DLLIST_TRAVERSE_BACKWARDS_SAFE_END;
@@ -2433,11 +2445,13 @@
 		if (monitor_iter->interface->monitor_class == AST_CC_DEVICE_MONITOR) {
 			if (monitor_iter->callbacks->cancel_available_timer(monitor_iter, &monitor_iter->available_timer_id)) {
 				AST_DLLIST_REMOVE_CURRENT(next);
-				cc_monitor_destroy(monitor_iter);
+				cc_unref(monitor_iter, "cancel_available_timer failed. Unref list's reference to monitor");
+				cc_unref(monitor_iter, "cancel_available_timer failed. Unref local reference to monitor");
 			}
 		} else if (!has_children(monitor_iter)) {
 			AST_DLLIST_REMOVE_CURRENT(next);
-			cc_monitor_destroy(monitor_iter);
+			cc_unref(monitor_iter, "cancel_available_timer failed on all children. Unref list's reference to monitor");
+			cc_unref(monitor_iter, "cancel_available_timer failed on all children. Unref local reference to monitor");
 		}
 	}
 	AST_DLLIST_TRAVERSE_BACKWARDS_SAFE_END;
@@ -2708,7 +2722,7 @@
 		}
 	}
 	AST_DLLIST_UNLOCK(core_instance->monitors);
-	return monitor_iter;
+	return cc_ref(monitor_iter, "Hand the requester of the monitor a reference");
 }
 
 int ast_cc_agent_set_interfaces_chanvar(struct ast_channel *chan, struct ast_cc_agent *agent)
@@ -2942,11 +2956,13 @@
 			if (!strcmp(monitor_iter->interface->name, failure_data->device_name) &&
 					!strcmp(monitor_iter->interface->monitor_type, failure_data->monitor_type)) {
 				AST_DLLIST_REMOVE_CURRENT(next);
-				cc_monitor_destroy(monitor_iter);
+				cc_unref(monitor_iter, "Monitor reported failure. Unref list's reference.");
+				cc_unref(monitor_iter, "Monitor reported failure. Unref local reference.");
 			}
 		} else if (!has_children(monitor_iter)) {
 			AST_DLLIST_REMOVE_CURRENT(next);
-			cc_monitor_destroy(monitor_iter);
+			cc_unref(monitor_iter, "All of monitor's children reported failure. Unref list's reference.");
+			cc_unref(monitor_iter, "All of monitor's children reported failure. Unref local reference.");
 		}
 	}
 	AST_DLLIST_TRAVERSE_BACKWARDS_SAFE_END;




More information about the svn-commits mailing list