Related to https://bugzilla.redhat.com/show_bug.cgi?id=529424
Patch implements new callback with current totem ring id and members. Included is modified testcpg using functionality. As required, callback is delivered AFTER all normal confchg callbacks. Patch is not 100% tested (specially big endian issues and whitetank/older versions of corosync coexistence) but looks stable. David, fulfill that functionality your requirements? Regards, Honza
commit 41c960c0ab6ec8a51ce2ca8705b31d5fdfbc16da Author: Jan Friesse <[email protected]> Date: Mon Feb 22 17:54:16 2010 +0100 Cpg TOTEM ringid + members callback diff --git a/trunk/include/corosync/cpg.h b/trunk/include/corosync/cpg.h index b5609df..bbfcad7 100644 --- a/trunk/include/corosync/cpg.h +++ b/trunk/include/corosync/cpg.h @@ -98,6 +98,11 @@ struct cpg_iteration_description_t { uint32_t pid; }; +struct cpg_ring_id { + uint32_t nodeid; + uint64_t seq; +}; + typedef void (*cpg_deliver_fn_t) ( cpg_handle_t handle, const struct cpg_name *group_name, @@ -117,9 +122,16 @@ typedef void (*cpg_confchg_fn_t) ( const struct cpg_address *left_list, size_t left_list_entries, const struct cpg_address *joined_list, size_t joined_list_entries); +typedef void (*cpg_totem_confchg_fn_t) ( + cpg_handle_t handle, + struct cpg_ring_id ring_id, + uint32_t member_list_entries, + const uint32_t *member_list); + typedef struct { cpg_deliver_fn_t cpg_deliver_fn; cpg_confchg_fn_t cpg_confchg_fn; + cpg_totem_confchg_fn_t cpg_totem_confchg_fn; } cpg_callbacks_t; /** @} */ diff --git a/trunk/include/corosync/ipc_cpg.h b/trunk/include/corosync/ipc_cpg.h index 7df1891..77ff546 100644 --- a/trunk/include/corosync/ipc_cpg.h +++ b/trunk/include/corosync/ipc_cpg.h @@ -63,6 +63,7 @@ enum res_cpg_types { MESSAGE_RES_CPG_ITERATIONINITIALIZE = 9, MESSAGE_RES_CPG_ITERATIONNEXT = 10, MESSAGE_RES_CPG_ITERATIONFINALIZE = 11, + MESSAGE_RES_CPG_TOTEM_CONFCHG_CALLBACK = 12, }; enum lib_cpg_confchg_reason { @@ -147,6 +148,19 @@ static inline void marshall_from_mar_cpg_iteration_description_t( marshall_from_mar_cpg_name_t (&dest->group, &src->group); }; +typedef struct { + mar_uint32_t nodeid __attribute__((aligned(8))); + mar_uint64_t seq __attribute__((aligned(8))); +} mar_cpg_ring_id_t; + +static inline void marshall_from_mar_cpg_ring_id_t ( + struct cpg_ring_id *dest, + const mar_cpg_ring_id_t *src) +{ + dest->nodeid = src->nodeid; + dest->seq = src->seq; +} + struct req_lib_cpg_join { coroipc_request_header_t header __attribute__((aligned(8))); mar_cpg_name_t group_name __attribute__((aligned(8))); @@ -228,6 +242,13 @@ struct res_lib_cpg_confchg_callback { // struct cpg_address joined_list[]; }; +struct res_lib_cpg_totem_confchg_callback { + coroipc_response_header_t header __attribute__((aligned(8))); + mar_cpg_ring_id_t ring_id __attribute__((aligned(8))); + mar_uint32_t member_list_entries __attribute__((aligned(8))); + mar_uint32_t member_list[]; +}; + struct req_lib_cpg_leave { coroipc_request_header_t header __attribute__((aligned(8))); mar_cpg_name_t group_name __attribute__((aligned(8))); diff --git a/trunk/lib/cpg.c b/trunk/lib/cpg.c index 780e79f..c1b9244 100644 --- a/trunk/lib/cpg.c +++ b/trunk/lib/cpg.c @@ -256,6 +256,7 @@ cs_error_t cpg_dispatch ( struct cpg_inst *cpg_inst; struct res_lib_cpg_confchg_callback *res_cpg_confchg_callback; struct res_lib_cpg_deliver_callback *res_cpg_deliver_callback; + struct res_lib_cpg_totem_confchg_callback *res_cpg_totem_confchg_callback; cpg_callbacks_t callbacks; coroipc_response_header_t *dispatch_data; struct cpg_address member_list[CPG_MEMBERS_MAX]; @@ -265,6 +266,8 @@ cs_error_t cpg_dispatch ( mar_cpg_address_t *left_list_start; mar_cpg_address_t *joined_list_start; unsigned int i; + struct cpg_ring_id ring_id; + uint32_t totem_member_list[CPG_MEMBERS_MAX]; error = hdb_error_to_cs (hdb_handle_get (&cpg_handle_t_db, handle, (void *)&cpg_inst)); if (error != CS_OK) { @@ -367,6 +370,24 @@ cs_error_t cpg_dispatch ( res_cpg_confchg_callback->joined_list_entries); break; + case MESSAGE_RES_CPG_TOTEM_CONFCHG_CALLBACK: + if (callbacks.cpg_totem_confchg_fn == NULL) { + continue; + } + + res_cpg_totem_confchg_callback = (struct res_lib_cpg_totem_confchg_callback *)dispatch_data; + + marshall_from_mar_cpg_ring_id_t (&ring_id, &res_cpg_totem_confchg_callback->ring_id); + for (i = 0; i < res_cpg_totem_confchg_callback->member_list_entries; i++) { + totem_member_list[i] = res_cpg_totem_confchg_callback->member_list[i]; + } + + callbacks.cpg_totem_confchg_fn (handle, + ring_id, + res_cpg_totem_confchg_callback->member_list_entries, + totem_member_list); + break; + default: coroipcc_dispatch_put (cpg_inst->handle); error = CS_ERR_LIBRARY; @@ -900,5 +921,4 @@ error_put: error_exit: return (error); } - /** @} */ diff --git a/trunk/services/cpg.c b/trunk/services/cpg.c index 68bd1ed..202e3fd 100644 --- a/trunk/services/cpg.c +++ b/trunk/services/cpg.c @@ -160,6 +160,8 @@ static struct corosync_api_v1 *api = NULL; static enum cpg_sync_state my_sync_state = CPGSYNC_DOWNLIST; +static mar_cpg_ring_id_t last_sync_ring_id; + struct process_info { unsigned int nodeid; uint32_t pid; @@ -253,6 +255,10 @@ static void cpg_sync_activate (void); static void cpg_sync_abort (void); +static int notify_lib_totem_membership ( + int member_list_entries, + const unsigned int *member_list); + /* * Library Handler Definition */ @@ -426,6 +432,9 @@ static void cpg_sync_init_v2 ( sizeof (unsigned int)); my_member_list_entries = member_list_entries; + last_sync_ring_id.nodeid = ring_id->rep.nodeid; + last_sync_ring_id.seq = ring_id->seq; + for (i = 0; i < my_member_list_entries; i++) { if (my_member_list[i] < lowest_nodeid) { lowest_nodeid = my_member_list[i]; @@ -476,13 +485,45 @@ static void cpg_sync_activate (void) memcpy (my_old_member_list, my_member_list, my_member_list_entries * sizeof (unsigned int)); my_old_member_list_entries = my_member_list_entries; + + notify_lib_totem_membership (my_member_list_entries, my_member_list); } static void cpg_sync_abort (void) { } +static int notify_lib_totem_membership ( + int member_list_entries, + const unsigned int *member_list) +{ + struct list_head *iter; + char *buf; + int size; + struct res_lib_cpg_totem_confchg_callback *res; + size = sizeof(struct res_lib_cpg_totem_confchg_callback) + + sizeof(mar_uint32_t) * (member_list_entries); + buf = alloca(size); + if (!buf) + return CPG_ERR_LIBRARY; + + res = (struct res_lib_cpg_totem_confchg_callback *)buf; + res->member_list_entries = member_list_entries; + res->header.size = size; + res->header.id = MESSAGE_RES_CPG_TOTEM_CONFCHG_CALLBACK; + res->header.error = CS_OK; + + memcpy (&res->ring_id, &last_sync_ring_id, sizeof (mar_cpg_ring_id_t)); + memcpy (res->member_list, member_list, res->member_list_entries * sizeof (mar_uint32_t)); + + for (iter = cpg_pd_list_head.next; iter != &cpg_pd_list_head; iter = iter->next) { + struct cpg_pd *cpg_pd = list_entry (iter, struct cpg_pd, list); + api->ipc_dispatch_send (cpg_pd->conn, buf, size); + } + + return CPG_OK; +} static int notify_lib_joinlist( const mar_cpg_name_t *group_name, diff --git a/trunk/test/testcpg.c b/trunk/test/testcpg.c index c9fe79d..40f21c2 100644 --- a/trunk/test/testcpg.c +++ b/trunk/test/testcpg.c @@ -132,9 +132,28 @@ static void ConfchgCallback ( } } +static void TotemConfchgCallback ( + cpg_handle_t handle, + struct cpg_ring_id ring_id, + uint32_t member_list_entries, + const uint32_t *member_list) +{ + int i; + + printf("\nTotemConfchgCallback: ringid (%u.%llu)\n", ring_id.nodeid, ring_id.seq); + + printf("nodes in group now %lu\n", + (unsigned long int) member_list_entries); + for (i=0; i<member_list_entries; i++) { + printf("%d ", member_list[i]); + } + printf ("\n"); +} + static cpg_callbacks_t callbacks = { .cpg_deliver_fn = DeliverCallback, .cpg_confchg_fn = ConfchgCallback, + .cpg_totem_confchg_fn = TotemConfchgCallback, }; static void sigintr_handler (int signum) __attribute__((__noreturn__));
_______________________________________________ Openais mailing list [email protected] https://lists.linux-foundation.org/mailman/listinfo/openais
