Server IP : 104.21.38.3 / Your IP : 162.158.106.187 Web Server : Apache System : Linux krdc-ubuntu-s-2vcpu-4gb-amd-blr1-01.localdomain 5.15.0-142-generic #152-Ubuntu SMP Mon May 19 10:54:31 UTC 2025 x86_64 User : www ( 1000) PHP Version : 7.4.33 Disable Function : passthru,exec,system,putenv,chroot,chgrp,chown,shell_exec,popen,proc_open,pcntl_exec,ini_alter,ini_restore,dl,openlog,syslog,readlink,symlink,popepassthru,pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,imap_open,apache_setenv MySQL : OFF | cURL : ON | WGET : ON | Perl : ON | Python : OFF | Sudo : ON | Pkexec : ON Directory : /www/server/mysql/src/rapid/plugin/group_replication/libmysqlgcs/src/bindings/xcom/xcom/ |
Upload File : |
/* Copyright (c) 2015, 2023, Oracle and/or its affiliates. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License, version 2.0, as published by the Free Software Foundation. This program is also distributed with certain software (including but not limited to OpenSSL) that is licensed under separate terms, as designated in a particular file or component or in included license documentation. The authors of MySQL hereby grant you an additional permission to link the program and your derivative works with the separately licensed software that they have included with MySQL. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License, version 2.0, for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ #include <stdlib.h> #include <assert.h> #include "x_platform.h" #include "xcom_common.h" #include "xcom_vp.h" #include "node_list.h" #include "simset.h" #include "task.h" #include "server_struct.h" #include "xcom_detector.h" #include "site_struct.h" #include "xcom_base.h" #include "bitset.h" #include "xcom_memory.h" #include "synode_no.h" #include "node_no.h" #include "task_debug.h" #include "xcom_transport.h" #include "site_def.h" #include "node_set.h" typedef site_def *site_def_ptr; struct site_def_ptr_array { u_int count; u_int site_def_ptr_array_len; site_def_ptr *site_def_ptr_array_val; }; typedef struct site_def_ptr_array site_def_ptr_array; init_xdr_array(site_def_ptr) free_xdr_array(site_def_ptr) set_xdr_array(site_def_ptr) /* FIFO of site definitions */ static site_def_ptr_array site_defs; static site_def *incoming = 0; static inline node_no _get_maxnodes(site_def const *site); /* purecov: begin deadcode */ /* Save incoming site def, but do not make it available yet */ site_def *begin_site_def(site_def *s) { assert(!incoming); incoming = s; assert(s->global_node_set.node_set_len == _get_maxnodes(s)); return incoming; } /* Push saved site def, making it active from synode start */ site_def *end_site_def(synode_no start) { assert(incoming); incoming->start = start; return push_site_def(incoming); } /* purecov: end */ /* Rteurn pointer to array of site defs */ void get_all_site_defs(site_def ***s, uint32_t *n) { *s = site_defs.site_def_ptr_array_val; *n = site_defs.site_def_ptr_array_len; } /* Module initialization */ void init_site_vars() { init_site_def_ptr_array(&site_defs); site_defs.count = 0; incoming = 0; } /* Recursively free a complete site_def. Only free the site_def, not the servers that it points to, since servers are shared by multiple site_defs, and will eventually be deallocated by garbage_collect_servers */ void free_site_def(site_def *s) { if (s) { invalidate_detector_sites(s); xdr_free((xdrproc_t) xdr_node_list, (char *)(&s->nodes)); free_node_set(&s->global_node_set); free_node_set(&s->local_node_set); free(s); } } /* Free all resources in this module */ void free_site_defs() { u_int i; for(i = 0; i < site_defs.count; i++) { free_site_def(site_defs.site_def_ptr_array_val[i]); } free_site_def_ptr_array(&site_defs); site_defs.count = 0; free_site_def(incoming); } /* Add a new site definition to the list */ site_def *push_site_def(site_def *s) { uint32_t i; set_site_def_ptr(&site_defs, 0, site_defs.count); DBGOUT(FN; NDBG(site_defs.count,u); PTREXP(s); if (s) { SYCEXP(s->start); SYCEXP(s->boot_key); } ); for (i = site_defs.count; i > 0; i--) { DBGOUT(NDBG(i-1,d); PTREXP(site_defs.site_def_ptr_array_val[i-1]); if (site_defs.site_def_ptr_array_val[i-1]) { SYCEXP(site_defs.site_def_ptr_array_val[i-1]->start); SYCEXP(site_defs.site_def_ptr_array_val[i-1]->boot_key); } ); site_defs.site_def_ptr_array_val[i] = site_defs.site_def_ptr_array_val[i-1]; } set_site_def_ptr(&site_defs, s, 0); if(s){ s->x_proto = set_latest_common_proto(common_xcom_version(s)); G_DEBUG("latest common protocol is now %d",s->x_proto); } site_defs.count++; assert(!s || (s->global_node_set.node_set_len == _get_maxnodes(s))); return s; } /* Return first site def */ static inline site_def const *_get_site_def() { assert(site_defs.count == 0 || !site_defs.site_def_ptr_array_val[0] || site_defs.site_def_ptr_array_val[0]->global_node_set.node_set_len == _get_maxnodes(site_defs.site_def_ptr_array_val[0])); if (site_defs.count > 0) return site_defs.site_def_ptr_array_val[0]; else return 0; } /* Return first site def */ site_def *get_site_def_rw() { if (site_defs.count > 0) return site_defs.site_def_ptr_array_val[0]; else return 0; } /* purecov: begin deadcode */ /* Return previous site def */ static inline site_def const *_get_prev_site_def() { assert(site_defs.count == 0 || !site_defs.site_def_ptr_array_val[1] || site_defs.site_def_ptr_array_val[1]->global_node_set.node_set_len == _get_maxnodes(site_defs.site_def_ptr_array_val[1])); if (site_defs.count > 0) return site_defs.site_def_ptr_array_val[1]; else return 0; } /* purecov: end */ /* Return first site def */ site_def const *get_site_def() { return _get_site_def(); } /* purecov: begin deadcode */ /* Return previous site def */ site_def const *get_prev_site_def() { return _get_prev_site_def(); } /* purecov: end */ static inline int match_def(site_def const *site, synode_no synode) { return site && (synode.group_id == 0 || synode.group_id == site->start.group_id) && !synode_lt(synode, site->start); } /* Return first site def which has start less than or equal to synode */ site_def const *find_site_def(synode_no synode) { site_def const * retval = 0; u_int i; for(i = 0; i < site_defs.count; i++) if (match_def(site_defs.site_def_ptr_array_val[i], synode)){ retval = site_defs.site_def_ptr_array_val[i]; break; } assert(!retval || retval->global_node_set.node_set_len == _get_maxnodes(retval)); return retval; } /* As find_site_def, but return pointer to non-const object */ site_def *find_site_def_rw(synode_no synode) { site_def * retval = 0; u_int i; for(i = 0; i < site_defs.count; i++) if (match_def(site_defs.site_def_ptr_array_val[i], synode)){ retval = site_defs.site_def_ptr_array_val[i]; break; } assert(!retval || retval->global_node_set.node_set_len == _get_maxnodes(retval)); return retval; } void garbage_collect_site_defs(synode_no x) { u_int i; u_int s_max = site_defs.count; DBGOUT(FN; NDBG(site_defs.count, u); SYCEXP(x); ); for (i = 3; i < s_max; i++) { if (match_def(site_defs.site_def_ptr_array_val[i], x)) { break; } } i++; for (; i < s_max; i++) { site_def * site = site_defs.site_def_ptr_array_val[i]; DBGOUT(NDBG(i, d); PTREXP(site_defs.site_def_ptr_array_val[i]); ); if (site) { DBGOUT(SYCEXP(site->start); SYCEXP(site->boot_key); ); free_site_def(site); site_defs.site_def_ptr_array_val[i] = 0; } site_defs.count--; } } /* purecov: begin deadcode */ char *dbg_site_def(site_def const *site) { assert(site->global_node_set.node_set_len == _get_maxnodes(site)); return dbg_list(&site->nodes); } /* purecov: end */ /* Create a new empty site_def */ site_def *new_site_def() { site_def * retval = (site_def * ) calloc(1, sizeof(site_def)); retval->nodeno = VOID_NODE_NO; return retval; } /* {{{ Clone a site definition */ site_def *clone_site_def(site_def const *site) { site_def * retval = new_site_def(); assert(site->global_node_set.node_set_len == _get_maxnodes(site)); *retval = *site; init_node_list(site->nodes.node_list_len, site->nodes.node_list_val, &retval->nodes); retval->global_node_set = clone_node_set(site->global_node_set); retval->local_node_set = clone_node_set(site->local_node_set); assert(retval->global_node_set.node_set_len == _get_maxnodes(retval)); DBGOUT(FN; PTREXP(site); PTREXP(retval)); return retval; } /* }}} */ /* {{{ Initialize a site definition from array of string pointers */ void init_site_def(u_int n, node_address *names, site_def *site) { site->start = null_synode; site->boot_key = null_synode; site->nodeno = VOID_NODE_NO; init_detector(site->detected); init_node_list(n, names, &site->nodes); site->global_node_count = 0; alloc_node_set(&site->global_node_set, NSERVERS); site->global_node_set.node_set_len = site->nodes.node_list_len; set_node_set(&site->global_node_set); /* Assume everyone is there */ assert(site->global_node_set.node_set_len == _get_maxnodes(site)); alloc_node_set(&site->local_node_set, NSERVERS); site->local_node_set.node_set_len = site->nodes.node_list_len; set_node_set(&site->local_node_set); /* Assume everyone is there */ assert(site->local_node_set.node_set_len == _get_maxnodes(site)); site->detector_updated = 0; site->x_proto = my_xcom_version; } /* }}} */ /* Add nodes to site definition, avoid duplicates */ void add_site_def(u_int n, node_address *names, site_def *site) { if (n > 0) { add_node_list(n, names, &site->nodes); } realloc_node_set(&site->global_node_set, _get_maxnodes(site)); realloc_node_set(&site->local_node_set, _get_maxnodes(site)); } /* Remove nodes from site definition, ignore missing nodes */ void remove_site_def(u_int n, node_address *names, site_def *site) { if (n > 0) { remove_node_list(n, names, &site->nodes); } init_detector(site->detected); /* Zero all unused timestamps */ realloc_node_set(&site->global_node_set, _get_maxnodes(site)); realloc_node_set(&site->local_node_set, _get_maxnodes(site)); } /* purecov: begin deadcode */ /* Return boot_key of first site def */ synode_no get_boot_key() { assert(!_get_site_def() || _get_site_def()->global_node_set.node_set_len == _get_maxnodes(_get_site_def())); if (get_site_def()) { return get_site_def()->boot_key; } else { return null_synode; } } /* Set boot_key of first site def */ void set_boot_key(synode_no const x) { assert(_get_site_def()); assert(_get_site_def()->global_node_set.node_set_len == _get_maxnodes(_get_site_def())); if (site_defs.site_def_ptr_array_val[0]) { site_defs.site_def_ptr_array_val[0]->boot_key = x; } } /* purecov: end */ /* Return group id of site */ uint32_t get_group_id(site_def const *site) { if (site) { uint32_t group_id = site->start.group_id; assert(site->global_node_set.node_set_len == _get_maxnodes(site)); MAY_DBG(FN; NDBG(group_id, lx); ); return group_id; } else { return null_id; } } #if 0 void set_group_id(site_def *site, uint32_t id) { MAY_DBG(FN; STRLIT("changing group id from "); NDBG(get_group_id(site), lx); STRLIT("to "); NDBG(id, lu); ); site->group_id = id; } #endif static inline node_no _get_maxnodes(site_def const *site) { if (site) { return site->nodes.node_list_len; } else return 0; } /* Return maxnodes of site */ node_no get_maxnodes(site_def const *site) { return _get_maxnodes(site); } /* purecov: begin deadcode */ node_no get_prev_maxnodes() { return _get_maxnodes(_get_prev_site_def()); } /* purecov: end */ /* Return nodeno of site */ static inline node_no _get_nodeno(site_def const *site) { if (site) { assert(site->global_node_set.node_set_len == _get_maxnodes(site)); return site->nodeno; } else return VOID_NODE_NO; } /* purecov: begin deadcode */ /* Return nodeno of site */ node_no get_nodeno(site_def const *site) { return _get_nodeno(site); } /* purecov: end */ node_no get_prev_nodeno() { return _get_nodeno(_get_prev_site_def()); } void import_config(gcs_snapshot *gcs_snap) { int i; DBGOUT(FN; SYCEXP(gcs_snap->log_start)); for (i = (int)gcs_snap->cfg.configs_len-1; i >= 0; i--) { config_ptr cp = gcs_snap->cfg.configs_val[i]; if (cp) { site_def * site = new_site_def(); DBGOUT(FN; SYCEXP(cp->start); SYCEXP(cp->boot_key)); init_site_def(cp->nodes.node_list_len, cp->nodes.node_list_val, site); site->start = cp->start; site->boot_key = cp->boot_key; site_install_action(site, app_type); } } } extern synode_no executed_msg; gcs_snapshot *export_config() { u_int i; gcs_snapshot *gcs_snap = calloc(1, sizeof(gcs_snapshot)); gcs_snap->cfg.configs_val = calloc(site_defs.count, sizeof(config_ptr)); gcs_snap->cfg.configs_len = site_defs.count; for (i = 0; i < site_defs.count; i++) { site_def *site = site_defs.site_def_ptr_array_val[i]; if(site) { config_ptr cp = calloc(1, sizeof(config)); init_node_list(site->nodes.node_list_len, site->nodes.node_list_val, &cp->nodes); cp->start = site->start; cp->boot_key = site->boot_key; DBGOUT(FN; SYCEXP(cp->start); SYCEXP(cp->boot_key)); gcs_snap->cfg.configs_val[i] = cp; } } gcs_snap->log_start = get_delivered_msg(); return gcs_snap; } /* Return the global minimum delivered message number, based on incoming gossip */ synode_no get_min_delivered_msg(site_def const *s) { u_int i; synode_no retval = null_synode; int init = 1; for (i = 0; i < s->nodes.node_list_len; i++) { if (s->servers[i]->detected + DETECTOR_LIVE_TIMEOUT > task_now()) { if (init) { init = 0; retval = s->delivered_msg[i]; } else { if (synode_lt(s->delivered_msg[i], retval)) { retval = s->delivered_msg[i]; } } } } DBGOUT(FN; SYCEXP(retval)); return retval; } /* Track the minimum delivered message numbers based on incoming messages */ void update_delivered(site_def *s, node_no node, synode_no msgno) { if(node < s->nodes.node_list_len){ s->delivered_msg[node] = msgno; DBGOUT(FN; SYCEXP(s->delivered_msg[node]); NDBG(node,u)); } }