Re: [PATCH 2/2] Don't call sync_* funcs for unloaded services

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Reviewed-by: Steven Dake <sdake@xxxxxxxxxx>

On 08/01/2012 08:14 AM, Jan Friesse wrote:
> When service is unloaded, sync shouldn't call sync_init|process|activate
> and abort functions. It happens very rare, but in process of unloading
> all services, totem can recreate membership and bad things can happen
> (service is unloaded, so there may be access to already freed memory,
>  ...)
> 
> Solution is to fetch services sync handlers in every time when we are
> building service list instead of using precreated one.
> 
> Signed-off-by: Jan Friesse <jfriesse@xxxxxxxxxx>
> ---
>  exec/sync.c |   64 +++++++++++++++++++++++++++++-----------------------------
>  1 files changed, 32 insertions(+), 32 deletions(-)
> 
> diff --git a/exec/sync.c b/exec/sync.c
> index f9f8cb4..b09ea53 100644
> --- a/exec/sync.c
> +++ b/exec/sync.c
> @@ -149,10 +149,6 @@ static int my_service_list_entries = 0;
>  
>  static const struct memb_ring_id sync_ring_id;
>  
> -static struct service_entry my_initial_service_list[SERVICES_COUNT_MAX];
> -
> -static int my_initial_service_list_entries;
> -
>  static void (*sync_synchronization_completed) (void);
>  
>  static void sync_deliver_fn (
> @@ -172,6 +168,10 @@ static struct totempg_group sync_group = {
>  
>  static void *sync_group_handle;
>  
> +int (*my_sync_callbacks_retrieve) (
> +		int service_id,
> +                struct sync_callbacks *callbacks);
> +
>  int sync_init (
>          int (*sync_callbacks_retrieve) (
>                  int service_id,
> @@ -179,8 +179,6 @@ int sync_init (
>          void (*synchronization_completed) (void))
>  {
>  	unsigned int res;
> -	int i;
> -	struct sync_callbacks sync_callbacks;
>  
>  	res = totempg_groups_initialize (
>  		&sync_group_handle,
> @@ -202,25 +200,8 @@ int sync_init (
>  	}
>  
>  	sync_synchronization_completed = synchronization_completed;
> -	for (i = 0; i < SERVICES_COUNT_MAX; i++) {
> -		res = sync_callbacks_retrieve (i, &sync_callbacks);
> -		if (res == -1) {
> -			continue;
> -		}
> -		if (sync_callbacks.sync_init == NULL) {
> -			continue;
> -		}
> -		my_initial_service_list[my_initial_service_list_entries].state =
> -			INIT;
> -		my_initial_service_list[my_initial_service_list_entries].service_id = i;
> -		strcpy (my_initial_service_list[my_initial_service_list_entries].name,
> -			sync_callbacks.name);
> -		my_initial_service_list[my_initial_service_list_entries].sync_init = sync_callbacks.sync_init;
> -		my_initial_service_list[my_initial_service_list_entries].sync_process = sync_callbacks.sync_process;
> -		my_initial_service_list[my_initial_service_list_entries].sync_abort = sync_callbacks.sync_abort;
> -		my_initial_service_list[my_initial_service_list_entries].sync_activate = sync_callbacks.sync_activate;
> -		my_initial_service_list_entries += 1;
> -	}
> +	my_sync_callbacks_retrieve = sync_callbacks_retrieve;
> +
>  	return (0);
>  }
>  
> @@ -346,7 +327,7 @@ static void sync_service_build_handler (unsigned int nodeid, const void *msg)
>  			my_service_list[my_service_list_entries].service_id =
>  				req_exec_service_build_message->service_list[i];
>  			sprintf (my_service_list[my_service_list_entries].name,
> -				"External Service (id = %d)\n",
> +				"Uknown External Service (id = %d)\n",
>  				req_exec_service_build_message->service_list[i]);
>  			my_service_list[my_service_list_entries].sync_init =
>  				dummy_sync_init;
> @@ -491,6 +472,8 @@ static void sync_servicelist_build_enter (
>  {
>  	struct req_exec_service_build_message service_build;
>  	int i;
> +	int res;
> +	struct sync_callbacks sync_callbacks;
>  
>  	my_state = SYNC_SERVICELIST_BUILD;
>  	for (i = 0; i < member_list_entries; i++) {
> @@ -505,14 +488,31 @@ static void sync_servicelist_build_enter (
>  
>  	my_processing_idx = 0;
>  
> -	memcpy (my_service_list, my_initial_service_list,
> -		sizeof (struct service_entry) *
> -			my_initial_service_list_entries);
> -	my_service_list_entries = my_initial_service_list_entries;
> +	memset(my_service_list, 0, sizeof (struct service_entry) * SERVICES_COUNT_MAX);
> +	my_service_list_entries = 0;
> +
> +	for (i = 0; i < SERVICES_COUNT_MAX; i++) {
> +		res = my_sync_callbacks_retrieve (i, &sync_callbacks);
> +		if (res == -1) {
> +			continue;
> +		}
> +		if (sync_callbacks.sync_init == NULL) {
> +			continue;
> +		}
> +		my_service_list[my_service_list_entries].state = INIT;
> +		my_service_list[my_service_list_entries].service_id = i;
> +		strcpy (my_service_list[my_service_list_entries].name,
> +			sync_callbacks.name);
> +		my_service_list[my_service_list_entries].sync_init = sync_callbacks.sync_init;
> +		my_service_list[my_service_list_entries].sync_process = sync_callbacks.sync_process;
> +		my_service_list[my_service_list_entries].sync_abort = sync_callbacks.sync_abort;
> +		my_service_list[my_service_list_entries].sync_activate = sync_callbacks.sync_activate;
> +		my_service_list_entries += 1;
> +	}
>  
> -	for (i = 0; i < my_initial_service_list[i].service_id; i++) {
> +	for (i = 0; i < my_service_list[i].service_id; i++) {
>  		service_build.service_list[i] =
> -			my_initial_service_list[i].service_id;
> +			my_service_list[i].service_id;
>  	}
>  	service_build.service_list_entries = i;
>  
> 

_______________________________________________
discuss mailing list
discuss@xxxxxxxxxxxx
http://lists.corosync.org/mailman/listinfo/discuss


[Index of Archives]     [Linux Clusters]     [Corosync Project]     [Linux USB Devel]     [Linux Audio Users]     [Photo]     [Yosemite News]    [Yosemite Photos]    [Linux Kernel]     [Linux SCSI]     [X.Org]

  Powered by Linux