diff options
author | Seppo Jaakola <seppo.jaakola@codership.com> | 2012-06-12 10:55:11 +0300 |
---|---|---|
committer | Seppo Jaakola <seppo.jaakola@codership.com> | 2012-06-12 10:55:11 +0300 |
commit | 33ffe0dd29b6564e49dde8b1abda914da4b2f178 (patch) | |
tree | d4ed7e628eb0b8bdf7be707261de9d862655211a | |
parent | 609388fcfd912c9c2cb03a92251469a25a781893 (diff) | |
download | mariadb-git-33ffe0dd29b6564e49dde8b1abda914da4b2f178.tar.gz |
References lp:1011983
Merged from codership-mysql/5.5 changes revisions 3743-3756
-rw-r--r-- | cmake/wsrep.cmake | 2 | ||||
-rw-r--r-- | scripts/mysqld_safe.sh | 39 | ||||
-rw-r--r-- | sql/log_event.cc | 6 | ||||
-rw-r--r-- | sql/mysqld.cc | 23 | ||||
-rw-r--r-- | sql/sql_parse.cc | 8 | ||||
-rw-r--r-- | sql/wsrep_hton.cc | 11 | ||||
-rw-r--r-- | sql/wsrep_mysqld.cc | 12 | ||||
-rw-r--r-- | sql/wsrep_mysqld.h | 4 | ||||
-rw-r--r-- | sql/wsrep_sst.cc | 26 | ||||
-rw-r--r-- | storage/innobase/handler/ha_innodb.cc | 30 | ||||
-rw-r--r-- | storage/innobase/include/rem0rec.h | 3 | ||||
-rw-r--r-- | storage/innobase/rem/rem0rec.c | 46 | ||||
-rw-r--r-- | storage/xtradb/handler/ha_innodb.cc | 30 | ||||
-rw-r--r-- | storage/xtradb/include/rem0rec.h | 3 | ||||
-rw-r--r-- | storage/xtradb/rem/rem0rec.c | 46 |
15 files changed, 236 insertions, 53 deletions
diff --git a/cmake/wsrep.cmake b/cmake/wsrep.cmake index 1fd747cddd6..3c10c5b3836 100644 --- a/cmake/wsrep.cmake +++ b/cmake/wsrep.cmake @@ -17,7 +17,7 @@ # so WSREP_VERSION is produced regardless # Set the patch version -SET(WSREP_PATCH_VERSION "5") +SET(WSREP_PATCH_VERSION "6") # Obtain patch revision number SET(WSREP_PATCH_REVNO $ENV{WSREP_REV}) diff --git a/scripts/mysqld_safe.sh b/scripts/mysqld_safe.sh index aaf1936afe1..5a390a32f26 100644 --- a/scripts/mysqld_safe.sh +++ b/scripts/mysqld_safe.sh @@ -63,6 +63,7 @@ Usage: $0 [OPTIONS] --syslog Log messages to syslog with 'logger' --skip-syslog Log messages to error log (default) --syslog-tag=TAG Pass -t "mysqld-TAG" to 'logger' + --wsrep-urls=WSREP_URLS Comma-separated list of wsrep URLs All other options are passed to the mysqld program. @@ -161,6 +162,34 @@ shell_quote_string() { echo "$1" | sed -e 's,\([^a-zA-Z0-9/_.=-]\),\\\1,g' } +wsrep_pick_url() { + [ $# -eq 0 ] && return 0 + + if ! which nc >/dev/null; then + log_error "ERROR: nc tool not found in PATH! Make sure you have it installed." + return 1 + fi + + local url + # Assuming URL in the form scheme://host:port + # If host and port are not NULL, the liveness of URL is assumed to be tested + # If port part is absent, the url is returned literally and unconditionally + # If every URL has port but none is reachable, nothing is returned + for url in `echo $@ | sed s/,/\ /g` 0; do + local host=`echo $url | cut -d \: -f 2 | sed s/^\\\/\\\///` + local port=`echo $url | cut -d \: -f 3` + [ -z "$port" ] && break + nc -z "$host" $port >/dev/null && break + done + + if [ "$url" == "0" ]; then + log_error "ERROR: none of the URLs in '$@' is reachable." + return 1 + fi + + echo $url +} + parse_arguments() { # We only need to pass arguments through to the server if we don't # handle them here. So, we collect unrecognized options (passed on @@ -221,6 +250,7 @@ parse_arguments() { --skip-syslog) want_syslog=0 ;; --syslog-tag=*) syslog_tag="$val" ;; --timezone=*) TZ="$val"; export TZ; ;; + --wsrep[-_]urls=*) wsrep_urls="$val"; ;; --help) usage ;; @@ -772,9 +802,16 @@ while true do rm -f $safe_mysql_unix_port "$pid_file" # Some extra safety + [ -n "$wsrep_urls" ] && url=`wsrep_pick_url $wsrep_urls` # check connect address + start_time=`date +%M%S` - eval_log_error "$cmd" + if [ -z "$url" ] + then + eval_log_error "$cmd" + else + eval_log_error "$cmd --wsrep_cluster_address=$url" + fi end_time=`date +%M%S` diff --git a/sql/log_event.cc b/sql/log_event.cc index 1536d9e899b..ccfa1ae73e2 100644 --- a/sql/log_event.cc +++ b/sql/log_event.cc @@ -9237,8 +9237,12 @@ check_table_map(Relay_log_info const *rli, RPL_TABLE_LIST *table_list) { DBUG_ENTER("check_table_map"); enum_tbl_map_status res= OK_TO_PROCESS; - +#ifdef WITH_WSREP + if ((rli->sql_thd->slave_thread /* filtering is for slave only */ || + (WSREP(rli->sql_thd) && rli->sql_thd->wsrep_applier)) && +#else if (rli->sql_thd->slave_thread /* filtering is for slave only */ && +#endif /* WITH_WSREP */ (!rpl_filter->db_ok(table_list->db) || (rpl_filter->is_on() && !rpl_filter->tables_ok("", table_list)))) res= FILTERED_OUT; diff --git a/sql/mysqld.cc b/sql/mysqld.cc index ec6219b978f..a88e76972e4 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -4857,6 +4857,17 @@ WSREP_WARN("applier has wsrep_exec_mode = %d", thd->wsrep_exec_mode); #endif /* REMOVE */ } +static inline bool is_replaying_connection(THD *thd) +{ + bool ret; + + mysql_mutex_lock(&thd->LOCK_wsrep_thd); + ret= (thd->wsrep_conflict_state == REPLAYING) ? true : false; + mysql_mutex_unlock(&thd->LOCK_wsrep_thd); + + return ret; +} + static bool have_client_connections() { THD *tmp; @@ -4932,6 +4943,12 @@ void wsrep_close_client_connections(my_bool wait_to_end) if (!is_client_connection(tmp)) continue; + if (is_replaying_connection(tmp)) + { + tmp->killed= KILL_CONNECTION; + continue; + } + /* replicated transactions must be skipped */ if (abort_replicated(tmp)) continue; @@ -4953,9 +4970,11 @@ void wsrep_close_client_connections(my_bool wait_to_end) while ((tmp=it2++)) { #ifndef __bsdi__ // Bug in BSDI kernel - if (is_client_connection(tmp) && !abort_replicated(tmp)) + if (is_client_connection(tmp) && + !abort_replicated(tmp) && + !is_replaying_connection(tmp)) { - WSREP_INFO("SST kill local trx: %ld",tmp->thread_id); + WSREP_INFO("killing local connection: %ld",tmp->thread_id); close_connection(tmp,0,0); } #endif diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index b4b7eb0b2cf..cce1aaf05d4 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -8304,14 +8304,6 @@ void wsrep_replication_process(THD *thd) mysql_cond_broadcast(&COND_thread_count); mysql_mutex_unlock(&LOCK_thread_count); } - - if (thd->killed != KILL_CONNECTION) - { - mysql_mutex_lock(&LOCK_thread_count); - wsrep_close_applier(thd); - mysql_cond_broadcast(&COND_thread_count); - mysql_mutex_unlock(&LOCK_thread_count); - } wsrep_return_from_bf_mode(thd, &shadow); DBUG_VOID_RETURN; } diff --git a/sql/wsrep_hton.cc b/sql/wsrep_hton.cc index bb5faafc768..49b3ea5c0bf 100644 --- a/sql/wsrep_hton.cc +++ b/sql/wsrep_hton.cc @@ -305,8 +305,15 @@ wsrep_run_wsrep_commit( thd->stmt_da->affected_rows() > 0 && !binlog_filter->is_on()) { - WSREP_WARN("empty rbr buffer, query: %s, affected rows: %llu", - thd->query(), thd->stmt_da->affected_rows()); + WSREP_DEBUG("empty rbr buffer, query: %s, " + "affected rows: %llu, " + "changed tables: %d, " + "sql_log_bin: %d, " + "wsrep status (%d %d %d)", + thd->query(), thd->stmt_da->affected_rows(), + stmt_has_updated_trans_table(thd), thd->variables.sql_log_bin, + thd->wsrep_exec_mode, thd->wsrep_query_state, + thd->wsrep_conflict_state); } else { diff --git a/sql/wsrep_mysqld.cc b/sql/wsrep_mysqld.cc index be2b8d7fa81..0bf0c2294d3 100644 --- a/sql/wsrep_mysqld.cc +++ b/sql/wsrep_mysqld.cc @@ -45,7 +45,7 @@ long long wsrep_max_ws_size = 1073741824LL; //max ws (RBR buffer) siz long wsrep_max_ws_rows = 65536; // max number of rows in ws int wsrep_to_isolation = 0; // # of active TO isolation threads my_bool wsrep_certify_nonPK = 1; // certify, even when no primary key -long wsrep_max_protocol_version = 1; // maximum protocol version to use +long wsrep_max_protocol_version = 2; // maximum protocol version to use ulong wsrep_forced_binlog_format = BINLOG_FORMAT_UNSPEC; my_bool wsrep_recovery = 0; // recovery my_bool wsrep_replicate_myisam = 0; // enable myisam replication @@ -90,7 +90,7 @@ const char* wsrep_provider_vendor = provider_vendor; wsrep_uuid_t local_uuid = WSREP_UUID_UNDEFINED; wsrep_seqno_t local_seqno = WSREP_SEQNO_UNDEFINED; wsp::node_status local_status; -long wsrep_protocol_version = 1; +long wsrep_protocol_version = 2; // action execute callback extern wsrep_status_t wsrep_apply_cb(void *ctx, @@ -229,6 +229,7 @@ static void wsrep_view_handler_cb (void* app_ctx, { case 0: case 1: + case 2: // version change if (view->proto_ver != wsrep_protocol_version) { @@ -278,9 +279,10 @@ static void wsrep_view_handler_cb (void* app_ctx, { /* * NOTE: Initialize wsrep_group_uuid here only if it wasn't initialized - * before. + * before - OR - it was reinitilized on startup (lp:992840) */ - if (!memcmp (&local_uuid, &WSREP_UUID_UNDEFINED, sizeof(wsrep_uuid_t))) + if (!memcmp (&local_uuid, &WSREP_UUID_UNDEFINED, sizeof(wsrep_uuid_t)) || + 0 == wsrep_cluster_conf_id) { if (wsrep_init_first()) { @@ -730,6 +732,7 @@ static bool wsrep_prepare_key_for_isolation(const char* db, *key_len= 0; break; case 1: + case 2: { *key_len= 0; if (db) @@ -860,6 +863,7 @@ bool wsrep_prepare_key_for_innodb(const uchar* cache_key, break; } case 1: + case 2: { key[*key_len].buf = cache_key; key[*key_len].buf_len = strlen( (char*)cache_key ); diff --git a/sql/wsrep_mysqld.h b/sql/wsrep_mysqld.h index 985431e74b9..ebea44c9151 100644 --- a/sql/wsrep_mysqld.h +++ b/sql/wsrep_mysqld.h @@ -1,4 +1,4 @@ -/* Copyright 2008 Codership Oy <http://www.codership.com> +/* Copyright 2008-2012 Codership Oy <http://www.codership.com> This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -131,7 +131,7 @@ extern bool wsrep_sst_donor_update UPDATE_ARGS; extern bool wsrep_init_first(); // initialize wsrep before storage - // engines or after + // engines (true) or after (false) extern int wsrep_init(); extern void wsrep_deinit(); extern void wsrep_recover(); diff --git a/sql/wsrep_sst.cc b/sql/wsrep_sst.cc index 4ce7fe84b0f..37779c4b96d 100644 --- a/sql/wsrep_sst.cc +++ b/sql/wsrep_sst.cc @@ -1,4 +1,4 @@ -/* Copyright 2008-2011 Codership Oy <http://www.codership.com> +/* Copyright 2008-2012 Codership Oy <http://www.codership.com> This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -25,10 +25,11 @@ extern const char wsrep_defaults_file[]; -#define WSREP_SST_MYSQLDUMP "mysqldump" -#define WSREP_SST_DEFAULT WSREP_SST_MYSQLDUMP +#define WSREP_SST_MYSQLDUMP "mysqldump" +#define WSREP_SST_SKIP "skip" +#define WSREP_SST_DEFAULT WSREP_SST_MYSQLDUMP #define WSREP_SST_ADDRESS_AUTO "AUTO" -#define WSREP_SST_AUTH_MASK "********" +#define WSREP_SST_AUTH_MASK "********" const char* wsrep_sst_method = WSREP_SST_DEFAULT; const char* wsrep_sst_receive_address = WSREP_SST_ADDRESS_AUTO; @@ -158,6 +159,7 @@ bool wsrep_init_first() { return (wsrep_provider != NULL && strcmp (wsrep_provider, WSREP_NONE) + && strcmp (wsrep_sst_method, WSREP_SST_SKIP) && strcmp (wsrep_sst_method, WSREP_SST_MYSQLDUMP)); } @@ -439,8 +441,8 @@ static ssize_t sst_prepare_mysqldump (const char* addr_in, ret= -ENOMEM; } - sql_print_error ("WSREP: Could not prepare state transfer request: " - "adding default port failed: %zd.", ret); + WSREP_ERROR ("Could not prepare state transfer request: " + "adding default port failed: %zd.", ret); } else { *addr_out= addr_in; @@ -458,6 +460,18 @@ ssize_t wsrep_sst_prepare (void** msg) const char* addr_in= NULL; const char* addr_out= NULL; + if (!strcmp(wsrep_sst_method, WSREP_SST_SKIP)) + { + ssize_t ret = strlen(WSREP_STATE_TRANSFER_TRIVIAL) + 1; + *msg = strdup(WSREP_STATE_TRANSFER_TRIVIAL); + if (!msg) + { + WSREP_ERROR("Could not allocate %zd bytes for state request", ret); + unireg_abort(1); + } + return ret; + } + // Figure out SST address. Common for all SST methods if (wsrep_sst_receive_address && strcmp (wsrep_sst_receive_address, WSREP_SST_ADDRESS_AUTO)) diff --git a/storage/innobase/handler/ha_innodb.cc b/storage/innobase/handler/ha_innodb.cc index 050ebf7d505..52df97e5eee 100644 --- a/storage/innobase/handler/ha_innodb.cc +++ b/storage/innobase/handler/ha_innodb.cc @@ -4751,14 +4751,17 @@ wsrep_store_key_val_for_row( wsrep_innobase_mysql_sort( mysql_type, cs->number, sorted, true_len); - /* Note that we always reserve the maximum possible + if (wsrep_protocol_version > 1) { + memcpy(buff, sorted, true_len); + /* Note that we always reserve the maximum possible length of the true VARCHAR in the key value, though only len first bytes after the 2 length bytes contain actual data. The rest of the space was reset to zero in the bzero() call above. */ - - buff += key_len; - + buff += true_len; + } else { + buff += key_len; + } } else if (mysql_type == MYSQL_TYPE_TINY_BLOB || mysql_type == MYSQL_TYPE_MEDIUM_BLOB || mysql_type == MYSQL_TYPE_BLOB @@ -4825,8 +4828,11 @@ wsrep_store_key_val_for_row( /* Note that we always reserve the maximum possible length of the BLOB prefix in the key value. */ - - buff += key_len; + if (wsrep_protocol_version > 1) { + buff += true_len; + } else { + buff += key_len; + } } else { /* Here we handle all other data types except the true VARCHAR, BLOB and TEXT. Note that the column @@ -6947,20 +6953,24 @@ wsrep_append_foreign_key( key[0] = '\0'; rcode = wsrep_rec_get_primary_key( - &key[1], &len, clust_rec, clust_index); + &key[1], &len, clust_rec, clust_index, + wsrep_protocol_version > 1); if (rcode != DB_SUCCESS) { WSREP_ERROR("FK key set failed: %lu", rcode); return rcode; } #ifdef WSREP_DEBUG_PRINT ulint i; - fprintf(stderr, "FK parent key, len: %lu ", len+1); + fprintf(stderr, "FK parent key, table: %s shared: %d len: %lu ", + foreign->referenced_table_name, (int)shared, len+1); for (i=0; i<len+1; i++) { - fprintf(stderr, " (%X), ", key[i]); + fprintf(stderr, " %hhX, ", key[i]); } fprintf(stderr, "\n"); #endif - strncpy(cache_key, foreign->foreign_table->name, 512); + strncpy(cache_key, (wsrep_protocol_version > 1) ? + foreign->referenced_table->name : + foreign->foreign_table->name, 512); char *p = strchr(cache_key, '/'); if (p) { *p = '\0'; diff --git a/storage/innobase/include/rem0rec.h b/storage/innobase/include/rem0rec.h index ab390f4fb3a..30ef3048ff1 100644 --- a/storage/innobase/include/rem0rec.h +++ b/storage/innobase/include/rem0rec.h @@ -837,7 +837,8 @@ int wsrep_rec_get_primary_key( byte *buf, /* out: extracted key */ ulint *buf_len, /* in/out: length of buf */ const rec_t* rec, /* in: physical record */ - dict_index_t* index); /* in: record descriptor */ + dict_index_t* index, /* in: record descriptor */ + ibool new_protocol); /* in: protocol > 1 */ #endif /* WITH_WSREP */ #ifndef UNIV_NONINL #include "rem0rec.ic" diff --git a/storage/innobase/rem/rem0rec.c b/storage/innobase/rem/rem0rec.c index dbfc41881ce..15618a3fa02 100644 --- a/storage/innobase/rem/rem0rec.c +++ b/storage/innobase/rem/rem0rec.c @@ -1781,7 +1781,8 @@ wsrep_rec_get_primary_key( byte *buf, /* out: extracted key */ ulint *buf_len, /* in/out: length of buf */ const rec_t* rec, /* in: physical record */ - dict_index_t* index) /* in: record descriptor */ + dict_index_t* index, /* in: record descriptor */ + ibool new_protocol) /* in: protocol > 1 */ { const byte* data; ulint len; @@ -1819,7 +1820,7 @@ wsrep_rec_get_primary_key( ut_a(!(col->prtype & DATA_NOT_NULL)); *buf++ = 1; key_len++; - } else { + } else if (!new_protocol) { if (!(col->prtype & DATA_NOT_NULL)) { *buf++ = 0; key_len++; @@ -1829,6 +1830,47 @@ wsrep_rec_get_primary_key( (int)(col->prtype & DATA_MYSQL_TYPE_MASK), (uint)dtype_get_charset_coll(col->prtype), buf, len); + } else { /* new protocol */ + if (!(col->prtype & DATA_NOT_NULL)) { + *buf++ = 0; + key_len++; + } + switch (col->mtype) { + case DATA_INT: { + byte* ptr = buf+len; + for (;;) { + ptr--; + *ptr = *data; + if (ptr == buf) { + break; + } + data++; + } + + if (!(col->prtype & DATA_UNSIGNED)) { + buf[len-1] = (byte) (buf[len-1] ^ 128); + } + + break; + } + case DATA_VARCHAR: + case DATA_VARMYSQL: + case DATA_BINARY: + /* Copy the actual data */ + ut_memcpy(buf, data, len); + wsrep_innobase_mysql_sort( + (int)(col->prtype & DATA_MYSQL_TYPE_MASK), + (uint)dtype_get_charset_coll(col->prtype), + buf, len); + break; + case DATA_BLOB: + case DATA_MYSQL: + memcpy(buf, data, len); + break; + default: + break; + } + key_len += len; buf += len; } diff --git a/storage/xtradb/handler/ha_innodb.cc b/storage/xtradb/handler/ha_innodb.cc index a1119fc3d47..4a869cf64b0 100644 --- a/storage/xtradb/handler/ha_innodb.cc +++ b/storage/xtradb/handler/ha_innodb.cc @@ -5131,14 +5131,17 @@ wsrep_store_key_val_for_row( wsrep_innobase_mysql_sort( mysql_type, cs->number, sorted, true_len); - /* Note that we always reserve the maximum possible + if (wsrep_protocol_version > 1) { + memcpy(buff, sorted, true_len); + /* Note that we always reserve the maximum possible length of the true VARCHAR in the key value, though only len first bytes after the 2 length bytes contain actual data. The rest of the space was reset to zero in the bzero() call above. */ - - buff += key_len; - + buff += true_len; + } else { + buff += key_len; + } } else if (mysql_type == MYSQL_TYPE_TINY_BLOB || mysql_type == MYSQL_TYPE_MEDIUM_BLOB || mysql_type == MYSQL_TYPE_BLOB @@ -5205,8 +5208,11 @@ wsrep_store_key_val_for_row( /* Note that we always reserve the maximum possible length of the BLOB prefix in the key value. */ - - buff += key_len; + if (wsrep_protocol_version > 1) { + buff += true_len; + } else { + buff += key_len; + } } else { /* Here we handle all other data types except the true VARCHAR, BLOB and TEXT. Note that the column @@ -7591,20 +7597,24 @@ wsrep_append_foreign_key( key[0] = '\0'; rcode = wsrep_rec_get_primary_key( - &key[1], &len, clust_rec, clust_index); + &key[1], &len, clust_rec, clust_index, + wsrep_protocol_version > 1); if (rcode != DB_SUCCESS) { WSREP_ERROR("FK key set failed: %lu", rcode); return rcode; } #ifdef WSREP_DEBUG_PRINT ulint i; - fprintf(stderr, "FK parent key, len: %lu ", len+1); + fprintf(stderr, "FK parent key, table: %s shared: %d len: %lu ", + foreign->referenced_table_name, (int)shared, len+1); for (i=0; i<len+1; i++) { - fprintf(stderr, " (%X), ", key[i]); + fprintf(stderr, " %hhX, ", key[i]); } fprintf(stderr, "\n"); #endif - strncpy(cache_key, foreign->foreign_table->name, 512); + strncpy(cache_key, (wsrep_protocol_version > 1) ? + foreign->referenced_table->name : + foreign->foreign_table->name, 512); char *p = strchr(cache_key, '/'); if (p) { *p = '\0'; diff --git a/storage/xtradb/include/rem0rec.h b/storage/xtradb/include/rem0rec.h index ab390f4fb3a..30ef3048ff1 100644 --- a/storage/xtradb/include/rem0rec.h +++ b/storage/xtradb/include/rem0rec.h @@ -837,7 +837,8 @@ int wsrep_rec_get_primary_key( byte *buf, /* out: extracted key */ ulint *buf_len, /* in/out: length of buf */ const rec_t* rec, /* in: physical record */ - dict_index_t* index); /* in: record descriptor */ + dict_index_t* index, /* in: record descriptor */ + ibool new_protocol); /* in: protocol > 1 */ #endif /* WITH_WSREP */ #ifndef UNIV_NONINL #include "rem0rec.ic" diff --git a/storage/xtradb/rem/rem0rec.c b/storage/xtradb/rem/rem0rec.c index dbfc41881ce..15618a3fa02 100644 --- a/storage/xtradb/rem/rem0rec.c +++ b/storage/xtradb/rem/rem0rec.c @@ -1781,7 +1781,8 @@ wsrep_rec_get_primary_key( byte *buf, /* out: extracted key */ ulint *buf_len, /* in/out: length of buf */ const rec_t* rec, /* in: physical record */ - dict_index_t* index) /* in: record descriptor */ + dict_index_t* index, /* in: record descriptor */ + ibool new_protocol) /* in: protocol > 1 */ { const byte* data; ulint len; @@ -1819,7 +1820,7 @@ wsrep_rec_get_primary_key( ut_a(!(col->prtype & DATA_NOT_NULL)); *buf++ = 1; key_len++; - } else { + } else if (!new_protocol) { if (!(col->prtype & DATA_NOT_NULL)) { *buf++ = 0; key_len++; @@ -1829,6 +1830,47 @@ wsrep_rec_get_primary_key( (int)(col->prtype & DATA_MYSQL_TYPE_MASK), (uint)dtype_get_charset_coll(col->prtype), buf, len); + } else { /* new protocol */ + if (!(col->prtype & DATA_NOT_NULL)) { + *buf++ = 0; + key_len++; + } + switch (col->mtype) { + case DATA_INT: { + byte* ptr = buf+len; + for (;;) { + ptr--; + *ptr = *data; + if (ptr == buf) { + break; + } + data++; + } + + if (!(col->prtype & DATA_UNSIGNED)) { + buf[len-1] = (byte) (buf[len-1] ^ 128); + } + + break; + } + case DATA_VARCHAR: + case DATA_VARMYSQL: + case DATA_BINARY: + /* Copy the actual data */ + ut_memcpy(buf, data, len); + wsrep_innobase_mysql_sort( + (int)(col->prtype & DATA_MYSQL_TYPE_MASK), + (uint)dtype_get_charset_coll(col->prtype), + buf, len); + break; + case DATA_BLOB: + case DATA_MYSQL: + memcpy(buf, data, len); + break; + default: + break; + } + key_len += len; buf += len; } |