]> git.pld-linux.org Git - packages/mysql.git/commitdiff
- up to 5.5.17 auto/th/mysql-5_5_17-1
authorArkadiusz Miśkiewicz <arekm@maven.pl>
Sat, 19 Nov 2011 15:13:39 +0000 (15:13 +0000)
committercvs2git <feedback@pld-linux.org>
Sun, 24 Jun 2012 12:13:13 +0000 (12:13 +0000)
Changed files:
    bug45702.patch -> 1.2
    bug580324.patch -> 1.5
    bug860910.patch -> 1.2
    innodb_adaptive_hash_index_partitions.patch -> 1.9
    innodb_admin_command_base.patch -> 1.8
    innodb_buffer_pool_pages_i_s.patch -> 1.9
    innodb_buffer_pool_shm.patch -> 1.9
    innodb_deadlock_count.patch -> 1.9
    innodb_dict_size_limit.patch -> 1.7
    innodb_expand_fast_index_creation.patch -> 1.4
    innodb_expand_import.patch -> 1.8
    innodb_extend_slow.patch -> 1.9
    innodb_extra_rseg.patch -> 1.7
    innodb_fake_changes.patch -> 1.2
    innodb_fast_checksum.patch -> 1.8
    innodb_files_extend.patch -> 1.8
    innodb_fix_misc.patch -> 1.10
    innodb_io_patches.patch -> 1.8
    innodb_kill_idle_transaction.patch -> 1.2
    innodb_lru_dump_restore.patch -> 1.8
    innodb_opt_lru_count.patch -> 1.6
    innodb_overwrite_relay_log_info.patch -> 1.8
    innodb_pass_corrupt_table.patch -> 1.10
    innodb_recovery_patches.patch -> 1.9
    innodb_separate_doublewrite.patch -> 1.11
    innodb_show_lock_name.patch -> 1.7
    innodb_show_status.patch -> 1.7
    innodb_show_status_extend.patch -> 1.8
    innodb_show_sys_tables.patch -> 1.8
    innodb_split_buf_pool_mutex.patch -> 1.8
    innodb_stats.patch -> 1.8
    innodb_thread_concurrency_timer_based.patch -> 1.7
    log_warnings_suppress.patch -> 1.7
    memory_dynamic_rows.patch -> 1.3
    microsec_process.patch -> 1.7
    mysql.spec -> 1.561
    percona_support.patch -> 1.4
    processlist_row_stats.patch -> 1.5
    query_cache_enhance.patch -> 1.9
    response_time_distribution.patch -> 1.8
    show_slave_status_nolock.patch -> 1.8
    show_temp.patch -> 1.8
    slow_extended.patch -> 1.9
    sql_no_fcache.patch -> 1.8
    subunit.patch -> 1.2
    userstat.patch -> 1.9
    valgrind_zlib_suppression.patch -> 1.2

47 files changed:
bug45702.patch [new file with mode: 0644]
bug580324.patch
bug860910.patch [new file with mode: 0644]
innodb_adaptive_hash_index_partitions.patch
innodb_admin_command_base.patch
innodb_buffer_pool_pages_i_s.patch
innodb_buffer_pool_shm.patch
innodb_deadlock_count.patch
innodb_dict_size_limit.patch
innodb_expand_fast_index_creation.patch
innodb_expand_import.patch
innodb_extend_slow.patch
innodb_extra_rseg.patch
innodb_fake_changes.patch [new file with mode: 0644]
innodb_fast_checksum.patch
innodb_files_extend.patch
innodb_fix_misc.patch
innodb_io_patches.patch
innodb_kill_idle_transaction.patch [new file with mode: 0644]
innodb_lru_dump_restore.patch
innodb_opt_lru_count.patch
innodb_overwrite_relay_log_info.patch
innodb_pass_corrupt_table.patch
innodb_recovery_patches.patch
innodb_separate_doublewrite.patch
innodb_show_lock_name.patch
innodb_show_status.patch
innodb_show_status_extend.patch
innodb_show_sys_tables.patch
innodb_split_buf_pool_mutex.patch
innodb_stats.patch
innodb_thread_concurrency_timer_based.patch
log_warnings_suppress.patch
memory_dynamic_rows.patch
microsec_process.patch
mysql.spec
percona_support.patch
processlist_row_stats.patch
query_cache_enhance.patch
response_time_distribution.patch
show_slave_status_nolock.patch
show_temp.patch
slow_extended.patch
sql_no_fcache.patch
subunit.patch [new file with mode: 0644]
userstat.patch
valgrind_zlib_suppression.patch

diff --git a/bug45702.patch b/bug45702.patch
new file mode 100644 (file)
index 0000000..191ca0e
--- /dev/null
@@ -0,0 +1,728 @@
+--- a/include/my_sys.h
++++ b/include/my_sys.h
+@@ -320,8 +320,8 @@
+ typedef struct st_dynamic_array
+ {
+   uchar *buffer;
+-  uint elements,max_element;
+-  uint alloc_increment;
++  ulong elements, max_element;
++  ulong alloc_increment;
+   uint size_of_element;
+ } DYNAMIC_ARRAY;
+@@ -758,21 +758,21 @@
+ #define my_init_dynamic_array2(A,B,C,D,E) init_dynamic_array2(A,B,C,D,E)
+ #define my_init_dynamic_array2_ci(A,B,C,D,E) init_dynamic_array2(A,B,C,D,E)
+ extern my_bool init_dynamic_array2(DYNAMIC_ARRAY *array, uint element_size,
+-                                   void *init_buffer, uint init_alloc,
+-                                   uint alloc_increment);
++                                   void *init_buffer, ulong init_alloc,
++                                   ulong alloc_increment);
+ /* init_dynamic_array() function is deprecated */
+ extern my_bool init_dynamic_array(DYNAMIC_ARRAY *array, uint element_size,
+-                                  uint init_alloc, uint alloc_increment);
++                                  ulong init_alloc, ulong alloc_increment);
+ extern my_bool insert_dynamic(DYNAMIC_ARRAY *array,uchar * element);
+ extern uchar *alloc_dynamic(DYNAMIC_ARRAY *array);
+ extern uchar *pop_dynamic(DYNAMIC_ARRAY*);
+-extern my_bool set_dynamic(DYNAMIC_ARRAY *array,uchar * element,uint array_index);
+-extern my_bool allocate_dynamic(DYNAMIC_ARRAY *array, uint max_elements);
+-extern void get_dynamic(DYNAMIC_ARRAY *array,uchar * element,uint array_index);
++extern my_bool set_dynamic(DYNAMIC_ARRAY *array, uchar * element, ulong array_index);
++extern my_bool allocate_dynamic(DYNAMIC_ARRAY *array, ulong max_elements);
++extern void get_dynamic(DYNAMIC_ARRAY *array, uchar * element, ulong array_index);
+ extern void delete_dynamic(DYNAMIC_ARRAY *array);
+-extern void delete_dynamic_element(DYNAMIC_ARRAY *array, uint array_index);
++extern void delete_dynamic_element(DYNAMIC_ARRAY *array, ulong array_index);
+ extern void freeze_size(DYNAMIC_ARRAY *array);
+-extern int  get_index_dynamic(DYNAMIC_ARRAY *array, uchar * element);
++extern long get_index_dynamic(DYNAMIC_ARRAY *array, uchar * element);
+ #define dynamic_array_ptr(array,array_index) ((array)->buffer+(array_index)*(array)->size_of_element)
+ #define dynamic_element(array,array_index,type) ((type)((array)->buffer) +(array_index))
+ #define push_dynamic(A,B) insert_dynamic((A),(B))
+--- a/mysys/array.c
++++ b/mysys/array.c
+@@ -41,8 +41,8 @@
+ */
+ my_bool init_dynamic_array2(DYNAMIC_ARRAY *array, uint element_size,
+-                            void *init_buffer, uint init_alloc, 
+-                            uint alloc_increment)
++                            void *init_buffer, ulong init_alloc, 
++                            ulong alloc_increment)
+ {
+   DBUG_ENTER("init_dynamic_array");
+   if (!alloc_increment)
+@@ -73,7 +73,7 @@
+ } 
+ my_bool init_dynamic_array(DYNAMIC_ARRAY *array, uint element_size,
+-                           uint init_alloc, uint alloc_increment)
++                           ulong init_alloc, ulong alloc_increment)
+ {
+   /* placeholder to preserve ABI */
+   return my_init_dynamic_array_ci(array, element_size, init_alloc, 
+@@ -196,7 +196,7 @@
+     FALSE     Ok
+ */
+-my_bool set_dynamic(DYNAMIC_ARRAY *array, uchar* element, uint idx)
++my_bool set_dynamic(DYNAMIC_ARRAY *array, uchar* element, ulong idx)
+ {
+   if (idx >= array->elements)
+   {
+@@ -228,11 +228,11 @@
+     TRUE      Allocation of new memory failed
+ */
+-my_bool allocate_dynamic(DYNAMIC_ARRAY *array, uint max_elements)
++my_bool allocate_dynamic(DYNAMIC_ARRAY *array, ulong max_elements)
+ {
+   if (max_elements >= array->max_element)
+   {
+-    uint size;
++    ulong size;
+     uchar *new_ptr;
+     size= (max_elements + array->alloc_increment)/array->alloc_increment;
+     size*= array->alloc_increment;
+@@ -273,11 +273,11 @@
+       idx     Index of element wanted. 
+ */
+-void get_dynamic(DYNAMIC_ARRAY *array, uchar* element, uint idx)
++void get_dynamic(DYNAMIC_ARRAY *array, uchar* element, ulong idx)
+ {
+   if (idx >= array->elements)
+   {
+-    DBUG_PRINT("warning",("To big array idx: %d, array size is %d",
++    DBUG_PRINT("warning",("To big array idx: %lu, array size is %lu",
+                           idx,array->elements));
+     bzero(element,array->size_of_element);
+     return;
+@@ -320,7 +320,7 @@
+       idx        Index of element to be deleted
+ */
+-void delete_dynamic_element(DYNAMIC_ARRAY *array, uint idx)
++void delete_dynamic_element(DYNAMIC_ARRAY *array, ulong idx)
+ {
+   char *ptr= (char*) array->buffer+array->size_of_element*idx;
+   array->elements--;
+@@ -340,7 +340,7 @@
+ void freeze_size(DYNAMIC_ARRAY *array)
+ {
+-  uint elements=max(array->elements,1);
++  ulong elements= max(array->elements, 1);
+   /*
+     Do nothing if we are using a static buffer
+@@ -368,7 +368,7 @@
+ */
+-int get_index_dynamic(DYNAMIC_ARRAY *array, uchar* element)
++long get_index_dynamic(DYNAMIC_ARRAY *array, uchar* element)
+ {
+   size_t ret;
+   if (array->buffer > element)
+--- a/storage/myisam/mi_check.c
++++ b/storage/myisam/mi_check.c
+@@ -2429,7 +2429,7 @@
+     if (_create_index_by_sort(&sort_param,
+                             (my_bool) (!(param->testflag & T_VERBOSE)),
+-                            (uint) param->sort_buffer_length))
++                            param->sort_buffer_length))
+     {
+       param->retry_repair=1;
+       goto err;
+--- a/storage/myisam/sort.c
++++ b/storage/myisam/sort.c
+@@ -45,42 +45,42 @@
+ /* Functions defined in this file */
+-static ha_rows find_all_keys(MI_SORT_PARAM *info,uint keys,
++static ha_rows find_all_keys(MI_SORT_PARAM *info, ulong keys,
+                              uchar **sort_keys,
+-                             DYNAMIC_ARRAY *buffpek,int *maxbuffer,
++                             DYNAMIC_ARRAY *buffpek, long *maxbuffer,
+                              IO_CACHE *tempfile,
+                              IO_CACHE *tempfile_for_exceptions);
+ static int write_keys(MI_SORT_PARAM *info,uchar **sort_keys,
+-                      uint count, BUFFPEK *buffpek,IO_CACHE *tempfile);
++                      ulong count, BUFFPEK *buffpek,IO_CACHE *tempfile);
+ static int write_key(MI_SORT_PARAM *info, uchar *key,
+                      IO_CACHE *tempfile);
+ static int write_index(MI_SORT_PARAM *info,uchar * *sort_keys,
+-                       uint count);
+-static int merge_many_buff(MI_SORT_PARAM *info,uint keys,
++                       ulong count);
++static int merge_many_buff(MI_SORT_PARAM *info, ulong keys,
+                            uchar * *sort_keys,
+-                           BUFFPEK *buffpek,int *maxbuffer,
++                           BUFFPEK *buffpek, long *maxbuffer,
+                            IO_CACHE *t_file);
+-static uint read_to_buffer(IO_CACHE *fromfile,BUFFPEK *buffpek,
++static ulong read_to_buffer(IO_CACHE *fromfile,BUFFPEK *buffpek,
+                            uint sort_length);
+-static int merge_buffers(MI_SORT_PARAM *info,uint keys,
++static int merge_buffers(MI_SORT_PARAM *info, ulong keys,
+                          IO_CACHE *from_file, IO_CACHE *to_file,
+                          uchar * *sort_keys, BUFFPEK *lastbuff,
+                          BUFFPEK *Fb, BUFFPEK *Tb);
+-static int merge_index(MI_SORT_PARAM *,uint,uchar **,BUFFPEK *, int,
++static int merge_index(MI_SORT_PARAM *, ulong, uchar **, BUFFPEK *, long,
+                        IO_CACHE *);
+ static int flush_ft_buf(MI_SORT_PARAM *info);
+ static int write_keys_varlen(MI_SORT_PARAM *info,uchar **sort_keys,
+-                             uint count, BUFFPEK *buffpek,
++                             ulong count, BUFFPEK *buffpek,
+                              IO_CACHE *tempfile);
+-static uint read_to_buffer_varlen(IO_CACHE *fromfile,BUFFPEK *buffpek,
+-                                  uint sort_length);
++static ulong read_to_buffer_varlen(IO_CACHE *fromfile,BUFFPEK *buffpek,
++                                   uint sort_length);
+ static int write_merge_key(MI_SORT_PARAM *info, IO_CACHE *to_file,
+-                           uchar *key, uint sort_length, uint count);
++                           uchar *key, uint sort_length, ulong count);
+ static int write_merge_key_varlen(MI_SORT_PARAM *info,
+                                   IO_CACHE *to_file,
+                                   uchar* key, uint sort_length,
+-                                  uint count);
++                                  ulong count);
+ static inline int
+ my_var_write(MI_SORT_PARAM *info, IO_CACHE *to_file, uchar *bufs);
+@@ -101,8 +101,9 @@
+ int _create_index_by_sort(MI_SORT_PARAM *info,my_bool no_messages,
+                         ulong sortbuff_size)
+ {
+-  int error,maxbuffer,skr;
+-  uint memavl,old_memavl,keys,sort_length;
++  int error;
++  long maxbuffer, skr;
++  ulong memavl, old_memavl, keys, sort_length;
+   DYNAMIC_ARRAY buffpek;
+   ha_rows records;
+   uchar **sort_keys;
+@@ -136,25 +137,25 @@
+   while (memavl >= MIN_SORT_BUFFER)
+   {
+-    if ((records < UINT_MAX32) && 
++    if ((records < ULONG_MAX) &&
+        ((my_off_t) (records + 1) * 
+         (sort_length + sizeof(char*)) <= (my_off_t) memavl))
+-      keys= (uint)records+1;
++      keys= (ulong) records + 1;
+     else
+       do
+       {
+       skr=maxbuffer;
+-      if (memavl < sizeof(BUFFPEK)*(uint) maxbuffer ||
+-          (keys=(memavl-sizeof(BUFFPEK)*(uint) maxbuffer)/
++        if (memavl < sizeof(BUFFPEK) * (ulong) maxbuffer ||
++            (keys = (memavl - sizeof(BUFFPEK) * (ulong) maxbuffer) /
+              (sort_length+sizeof(char*))) <= 1 ||
+-            keys < (uint) maxbuffer)
++            keys < (ulong) maxbuffer)
+       {
+         mi_check_print_error(info->sort_info->param,
+                              "myisam_sort_buffer_size is too small");
+         goto err;
+       }
+       }
+-      while ((maxbuffer= (int) (records/(keys-1)+1)) != skr);
++      while ((maxbuffer= (long) (records / (keys - 1) + 1)) != skr);
+     if ((sort_keys=(uchar **)my_malloc(keys*(sort_length+sizeof(char*))+
+                                      HA_FT_MAXBYTELEN, MYF(0))))
+@@ -180,7 +181,7 @@
+   (*info->lock_in_memory)(info->sort_info->param);/* Everything is allocated */
+   if (!no_messages)
+-    printf("  - Searching for keys, allocating buffer for %d keys\n",keys);
++    printf("  - Searching for keys, allocating buffer for %lu keys\n", keys);
+   if ((records=find_all_keys(info,keys,sort_keys,&buffpek,&maxbuffer,
+                                   &tempfile,&tempfile_for_exceptions))
+@@ -190,7 +191,7 @@
+   {
+     if (!no_messages)
+       printf("  - Dumping %lu keys\n", (ulong) records);
+-    if (write_index(info,sort_keys, (uint) records))
++    if (write_index(info,sort_keys, (ulong) records))
+       goto err; /* purecov: inspected */
+   }
+   else
+@@ -253,13 +254,13 @@
+ /* Search after all keys and place them in a temp. file */
+-static ha_rows find_all_keys(MI_SORT_PARAM *info, uint keys,
++static ha_rows find_all_keys(MI_SORT_PARAM *info, ulong keys,
+                              uchar **sort_keys, DYNAMIC_ARRAY *buffpek,
+-                             int *maxbuffer, IO_CACHE *tempfile,
++                             long *maxbuffer, IO_CACHE *tempfile,
+                              IO_CACHE *tempfile_for_exceptions)
+ {
+   int error;
+-  uint idx;
++  ulong idx;
+   DBUG_ENTER("find_all_keys");
+   idx=error=0;
+@@ -308,8 +309,8 @@
+ {
+   MI_SORT_PARAM *sort_param= (MI_SORT_PARAM*) arg;
+   int error;
+-  uint memavl,old_memavl,keys,sort_length;
+-  uint idx, maxbuffer;
++  ulong memavl,old_memavl,keys,sort_length;
++  ulong idx, maxbuffer;
+   uchar **sort_keys=0;
+   LINT_INIT(keys);
+@@ -345,7 +346,7 @@
+     sort_keys= (uchar **) NULL;
+     memavl=       max(sort_param->sortbuff_size, MIN_SORT_BUFFER);
+-    idx=          (uint)sort_param->sort_info->max_records;
++    idx=          (ulong) sort_param->sort_info->max_records;
+     sort_length=  sort_param->key_length;
+     maxbuffer=    1;
+@@ -356,21 +357,21 @@
+         keys= idx+1;
+       else
+       {
+-        uint skr;
++        ulong skr;
+         do
+         {
+           skr= maxbuffer;
+           if (memavl < sizeof(BUFFPEK)*maxbuffer ||
+               (keys=(memavl-sizeof(BUFFPEK)*maxbuffer)/
+                (sort_length+sizeof(char*))) <= 1 ||
+-              keys < (uint) maxbuffer)
++              keys < maxbuffer)
+           {
+             mi_check_print_error(sort_param->sort_info->param,
+                                  "myisam_sort_buffer_size is too small");
+             goto err;
+           }
+         }
+-        while ((maxbuffer= (int) (idx/(keys-1)+1)) != skr);
++        while ((maxbuffer= (idx/(keys-1)+1)) != skr);
+       }
+       if ((sort_keys= (uchar**)
+            my_malloc(keys*(sort_length+sizeof(char*))+
+@@ -399,7 +400,7 @@
+     }
+     if (sort_param->sort_info->param->testflag & T_VERBOSE)
+-      printf("Key %d - Allocating buffer for %d keys\n",
++      printf("Key %d - Allocating buffer for %lu keys\n",
+              sort_param->key + 1, keys);
+     sort_param->sort_keys= sort_keys;
+@@ -553,7 +554,7 @@
+     }
+     if (sinfo->buffpek.elements)
+     {
+-      uint maxbuffer=sinfo->buffpek.elements-1;
++      ulong maxbuffer=sinfo->buffpek.elements-1;
+       if (!mergebuf)
+       {
+         length=param->sort_buffer_length;
+@@ -576,7 +577,7 @@
+           printf("Key %d  - Merging %u keys\n",sinfo->key+1, sinfo->keys);
+         if (merge_many_buff(sinfo, keys, (uchar **)mergebuf,
+                           dynamic_element(&sinfo->buffpek, 0, BUFFPEK *),
+-                          (int*) &maxbuffer, &sinfo->tempfile))
++                          (long *) &maxbuffer, &sinfo->tempfile))
+         {
+           got_error=1;
+           continue;
+@@ -640,7 +641,7 @@
+         /* Write all keys in memory to file for later merge */
+ static int write_keys(MI_SORT_PARAM *info, register uchar **sort_keys,
+-                      uint count, BUFFPEK *buffpek, IO_CACHE *tempfile)
++                      ulong count, BUFFPEK *buffpek, IO_CACHE *tempfile)
+ {
+   uchar **end;
+   uint sort_length=info->key_length;
+@@ -682,7 +683,7 @@
+ static int write_keys_varlen(MI_SORT_PARAM *info,
+                              register uchar **sort_keys,
+-                             uint count, BUFFPEK *buffpek,
++                             ulong count, BUFFPEK *buffpek,
+                              IO_CACHE *tempfile)
+ {
+   uchar **end;
+@@ -727,7 +728,7 @@
+ /* Write index */
+ static int write_index(MI_SORT_PARAM *info, register uchar **sort_keys,
+-                       register uint count)
++                       register ulong count)
+ {
+   DBUG_ENTER("write_index");
+@@ -744,11 +745,11 @@
+         /* Merge buffers to make < MERGEBUFF2 buffers */
+-static int merge_many_buff(MI_SORT_PARAM *info, uint keys,
++static int merge_many_buff(MI_SORT_PARAM *info, ulong keys,
+                            uchar **sort_keys, BUFFPEK *buffpek,
+-                           int *maxbuffer, IO_CACHE *t_file)
++                           long *maxbuffer, IO_CACHE *t_file)
+ {
+-  register int i;
++  register long i;
+   IO_CACHE t_file2, *from_file, *to_file, *temp;
+   BUFFPEK *lastbuff;
+   DBUG_ENTER("merge_many_buff");
+@@ -778,7 +779,7 @@
+     if (flush_io_cache(to_file))
+       break;                                    /* purecov: inspected */
+     temp=from_file; from_file=to_file; to_file=temp;
+-    *maxbuffer= (int) (lastbuff-buffpek)-1;
++    *maxbuffer= (long) (lastbuff-buffpek)-1;
+   }
+ cleanup:
+   close_cached_file(to_file);                   /* This holds old result */
+@@ -807,18 +808,18 @@
+     -1        Error
+ */
+-static uint read_to_buffer(IO_CACHE *fromfile, BUFFPEK *buffpek,
+-                           uint sort_length)
++static ulong read_to_buffer(IO_CACHE *fromfile, BUFFPEK *buffpek,
++                            uint sort_length)
+ {
+-  register uint count;
+-  uint length;
++  register ulong count;
++  ulong length;
+-  if ((count=(uint) min((ha_rows) buffpek->max_keys,buffpek->count)))
++  if ((count=(ulong) min((ha_rows) buffpek->max_keys,buffpek->count)))
+   {
+     if (mysql_file_pread(fromfile->file, (uchar*) buffpek->base,
+                          (length= sort_length*count),
+                          buffpek->file_pos, MYF_RW))
+-      return((uint) -1);                        /* purecov: inspected */
++      return((ulong) -1);                        /* purecov: inspected */
+     buffpek->key=buffpek->base;
+     buffpek->file_pos+= length;                 /* New filepos */
+     buffpek->count-=    count;
+@@ -827,15 +828,15 @@
+   return (count*sort_length);
+ } /* read_to_buffer */
+-static uint read_to_buffer_varlen(IO_CACHE *fromfile, BUFFPEK *buffpek,
++static ulong read_to_buffer_varlen(IO_CACHE *fromfile, BUFFPEK *buffpek,
+                                   uint sort_length)
+ {
+-  register uint count;
++  register ulong count;
+   uint16 length_of_key = 0;
+-  uint idx;
++  ulong idx;
+   uchar *buffp;
+-  if ((count=(uint) min((ha_rows) buffpek->max_keys,buffpek->count)))
++  if ((count=(ulong) min((ha_rows) buffpek->max_keys,buffpek->count)))
+   {
+     buffp = buffpek->base;
+@@ -843,11 +844,11 @@
+     {
+       if (mysql_file_pread(fromfile->file, (uchar*)&length_of_key,
+                            sizeof(length_of_key), buffpek->file_pos, MYF_RW))
+-        return((uint) -1);
++        return((ulong) -1);
+       buffpek->file_pos+=sizeof(length_of_key);
+       if (mysql_file_pread(fromfile->file, (uchar*) buffp,
+                            length_of_key, buffpek->file_pos, MYF_RW))
+-        return((uint) -1);
++        return((ulong) -1);
+       buffpek->file_pos+=length_of_key;
+       buffp = buffp + sort_length;
+     }
+@@ -861,9 +862,9 @@
+ static int write_merge_key_varlen(MI_SORT_PARAM *info,
+                                   IO_CACHE *to_file, uchar* key,
+-                                  uint sort_length, uint count)
++                                  uint sort_length, ulong count)
+ {
+-  uint idx;
++  ulong idx;
+   uchar *bufs = key;
+   for (idx=1;idx<=count;idx++)
+@@ -879,7 +880,7 @@
+ static int write_merge_key(MI_SORT_PARAM *info __attribute__((unused)),
+                            IO_CACHE *to_file, uchar *key,
+-                           uint sort_length, uint count)
++                           uint sort_length, ulong count)
+ {
+   return my_b_write(to_file, key, (size_t) sort_length*count);
+ }
+@@ -890,12 +891,13 @@
+ */
+ static int
+-merge_buffers(MI_SORT_PARAM *info, uint keys, IO_CACHE *from_file,
++merge_buffers(MI_SORT_PARAM *info, ulong keys, IO_CACHE *from_file,
+               IO_CACHE *to_file, uchar **sort_keys, BUFFPEK *lastbuff,
+               BUFFPEK *Fb, BUFFPEK *Tb)
+ {
+-  int error;
+-  uint sort_length,maxcount;
++  ulong error;
++  uint sort_length;
++  ulong maxcount;
+   ha_rows count;
+   my_off_t UNINIT_VAR(to_start_filepos);
+   uchar *strpos;
+@@ -905,7 +907,7 @@
+   DBUG_ENTER("merge_buffers");
+   count=error=0;
+-  maxcount=keys/((uint) (Tb-Fb) +1);
++  maxcount= keys / ((ulong) (Tb-Fb) + 1);
+   DBUG_ASSERT(maxcount > 0);
+   LINT_INIT(to_start_filepos);
+   if (to_file)
+@@ -913,7 +915,7 @@
+   strpos=(uchar*) sort_keys;
+   sort_length=info->key_length;
+-  if (init_queue(&queue,(uint) (Tb-Fb)+1,offsetof(BUFFPEK,key),0,
++  if (init_queue(&queue, (uint) (Tb-Fb)+1, offsetof(BUFFPEK,key), 0,
+                  (int (*)(void*, uchar *,uchar*)) info->key_cmp,
+                  (void*) info))
+     DBUG_RETURN(1); /* purecov: inspected */
+@@ -923,9 +925,8 @@
+     count+= buffpek->count;
+     buffpek->base= strpos;
+     buffpek->max_keys=maxcount;
+-    strpos+= (uint) (error=(int) info->read_to_buffer(from_file,buffpek,
+-                                                      sort_length));
+-    if (error == -1)
++    strpos+= (error= info->read_to_buffer(from_file,buffpek, sort_length));
++    if (error == (ulong) -1)
+       goto err; /* purecov: inspected */
+     queue_insert(&queue,(uchar*) buffpek);
+   }
+@@ -957,10 +958,10 @@
+       buffpek->key+=sort_length;
+       if (! --buffpek->mem_count)
+       {
+-        if (!(error=(int) info->read_to_buffer(from_file,buffpek,sort_length)))
++        if (!(error= info->read_to_buffer(from_file,buffpek,sort_length)))
+         {
+           uchar *base=buffpek->base;
+-          uint max_keys=buffpek->max_keys;
++          ulong max_keys=buffpek->max_keys;
+           (void) queue_remove(&queue,0);
+@@ -985,7 +986,7 @@
+           break;                /* One buffer have been removed */
+         }
+       }
+-      else if (error == -1)
++      else if (error == (ulong) -1)
+         goto err;               /* purecov: inspected */
+       queue_replaced(&queue);   /* Top element has been replaced */
+     }
+@@ -1018,23 +1019,23 @@
+       }
+     }
+   }
+-  while ((error=(int) info->read_to_buffer(from_file,buffpek,sort_length)) != -1 &&
+-         error != 0);
++  while ((error= info->read_to_buffer(from_file,buffpek,sort_length))
++         != (ulong) -1 && error != 0);
+   lastbuff->count=count;
+   if (to_file)
+     lastbuff->file_pos=to_start_filepos;
+ err:
+   delete_queue(&queue);
+-  DBUG_RETURN(error);
++  DBUG_RETURN(error != 0);
+ } /* merge_buffers */
+         /* Do a merge to output-file (save only positions) */
+ static int
+-merge_index(MI_SORT_PARAM *info, uint keys, uchar **sort_keys,
+-            BUFFPEK *buffpek, int maxbuffer, IO_CACHE *tempfile)
++merge_index(MI_SORT_PARAM *info, ulong keys, uchar **sort_keys,
++            BUFFPEK *buffpek, long maxbuffer, IO_CACHE *tempfile)
+ {
+   DBUG_ENTER("merge_index");
+   if (merge_buffers(info,keys,tempfile,(IO_CACHE*) 0,sort_keys,buffpek,buffpek,
+--- /dev/null
++++ b/mysql-test/r/percona_bug45702.result
+@@ -0,0 +1,21 @@
++CREATE TABLE t1 (a BIGINT NOT NULL AUTO_INCREMENT PRIMARY KEY) ENGINE=MyISAM;
++INSERT INTO t1 VALUES (), (), (), (), (), (), (), ();
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++SET @old_myisam_sort_buffer_size = @@myisam_sort_buffer_size;
++SET @@myisam_sort_buffer_size = 4 * 1024 * 1024 * 1024;
++REPAIR TABLE t1;
++Table Op      Msg_type        Msg_text
++test.t1       repair  status  OK
++- recovering (with sort) MyISAM-table 'MYSQLD_DATADIR/test/t1'
++Data records: 4096
++- Fixing index 1
++SET @@myisam_sort_buffer_size = @old_myisam_sort_buffer_size;
++DROP TABLE t1;
+--- /dev/null
++++ b/mysql-test/t/percona_bug45702.test
+@@ -0,0 +1,34 @@
++###############################################################################
++# Bug #45702: Impossible to specify myisam_sort_buffer > 4GB on 64 bit machines
++###############################################################################
++
++--source include/have_64bit.inc
++
++# Check that having data larger than MIN_SORT_BUFFER bytes can be handled by
++# _create_index_by_sort() with myisam_sort_buffer_size = 4 GB without errors.
++# The full test with large data volumes can not be a part of the test suite.
++
++CREATE TABLE t1 (a BIGINT NOT NULL AUTO_INCREMENT PRIMARY KEY) ENGINE=MyISAM;
++INSERT INTO t1 VALUES (), (), (), (), (), (), (), ();
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++INSERT INTO t1 SELECT NULL FROM t1;
++
++SET @old_myisam_sort_buffer_size = @@myisam_sort_buffer_size;
++SET @@myisam_sort_buffer_size = 4 * 1024 * 1024 * 1024;
++
++REPAIR TABLE t1;
++
++--let $MYSQLD_DATADIR= `select @@datadir`
++--replace_result $MYSQLD_DATADIR MYSQLD_DATADIR
++--exec $MYISAMCHK -r --sort_buffer_size=4G $MYSQLD_DATADIR/test/t1
++
++SET @@myisam_sort_buffer_size = @old_myisam_sort_buffer_size;
++
++DROP TABLE t1;
+--- a/sql/opt_range.cc
++++ b/sql/opt_range.cc
+@@ -11716,7 +11716,7 @@
+   }
+   if (min_max_ranges.elements > 0)
+   {
+-    fprintf(DBUG_FILE, "%*susing %d quick_ranges for MIN/MAX:\n",
++    fprintf(DBUG_FILE, "%*susing %lu quick_ranges for MIN/MAX:\n",
+             indent, "", min_max_ranges.elements);
+   }
+ }
+--- a/mysys/my_pread.c
++++ b/mysys/my_pread.c
+@@ -49,6 +49,7 @@
+                 myf MyFlags)
+ {
+   size_t readbytes;
++  size_t total_readbytes= 0;
+   int error= 0;
+ #if !defined (HAVE_PREAD) && !defined (_WIN32)
+   int save_errno;
+@@ -76,8 +77,30 @@
+ #endif
+     error= (readbytes != Count);
+ #endif
++    if (readbytes > 0)
++      total_readbytes+= readbytes;
++
+     if(error)
+     {
++      if (readbytes > 0 && readbytes < Count && errno == 0)
++      {
++        /*
++          pread() may return less bytes than requested even if enough bytes are
++          available according to the Linux man page.
++          This makes determining the end-of-file condition a bit harder.
++          We just do another pread() call to see if more bytes can be read,
++          since all my_pread() users expect it to always return all available
++          bytes. For end-of-file 0 bytes is returned. This can never be the case
++          for a partial read, since according to the man page, -1 is returned
++          with errno set to EINTR if no data has been read.
++        */
++        Buffer+= readbytes;
++        offset+= readbytes;
++        Count-= readbytes;
++
++        continue;
++      }
++
+       my_errno= errno ? errno : -1;
+       if (errno == 0 || (readbytes != (size_t) -1 &&
+                       (MyFlags & (MY_NABP | MY_FNABP))))
+@@ -107,7 +130,7 @@
+     }
+     if (MyFlags & (MY_NABP | MY_FNABP))
+       DBUG_RETURN(0);                      /* Read went ok; Return 0 */
+-    DBUG_RETURN(readbytes);                /* purecov: inspected */
++    DBUG_RETURN(total_readbytes);                /* purecov: inspected */
+   }
+ } /* my_pread */
+--- a/storage/myisam/myisamdef.h
++++ b/storage/myisam/myisamdef.h
+@@ -340,10 +340,10 @@
+   int (*key_write)(struct st_mi_sort_param *, const void *);
+   void (*lock_in_memory)(MI_CHECK *);
+   int (*write_keys)(struct st_mi_sort_param *, register uchar **,
+-                    uint , struct st_buffpek *, IO_CACHE *);
+-  uint (*read_to_buffer)(IO_CACHE *,struct st_buffpek *, uint);
++                    ulong , struct st_buffpek *, IO_CACHE *);
++  ulong (*read_to_buffer)(IO_CACHE *,struct st_buffpek *, uint);
+   int (*write_key)(struct st_mi_sort_param *, IO_CACHE *,uchar *,
+-                   uint, uint);
++                   uint, ulong);
+ } MI_SORT_PARAM;
+       /* Some defines used by isam-funktions */
+--- a/sql/rpl_mi.cc
++++ b/sql/rpl_mi.cc
+@@ -491,7 +491,7 @@
+                          (1 + mi->ignore_server_ids.elements), MYF(MY_WME));
+     if (!ignore_server_ids_buf)
+       DBUG_RETURN(1);
+-    ulong cur_len= sprintf(ignore_server_ids_buf, "%u",
++    ulong cur_len= sprintf(ignore_server_ids_buf, "%lu",
+                            mi->ignore_server_ids.elements);
+     for (ulong i= 0; i < mi->ignore_server_ids.elements; i++)
+     {
index ae154782371c5504bf844e35e2aebb4fc98d9479..5904490fae9c8804c332a60fc6ffaccbc2f80ee4 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/sql/sql_base.cc
 +++ b/sql/sql_base.cc
-@@ -251,8 +251,12 @@
+@@ -314,8 +314,12 @@
                            const TABLE_LIST *table_list,
                            bool tmp_table)
  {
@@ -24,7 +24,7 @@
      int4store(key + key_length, thd->server_id);
 --- a/sql/sql_parse.cc
 +++ b/sql/sql_parse.cc
-@@ -1112,11 +1112,18 @@
+@@ -1113,11 +1113,18 @@
      break;
  #else
    {
@@ -44,7 +44,7 @@
      /*
        SHOW statements should not add the used tables to the list of tables
        used in a transaction.
-@@ -1129,24 +1136,23 @@
+@@ -1130,24 +1137,23 @@
      /*
        We have name + wildcard in packet, separated by endzero
      */
@@ -81,7 +81,7 @@
      mysql_reset_thd_for_next_command(thd);
      lex_start(thd);
      /* Must be before we init the table list. */
-@@ -1171,9 +1177,6 @@
+@@ -1172,9 +1178,6 @@
          table_list.schema_table= schema_table;
      }
  
diff --git a/bug860910.patch b/bug860910.patch
new file mode 100644 (file)
index 0000000..20d2251
--- /dev/null
@@ -0,0 +1,92 @@
+# name       : bug860910.patch
+# maintainer : Alexey
+#
+# Fixes LP bug #860910 / MySQL bug #62557
+#
+--- /dev/null
++++ b/mysql-test/suite/rpl/r/percona_bug860910.result
+@@ -0,0 +1,17 @@
++*** Set up master (server_1) <-> master (server_2) replication  ***
++include/rpl_init.inc [topology=1->2->1]
++
++SELECT @@global.log_slave_updates;
++@@global.log_slave_updates
++1
++SELECT @@global.log_slave_updates;
++@@global.log_slave_updates
++1
++CREATE TABLE t1(a INT);
++SET @var:=0;
++INSERT INTO t1 VALUES (@var);
++INSERT INTO t1 VALUES (1);
++DROP TABLE t1;
++include/rpl_sync.inc
++include/check_slave_param.inc [Exec_Master_Log_Pos]
++include/rpl_end.inc
+--- /dev/null
++++ b/mysql-test/suite/rpl/t/percona_bug860910.cnf
+@@ -0,0 +1,8 @@
++!include ../my.cnf
++
++[mysqld.1]
++log-slave-updates
++
++[mysqld.2]
++log-slave-updates
++
+--- /dev/null
++++ b/mysql-test/suite/rpl/t/percona_bug860910.test
+@@ -0,0 +1,38 @@
++########################################################################
++# Bug #860910: SHOW SLAVE STATUS gives wrong output with master-master
++#              and using SET uservars
++########################################################################
++
++--echo *** Set up master (server_1) <-> master (server_2) replication  ***
++--let $rpl_topology= 1->2->1
++--source include/rpl_init.inc
++--echo
++
++--connection server_1
++SELECT @@global.log_slave_updates;
++
++--connection server_2
++SELECT @@global.log_slave_updates;
++
++--connection server_1
++CREATE TABLE t1(a INT);
++SET @var:=0;
++INSERT INTO t1 VALUES (@var);
++INSERT INTO t1 VALUES (1);
++
++DROP TABLE t1;
++
++# The following would hang with the bug not fixed due to incorrect
++# Exec_Master_Log_Pos
++--source include/rpl_sync.inc
++
++--connection server_2
++--let $master_log_pos= query_get_value(SHOW MASTER STATUS, Position, 1)
++
++--connection server_1
++--let $slave_param= Exec_Master_Log_Pos
++--let $slave_param_value= $master_log_pos
++--source include/check_slave_param.inc
++
++# Cleanup
++--source include/rpl_end.inc
+--- a/sql/log.cc
++++ b/sql/log.cc
+@@ -5090,6 +5090,12 @@
+                                  user_var_event->type,
+                                  user_var_event->charset_number,
+                                  flags);
++             /*
++               These User_var_log_events must be logged with event_info's
++               server_id, rather than the current one.
++             */
++             e.server_id= event_info->server_id;
++
+             if (e.write(file))
+               goto err;
+             if (file == &log_file)
index 0f1a736e56a0f100fc4eb554fbc98dc6223a5d9a..f42e243f416250875d3078a9823ffab2ec8ea59f 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/btr/btr0btr.c
 +++ b/storage/innobase/btr/btr0btr.c
-@@ -1518,7 +1518,7 @@
+@@ -1523,7 +1523,7 @@
        }
        ut_a(block);
  
@@ -16,7 +16,7 @@
  
        header = buf_block_get_frame(block) + PAGE_HEADER + PAGE_BTR_SEG_TOP;
  #ifdef UNIV_BTR_DEBUG
-@@ -1587,7 +1587,7 @@
+@@ -1592,7 +1592,7 @@
  
  #ifndef UNIV_HOTBACKUP
        if (UNIV_LIKELY(!recovery)) {
@@ -25,7 +25,7 @@
        }
  
        block->check_index_page_at_flush = TRUE;
-@@ -1755,7 +1755,7 @@
+@@ -1760,7 +1760,7 @@
        ut_a(!page_zip || page_zip_validate(page_zip, page));
  #endif /* UNIV_ZIP_DEBUG */
  
@@ -34,7 +34,7 @@
        btr_blob_dbg_remove(page, index, "btr_page_empty");
  
        /* Recreate the page: note that global data on page (possible
-@@ -3066,7 +3066,7 @@
+@@ -3093,7 +3093,7 @@
                mem_heap_free(heap);
        }
  
@@ -43,7 +43,7 @@
  
        /* Make the father empty */
        btr_page_empty(father_block, father_page_zip, index, page_level, mtr);
-@@ -3300,7 +3300,7 @@
+@@ -3317,7 +3317,7 @@
                        goto err_exit;
                }
  
@@ -51,8 +51,8 @@
 +              btr_search_drop_page_hash_index(block, index);
  
                /* Remove the page from the level list */
-               btr_level_list_remove(space, zip_size, page, mtr);
-@@ -3345,7 +3345,7 @@
+               btr_level_list_remove(space, zip_size, page, index, mtr);
+@@ -3358,7 +3358,7 @@
                        goto err_exit;
                }
  
@@ -61,7 +61,7 @@
  
  #ifdef UNIV_BTR_DEBUG
                if (UNIV_LIKELY_NULL(merge_page_zip)) {
-@@ -3469,7 +3469,7 @@
+@@ -3473,7 +3473,7 @@
                ut_a(btr_page_get_next(page, mtr) == FIL_NULL);
  
                ut_ad(mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
@@ -70,7 +70,7 @@
  
                btr_page_get_father(index, block, mtr, &cursor);
                father = btr_cur_get_block(&cursor);
-@@ -3574,7 +3574,7 @@
+@@ -3578,7 +3578,7 @@
  
        page = buf_block_get_frame(block);
        ut_a(page_is_comp(merge_page) == page_is_comp(page));
@@ -81,7 +81,7 @@
  
 --- a/storage/innobase/btr/btr0cur.c
 +++ b/storage/innobase/btr/btr0cur.c
-@@ -498,7 +498,7 @@
+@@ -502,7 +502,7 @@
  #ifdef UNIV_SEARCH_PERF_STAT
        info->n_searches++;
  #endif
@@ -90,7 +90,7 @@
            && latch_mode <= BTR_MODIFY_LEAF
            && info->last_hash_succ
            && !estimate
-@@ -534,7 +534,7 @@
+@@ -538,7 +538,7 @@
  
        if (has_search_latch) {
                /* Release possible search latch to obey latching order */
@@ -99,7 +99,7 @@
        }
  
        /* Store the position of the tree latch we push to mtr so that we
-@@ -856,7 +856,7 @@
+@@ -862,7 +862,7 @@
  
        if (has_search_latch) {
  
        }
  }
  
-@@ -1971,7 +1971,7 @@
+@@ -1992,13 +1992,13 @@
                        btr_search_update_hash_on_delete(cursor);
                }
  
 +              rw_lock_x_lock(btr_search_get_latch(cursor->index->id));
        }
  
-       if (!(flags & BTR_KEEP_SYS_FLAG)) {
-@@ -1985,7 +1985,7 @@
        row_upd_rec_in_place(rec, index, offsets, update, page_zip);
  
-       if (block->is_hashed) {
+       if (is_hashed) {
 -              rw_lock_x_unlock(&btr_search_latch);
 +              rw_lock_x_unlock(btr_search_get_latch(cursor->index->id));
        }
  
        if (page_zip && !dict_index_is_clust(index)
-@@ -2824,7 +2824,7 @@
-       }
-       if (block->is_hashed) {
--              rw_lock_x_lock(&btr_search_latch);
-+              rw_lock_x_lock(btr_search_get_latch(index->id));
-       }
-       page_zip = buf_block_get_page_zip(block);
-@@ -2840,7 +2840,7 @@
-       }
-       if (block->is_hashed) {
--              rw_lock_x_unlock(&btr_search_latch);
-+              rw_lock_x_unlock(btr_search_get_latch(index->id));
-       }
-       btr_cur_del_mark_set_clust_rec_log(flags, rec, index, val, trx,
-@@ -2967,13 +2967,13 @@
-             == dict_table_is_comp(cursor->index->table));
-       if (block->is_hashed) {
--              rw_lock_x_lock(&btr_search_latch);
-+              rw_lock_x_lock(btr_search_get_latch(cursor->index->id));
-       }
-       btr_rec_set_deleted_flag(rec, buf_block_get_page_zip(block), val);
-       if (block->is_hashed) {
--              rw_lock_x_unlock(&btr_search_latch);
-+              rw_lock_x_unlock(btr_search_get_latch(cursor->index->id));
-       }
-       btr_cur_del_mark_set_sec_rec_log(rec, val, mtr);
 --- a/storage/innobase/btr/btr0sea.c
 +++ b/storage/innobase/btr/btr0sea.c
 @@ -48,6 +48,8 @@
        }
  
        if (build_index) {
-@@ -881,17 +909,17 @@
+@@ -882,17 +910,17 @@
        cursor->flag = BTR_CUR_HASH;
  
        if (UNIV_LIKELY(!has_search_latch)) {
  
        if (UNIV_UNLIKELY(!rec)) {
                goto failure_unlock;
-@@ -909,7 +937,7 @@
+@@ -910,7 +938,7 @@
                        goto failure_unlock;
                }
  
  
                buf_block_dbg_add_level(block, SYNC_TREE_NODE_FROM_HASH);
        }
-@@ -1006,7 +1034,7 @@
+@@ -1007,7 +1035,7 @@
        /*-------------------------------------------*/
  failure_unlock:
        if (UNIV_LIKELY(!has_search_latch)) {
        }
  failure:
        cursor->flag = BTR_CUR_HASH_FAIL;
-@@ -1029,10 +1057,11 @@
+@@ -1030,10 +1058,11 @@
  void
  btr_search_drop_page_hash_index(
  /*============================*/
  {
        hash_table_t*           table;
        ulint                   n_fields;
-@@ -1051,22 +1080,60 @@
+@@ -1052,22 +1081,60 @@
        ulint*                  offsets;
  
  #ifdef UNIV_SYNC_DEBUG
  
  #ifdef UNIV_SYNC_DEBUG
        ut_ad(rw_lock_own(&(block->lock), RW_LOCK_SHARED)
-@@ -1076,14 +1143,14 @@
+@@ -1077,14 +1144,14 @@
  
        n_fields = block->curr_n_fields;
        n_bytes = block->curr_n_bytes;
  
        ut_a(n_fields + n_bytes > 0);
  
-@@ -1133,7 +1200,7 @@
+@@ -1134,7 +1201,7 @@
                mem_heap_free(heap);
        }
  
  
        if (UNIV_UNLIKELY(!block->is_hashed)) {
                /* Someone else has meanwhile dropped the hash index */
-@@ -1149,7 +1216,7 @@
+@@ -1150,7 +1217,7 @@
                /* Someone else has meanwhile built a new hash index on the
                page, with different parameters */
  
  
                mem_free(folds);
                goto retry;
-@@ -1165,6 +1232,7 @@
+@@ -1166,6 +1233,7 @@
  
        block->is_hashed = FALSE;
        block->index = NULL;
        
  cleanup:
  #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG
-@@ -1177,14 +1245,14 @@
+@@ -1178,14 +1246,14 @@
                        "InnoDB: the hash index to a page of %s,"
                        " still %lu hash nodes remain.\n",
                        index->name, (ulong) block->n_pointers);
  #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
  
        mem_free(folds);
-@@ -1216,9 +1284,9 @@
+@@ -1217,9 +1285,9 @@
        ulint*          offsets;
        ibool           released_search_latch;
  
  
        for (j = 0; j < srv_buf_pool_instances; j++) {
                buf_pool_t*     buf_pool;
-@@ -1252,7 +1320,7 @@
+@@ -1253,7 +1321,7 @@
  
  
                                        /* keeping latch order */
                                        released_search_latch = TRUE;
                                        rw_lock_x_lock(&block->lock);
  
-@@ -1304,7 +1372,7 @@
+@@ -1305,7 +1373,7 @@
                                                mem_heap_empty(heap);
                                        }
  
  
                                        if (UNIV_UNLIKELY(!block->is_hashed)) {
                                                goto cleanup;
-@@ -1314,12 +1382,12 @@
+@@ -1315,12 +1383,12 @@
  
                                        if (UNIV_UNLIKELY(block->curr_n_fields != n_fields)
                                            || UNIV_UNLIKELY(block->curr_n_bytes != n_bytes)) {
                                                goto retry;
                                        }
  
-@@ -1333,6 +1401,7 @@
+@@ -1334,6 +1402,7 @@
  
                                        block->is_hashed = FALSE;
                                        block->index = NULL;
  
  cleanup:
  #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG
-@@ -1345,18 +1414,18 @@
+@@ -1346,18 +1415,18 @@
                                                        index->name, (ulong) block->n_pointers);
                                        }
  #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
  
        if (UNIV_LIKELY_NULL(heap)) {
                mem_heap_free(heap);
-@@ -1403,7 +1472,7 @@
+@@ -1404,7 +1473,7 @@
  
                buf_block_dbg_add_level(block, SYNC_TREE_NODE_FROM_HASH);
  
        }
  
        mtr_commit(&mtr);
-@@ -1445,26 +1514,26 @@
+@@ -1446,26 +1515,26 @@
        ut_ad(index);
        ut_a(!dict_index_is_ibuf(index));
  
        }
  
        n_recs = page_get_n_recs(page);
-@@ -1558,9 +1627,9 @@
+@@ -1559,9 +1628,9 @@
                fold = next_fold;
        }
  
  
        if (UNIV_UNLIKELY(btr_search_fully_disabled)) {
                goto exit_func;
-@@ -1588,6 +1657,7 @@
+@@ -1589,6 +1658,7 @@
        block->curr_n_bytes = n_bytes;
        block->curr_left_side = left_side;
        block->index = index;
  
        for (i = 0; i < n_cached; i++) {
  
-@@ -1595,7 +1665,7 @@
+@@ -1596,7 +1666,7 @@
        }
  
  exit_func:
  
        mem_free(folds);
        mem_free(recs);
-@@ -1634,13 +1704,13 @@
+@@ -1635,13 +1705,13 @@
        ut_a(!(new_block->is_hashed || block->is_hashed)
             || !dict_index_is_ibuf(index));
  
  
                return;
        }
-@@ -1655,7 +1725,7 @@
+@@ -1656,7 +1726,7 @@
                new_block->n_bytes = block->curr_n_bytes;
                new_block->left_side = left_side;
  
  
                ut_a(n_fields + n_bytes > 0);
  
-@@ -1667,7 +1737,7 @@
+@@ -1668,7 +1738,7 @@
                return;
        }
  
  }
  
  /********************************************************************//**
-@@ -1706,7 +1776,7 @@
+@@ -1707,7 +1777,7 @@
        ut_a(block->curr_n_fields + block->curr_n_bytes > 0);
        ut_a(!dict_index_is_ibuf(cursor->index));
  
  
        index_id = cursor->index->id;
        fold = rec_fold(rec, rec_get_offsets(rec, cursor->index, offsets_,
-@@ -1715,11 +1785,11 @@
+@@ -1716,11 +1786,11 @@
        if (UNIV_LIKELY_NULL(heap)) {
                mem_heap_free(heap);
        }
  }
  
  /********************************************************************//**
-@@ -1753,21 +1823,21 @@
+@@ -1754,21 +1824,21 @@
        ut_a(block->index == cursor->index);
        ut_a(!dict_index_is_ibuf(cursor->index));
  
  
                btr_search_update_hash_on_insert(cursor);
        }
-@@ -1802,9 +1872,9 @@
+@@ -1803,9 +1873,9 @@
        ulint*          offsets         = offsets_;
        rec_offs_init(offsets_);
  
  
        rec = btr_cur_get_rec(cursor);
  
-@@ -1849,7 +1919,7 @@
+@@ -1850,7 +1920,7 @@
        } else {
                if (left_side) {
  
  
                        locked = TRUE;
  
-@@ -1863,7 +1933,7 @@
+@@ -1864,7 +1934,7 @@
  
                if (!locked) {
  
  
                        locked = TRUE;
                }
-@@ -1881,7 +1951,7 @@
+@@ -1882,7 +1952,7 @@
                if (!left_side) {
  
                        if (!locked) {
  
                                locked = TRUE;
                        }
-@@ -1896,7 +1966,7 @@
+@@ -1897,7 +1967,7 @@
  
                if (!locked) {
  
  
                        locked = TRUE;
                }
-@@ -1919,7 +1989,7 @@
+@@ -1920,7 +1990,7 @@
                mem_heap_free(heap);
        }
        if (locked) {
        }
  }
  
-@@ -1935,7 +2005,7 @@
+@@ -1936,7 +2006,7 @@
        ha_node_t*      node;
        ulint           n_page_dumps    = 0;
        ibool           ok              = TRUE;
        ulint           cell_count;
        mem_heap_t*     heap            = NULL;
        ulint           offsets_[REC_OFFS_NORMAL_SIZE];
-@@ -1947,23 +2017,25 @@
+@@ -1948,23 +2018,25 @@
  
        rec_offs_init(offsets_);
  
  
                for (; node != NULL; node = node->next) {
                        const buf_block_t*      block
-@@ -2072,19 +2144,21 @@
+@@ -2073,19 +2145,21 @@
                give other queries a chance to run. */
                if (i != 0) {
                        buf_pool_page_hash_x_unlock_all();
        }
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -949,6 +949,7 @@
+@@ -950,6 +950,7 @@
  
        block->check_index_page_at_flush = FALSE;
        block->index = NULL;
  
        block->is_hashed = FALSE;
  
-@@ -1413,7 +1414,7 @@
+@@ -1414,7 +1415,7 @@
                        /* To follow the latching order, we
                        have to release btr_search_latch
                        before acquiring block->latch. */
                        /* When we release the search latch,
                        we must rescan all blocks, because
                        some may become hashed again. */
-@@ -1444,11 +1445,11 @@
+@@ -1445,11 +1446,11 @@
                        anything.  block->is_hashed can only
                        be set on uncompressed file pages. */
  
  
                        ut_ad(!btr_search_enabled);
                }
-@@ -1467,7 +1468,11 @@
+@@ -1468,7 +1469,11 @@
        ibool           released_search_latch;
  
  #ifdef UNIV_SYNC_DEBUG
  #endif /* UNIV_SYNC_DEBUG */
        ut_ad(!btr_search_enabled);
  
-@@ -2203,6 +2208,7 @@
+@@ -2204,6 +2209,7 @@
  {
        block->check_index_page_at_flush = FALSE;
        block->index            = NULL;
  
 --- a/storage/innobase/dict/dict0dict.c
 +++ b/storage/innobase/dict/dict0dict.c
-@@ -1845,7 +1845,7 @@
+@@ -1846,7 +1846,7 @@
        zero. */
  
        for (;;) {
  #ifndef UNIV_HOTBACKUP
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -11718,6 +11718,11 @@
+@@ -11824,6 +11824,11 @@
    "Disable with --skip-innodb-adaptive-hash-index.",
    NULL, innodb_adaptive_hash_index_update, TRUE);
  
  static MYSQL_SYSVAR_ULONG(replication_delay, srv_replication_delay,
    PLUGIN_VAR_RQCMDARG,
    "Replication thread delay (ms) on the slave server if "
-@@ -12085,6 +12090,7 @@
+@@ -12204,6 +12209,7 @@
    MYSQL_SYSVAR(use_sys_stats_table),
    MYSQL_SYSVAR(stats_sample_pages),
    MYSQL_SYSVAR(adaptive_hash_index),
 +
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1585,7 +1585,7 @@
+@@ -1576,7 +1576,7 @@
                                        pointers in the adaptive hash index
                                        pointing to this frame */
  #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
                                        already been built on this
                                        page; note that it does not
                                        guarantee that the index is
-@@ -1599,6 +1599,7 @@
+@@ -1590,6 +1590,7 @@
        unsigned        curr_left_side:1;/*!< TRUE or FALSE in hash indexing */
        dict_index_t*   index;          /*!< Index for which the adaptive
                                        hash index has been created. */
        /* @} */
  # ifdef UNIV_SYNC_DEBUG
        /** @name Debug fields */
---- a/storage/innobase/include/row0upd.ic
-+++ b/storage/innobase/include/row0upd.ic
-@@ -158,7 +158,7 @@
-       ut_ad(dict_index_is_clust(index));
-       ut_ad(rec_offs_validate(rec, index, offsets));
- #ifdef UNIV_SYNC_DEBUG
--      if (!rw_lock_own(&btr_search_latch, RW_LOCK_EX)) {
-+      if (!rw_lock_own(btr_search_get_latch(index->id), RW_LOCK_EX)) {
-               ut_ad(!buf_block_align(rec)->is_hashed);
-       }
- #endif /* UNIV_SYNC_DEBUG */
 --- a/storage/innobase/page/page0page.c
 +++ b/storage/innobase/page/page0page.c
 @@ -218,7 +218,7 @@
        ut_ad(block == back_block1);
 --- a/storage/innobase/row/row0mysql.c
 +++ b/storage/innobase/row/row0mysql.c
-@@ -2593,7 +2593,7 @@
+@@ -2594,7 +2594,7 @@
                        /* check adaptive hash entries */
                        index = dict_table_get_first_index(table);
                        while (index) {
                                if (ref_count) {
                                        fprintf(stderr, "InnoDB: Warning:"
                                                " hash index ref_count (%lu) is not zero"
-@@ -2954,7 +2954,7 @@
+@@ -2955,7 +2955,7 @@
                        table->space = space;
                        index = dict_table_get_first_index(table);
                        do {
                                        fprintf(stderr, "InnoDB: Warning:"
 --- a/storage/innobase/row/row0sel.c
 +++ b/storage/innobase/row/row0sel.c
-@@ -1211,7 +1211,7 @@
+@@ -1222,7 +1222,7 @@
        ut_ad(plan->unique_search);
        ut_ad(!plan->must_get_clust);
  #ifdef UNIV_SYNC_DEBUG
  #endif /* UNIV_SYNC_DEBUG */
  
        row_sel_open_pcur(plan, TRUE, mtr);
-@@ -1382,10 +1382,10 @@
+@@ -1393,10 +1393,10 @@
            && !plan->must_get_clust
            && !plan->table->big_rows) {
                if (!search_latch_locked) {
  
                        /* There is an x-latch request waiting: release the
                        s-latch for a moment; as an s-latch here is often
-@@ -1394,8 +1394,8 @@
+@@ -1405,8 +1405,8 @@
                        from acquiring an s-latch for a long time, lowering
                        performance significantly in multiprocessors. */
  
                }
  
                found_flag = row_sel_try_search_shortcut(node, plan, &mtr);
-@@ -1418,7 +1418,7 @@
+@@ -1429,7 +1429,7 @@
        }
  
        if (search_latch_locked) {
  
                search_latch_locked = FALSE;
        }
-@@ -1994,7 +1994,7 @@
+@@ -2005,7 +2005,7 @@
  
  func_exit:
        if (search_latch_locked) {
        }
        if (UNIV_LIKELY_NULL(heap)) {
                mem_heap_free(heap);
-@@ -3357,6 +3357,8 @@
+@@ -3408,6 +3408,8 @@
        /* if the returned record was locked and we did a semi-consistent
        read (fetch the newest committed version), then this is set to
        TRUE */
  #ifdef UNIV_SEARCH_DEBUG
        ulint           cnt                             = 0;
  #endif /* UNIV_SEARCH_DEBUG */
-@@ -3447,18 +3449,33 @@
+@@ -3505,18 +3507,33 @@
        /* PHASE 0: Release a possible s-latch we are holding on the
        adaptive hash index latch if there is someone waiting behind */
  
        }
  
        /* Reset the new record lock info if srv_locks_unsafe_for_binlog
-@@ -3609,9 +3626,28 @@
+@@ -3667,9 +3684,28 @@
                        hash index semaphore! */
  
  #ifndef UNIV_SEARCH_DEBUG
                        }
  #endif
                        switch (row_sel_try_search_shortcut_for_mysql(
-@@ -3672,7 +3708,11 @@
+@@ -3730,7 +3766,11 @@
  
                                        trx->search_latch_timeout--;
  
                                        trx->has_search_latch = FALSE;
                                }
  
-@@ -3696,7 +3736,12 @@
+@@ -3754,7 +3794,12 @@
        /* PHASE 3: Open or restore index cursor position */
  
        if (trx->has_search_latch) {
  
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -2045,7 +2045,9 @@
+@@ -2051,7 +2051,9 @@
              "-------------------------------------\n", file);
        ibuf_print(file);
  
  
        fprintf(file,
                "%.2f hash searches/s, %.2f non-hash searches/s\n",
-@@ -2070,14 +2072,15 @@
+@@ -2076,14 +2078,15 @@
                        ut_total_allocated_memory,
                        mem_pool_get_reserved(mem_comm_pool));
        /* Calcurate reserved memories */
  
        lock_sys_subtotal = 0;
        if (trx_sys) {
-@@ -2103,10 +2106,10 @@
+@@ -2109,10 +2112,10 @@
                        "    Recovery system     %lu \t(%lu + %lu)\n",
  
                        (ulong) (btr_search_sys
                        (ulong) (buf_pool_from_array(0)->page_hash->n_cells * sizeof(hash_cell_t)),
 --- a/storage/innobase/sync/sync0sync.c
 +++ b/storage/innobase/sync/sync0sync.c
-@@ -1228,7 +1228,6 @@
+@@ -1222,7 +1222,6 @@
        case SYNC_OUTER_ANY_LATCH:
        case SYNC_FILE_FORMAT_TAG:
        case SYNC_DOUBLEWRITE:
        case SYNC_SEARCH_SYS_CONF:
        case SYNC_TRX_LOCK_HEAP:
        case SYNC_KERNEL:
-@@ -1249,6 +1248,7 @@
+@@ -1244,6 +1243,7 @@
                        ut_error;
                }
                break;
index 8cb782b64e6295c9a0667331500521424ce5ae94..7c93c5f88350ca41bd2695029bea1e9774a52ffe 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -11880,7 +11880,8 @@
+@@ -11990,7 +11990,8 @@
  i_s_innodb_sys_foreign_cols,
  i_s_innodb_sys_stats,
  i_s_innodb_table_stats,
@@ -19,7 +19,7 @@
  /** @brief Initialize the default value of innodb_commit_concurrency.
 --- a/storage/innobase/handler/i_s.cc
 +++ b/storage/innobase/handler/i_s.cc
-@@ -4177,3 +4177,139 @@
+@@ -4205,3 +4205,139 @@
        STRUCT_FLD(system_vars, NULL),
        STRUCT_FLD(__reserved1, NULL)
  };
 +--source include/have_innodb.inc
 +select * from information_schema.XTRADB_ADMIN_COMMAND;
 +select * from information_schema.XTRADB_ADMIN_COMMAND /*!XTRA_HELLO*/;
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -731,6 +731,10 @@
+  -V, --version       Output version information and exit.
+  --wait-timeout=#    The number of seconds the server waits for activity on a
+  connection before closing it
++ --xtradb-admin-command[=name] 
++ Enable or disable XTRADB_ADMIN_COMMAND plugin. Possible
++ values are ON, OFF, FORCE (don't start if the plugin
++ fails to load).
+ Variables (--variable-name=value)
+ abort-slave-event-count 0
+@@ -955,6 +959,7 @@
+ updatable-views-with-limit YES
+ verbose TRUE
+ wait-timeout 28800
++xtradb-admin-command ON
+ To see what values a running MySQL server is using, type
+ 'mysqladmin variables' instead of 'mysqld --verbose --help'.
index 151cb5a1a2bbaea6d742207c62cd0697b6e0adb2..0ff3d4deba337e6bf275bc57d7b3882ca1675c62 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -4157,6 +4157,36 @@
+@@ -4224,6 +4224,36 @@
        mutex_exit(block_mutex);
  }
  
@@ -46,7 +46,7 @@
  @return       TRUE */
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -12165,6 +12165,9 @@
+@@ -12287,6 +12287,9 @@
  i_s_innodb_sys_stats,
  i_s_innodb_table_stats,
  i_s_innodb_index_stats,
@@ -66,7 +66,7 @@
  }
  
  #define OK(expr)              \
-@@ -4344,3 +4345,701 @@
+@@ -4372,3 +4373,701 @@
        STRUCT_FLD(system_vars, NULL),
        STRUCT_FLD(__reserved1, NULL)
  };
  #endif /* i_s_h */
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1183,6 +1183,14 @@
+@@ -1174,6 +1174,14 @@
  /*===========*/
        const buf_pool_t*       buf_pool)       /*!< in: buffer pool */
        __attribute__((nonnull, const));
index e5c7b470d18bb9a0db6ccf6883585873355e5773..42b98a29bb9353bfda1ec1238b7cb349573614aa 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -1006,10 +1006,12 @@
+@@ -1007,10 +1007,12 @@
        buf_block_t*    block;
        byte*           frame;
        ulint           i;
@@ -20,7 +20,7 @@
        /* Reserve space for the block descriptors. */
        mem_size += ut_2pow_round((mem_size / UNIV_PAGE_SIZE) * (sizeof *block)
                                  + (UNIV_PAGE_SIZE - 1), UNIV_PAGE_SIZE);
-@@ -1047,6 +1049,10 @@
+@@ -1048,6 +1050,10 @@
                chunk->size = size;
        }
  
@@ -42,7 +42,7 @@
  
  
  static char*  internal_innobase_data_file_path        = NULL;
-@@ -2675,6 +2677,12 @@
+@@ -2706,6 +2708,12 @@
        srv_buf_pool_size = (ulint) innobase_buffer_pool_size;
        srv_buf_pool_instances = (ulint) innobase_buffer_pool_instances;
  
@@ -55,7 +55,7 @@
        srv_mem_pool_size = (ulint) innobase_additional_mem_pool_size;
  
        srv_n_file_io_threads = (ulint) innobase_file_io_threads;
-@@ -11749,6 +11757,16 @@
+@@ -11855,6 +11863,16 @@
    "Number of buffer pool instances, set to higher value on high-end machines to increase scalability",
    NULL, NULL, 1L, 1L, MAX_BUFFER_POOLS, 1L);
  
@@ -72,7 +72,7 @@
  static MYSQL_SYSVAR_ULONG(commit_concurrency, innobase_commit_concurrency,
    PLUGIN_VAR_RQCMDARG,
    "Helps in performance tuning in heavily concurrent environments.",
-@@ -12043,6 +12061,8 @@
+@@ -12161,6 +12179,8 @@
    MYSQL_SYSVAR(autoextend_increment),
    MYSQL_SYSVAR(buffer_pool_size),
    MYSQL_SYSVAR(buffer_pool_instances),
index 44ad06d07829493fc05c437a16cc986b670111fb..4e38012e267656bb795469b95b4a724f9c1d1e1f 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -687,6 +687,8 @@
+@@ -691,6 +691,8 @@
    (char*) &export_vars.innodb_dblwr_pages_written,      SHOW_LONG},
    {"dblwr_writes",
    (char*) &export_vars.innodb_dblwr_writes,             SHOW_LONG},
@@ -28,7 +28,7 @@
  Gets the size of a lock struct.
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -758,6 +758,7 @@
+@@ -767,6 +767,7 @@
        ulint innodb_buffer_pool_read_ahead_evicted;/*!< srv_read_ahead evicted*/
        ulint innodb_dblwr_pages_written;       /*!< srv_dblwr_pages_written */
        ulint innodb_dblwr_writes;              /*!< srv_dblwr_writes */
@@ -48,7 +48,7 @@
                break;
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -468,6 +468,7 @@
+@@ -474,6 +474,7 @@
  static ulint  srv_n_rows_deleted_old          = 0;
  static ulint  srv_n_rows_read_old             = 0;
  
@@ -56,7 +56,7 @@
  UNIV_INTERN ulint             srv_n_lock_wait_count           = 0;
  UNIV_INTERN ulint             srv_n_lock_wait_current_count   = 0;
  UNIV_INTERN ib_int64_t        srv_n_lock_wait_time            = 0;
-@@ -2282,6 +2283,7 @@
+@@ -2290,6 +2291,7 @@
        export_vars.innodb_buffer_pool_pages_data = LRU_len;
        export_vars.innodb_buffer_pool_pages_dirty = flush_list_len;
        export_vars.innodb_buffer_pool_pages_free = free_len;
index e524a0776856ac7b507f0ba72229eec0dd50d9f4..288b2686165fae3233630f3afdd192438f169f1a 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/btr/btr0sea.c
 +++ b/storage/innobase/btr/btr0sea.c
-@@ -1185,6 +1185,179 @@
+@@ -1186,6 +1186,179 @@
        mem_free(folds);
  }
  
  /****************************************************************//**
  If the given column name is reserved for InnoDB system columns, return
  TRUE.
-@@ -1762,6 +1824,11 @@
+@@ -1763,6 +1825,11 @@
        ut_ad(index->magic_n == DICT_INDEX_MAGIC_N);
        ut_ad(mutex_own(&(dict_sys->mutex)));
  
        info = index->search_info;
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -675,6 +675,8 @@
+@@ -677,6 +677,8 @@
    (char*) &export_vars.innodb_dblwr_pages_written,      SHOW_LONG},
    {"dblwr_writes",
    (char*) &export_vars.innodb_dblwr_writes,             SHOW_LONG},
    {"have_atomic_builtins",
    (char*) &export_vars.innodb_have_atomic_builtins,     SHOW_BOOL},
    {"log_waits",
-@@ -11658,6 +11660,11 @@
+@@ -11765,6 +11767,11 @@
    "Choose method of innodb_adaptive_flushing. (native, [estimate], keep_average)",
    NULL, innodb_adaptive_flushing_method_update, 1, &adaptive_flushing_method_typelib);
  
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(additional_mem_pool_size),
    MYSQL_SYSVAR(autoextend_increment),
-@@ -11726,6 +11733,7 @@
+@@ -11834,6 +11841,7 @@
    MYSQL_SYSVAR(flush_neighbor_pages),
    MYSQL_SYSVAR(read_ahead),
    MYSQL_SYSVAR(adaptive_flushing_method),
  Drops possible hash index if the page happens to be in the buffer pool. */
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1594,6 +1594,15 @@
+@@ -1585,6 +1585,15 @@
  #define BUF_POOL_ZIP_FOLD_BPAGE(b) BUF_POOL_ZIP_FOLD((buf_block_t*) (b))
  /* @} */
  
        ulint   n_page_gets;    /*!< number of page gets performed;
 --- a/storage/innobase/include/dict0dict.h
 +++ b/storage/innobase/include/dict0dict.h
-@@ -1183,6 +1183,12 @@
+@@ -1200,6 +1200,12 @@
  /*====================================*/
        dict_table_t*   table,  /*!< in: table */
        const char*     name);  /*!< in: name of the index to find */
  extern FILE*  dict_foreign_err_file;
 --- a/storage/innobase/include/dict0dict.ic
 +++ b/storage/innobase/include/dict0dict.ic
-@@ -824,6 +824,13 @@
+@@ -825,6 +825,13 @@
        HASH_SEARCH(name_hash, dict_sys->table_hash, table_fold,
                    dict_table_t*, table, ut_ad(table->cached),
                    !strcmp(table->name, table_name));
        return(table);
  }
  
-@@ -905,6 +912,12 @@
+@@ -918,6 +925,12 @@
                table = dict_load_table_on_id(table_id);
        }
  
        /* TODO: should get the type information from MySQL */
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -229,6 +229,7 @@
+@@ -234,6 +234,7 @@
  extern ulint  srv_read_ahead;
  extern ulint  srv_adaptive_flushing_method;
  
  /*-------------------------------------------*/
  
  extern ulint  srv_n_rows_inserted;
-@@ -709,6 +710,7 @@
+@@ -714,6 +715,7 @@
        ulint innodb_data_writes;               /*!< I/O write requests */
        ulint innodb_data_written;              /*!< Data bytes written */
        ulint innodb_data_reads;                /*!< I/O read requests */
        ulint innodb_buffer_pool_pages_dirty;   /*!< Dirty data pages */
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -415,6 +415,8 @@
+@@ -417,6 +417,8 @@
  UNIV_INTERN ulint     srv_enable_unsafe_group_commit = 0; /* 0:disable 1:enable */
  UNIV_INTERN ulint     srv_read_ahead = 3; /* 1: random  2: linear  3: Both */
  UNIV_INTERN ulint     srv_adaptive_flushing_method = 0; /* 0: native  1: estimate  2: keep_average */
  /*-------------------------------------------*/
  UNIV_INTERN ulong     srv_n_spin_wait_rounds  = 30;
  UNIV_INTERN ulong     srv_n_free_tickets_to_enter = 500;
-@@ -2220,6 +2222,7 @@
+@@ -2222,6 +2224,7 @@
        export_vars.innodb_data_reads = os_n_file_reads;
        export_vars.innodb_data_writes = os_n_file_writes;
        export_vars.innodb_data_written = srv_data_written;
index ed494611165fd4dc8d8bf55d3f0ea838933312b3..b40e995885d9876f179efbd45d77317705611002 100644 (file)
@@ -25,7 +25,7 @@
  
  #include "client_priv.h"
  #include "mysql.h"
-@@ -143,6 +144,8 @@
+@@ -145,6 +146,8 @@
  
  static my_bool server_supports_sql_no_fcache= FALSE;
  
@@ -34,7 +34,7 @@
  /*
  Dynamic_string wrapper functions. In this file use these
  wrappers, they will terminate the process if there is
-@@ -188,6 +191,8 @@
+@@ -190,6 +193,8 @@
  
  HASH ignore_table;
  
@@ -43,7 +43,7 @@
  static struct my_option my_long_options[] =
  {
    {"all-databases", 'A',
-@@ -351,6 +356,11 @@
+@@ -353,6 +358,11 @@
     "in dump produced with --dump-slave.", &opt_include_master_host_port,
     &opt_include_master_host_port, 0, GET_BOOL, NO_ARG,
     0, 0, 0, 0, 0, 0},
    {"insert-ignore", OPT_INSERT_IGNORE, "Insert rows with INSERT IGNORE.",
     &opt_ignore, &opt_ignore, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0,
     0, 0},
-@@ -2238,6 +2248,77 @@
+@@ -2240,6 +2250,189 @@
  }
  
  /*
++  Parse the specified key definition string and check if the key indexes
++  any of the columns from ignored_columns.
++*/
++static my_bool contains_ignored_column(HASH *ignored_columns, char *keydef)
++{
++  char *leftp, *rightp;
++
++  if ((leftp = strchr(keydef, '(')) &&
++      (rightp = strchr(leftp, ')')) &&
++      rightp > leftp + 3 &&                      /* (`...`) */
++      leftp[1] == '`' &&
++      rightp[-1] == '`' &&
++      my_hash_search(ignored_columns, (uchar *) leftp + 2, rightp - leftp - 3))
++    return TRUE;
++
++  return FALSE;
++}
++
++
++/*
 +  Remove secondary/foreign key definitions from a given SHOW CREATE TABLE string
 +  and store them into a temporary list to be used later.
 +
 +  SYNOPSIS
 +    skip_secondary_keys()
 +    create_str                SHOW CREATE TABLE output
++    has_pk                    TRUE, if the table has PRIMARY KEY
++                              (or UNIQUE key on non-nullable columns)
 +
 +
 +  DESCRIPTION
 +
-+    Stores all lines starting with "KEY" or "UNIQUE KEY" or "CONSTRAINT"
++    Stores all lines starting with "KEY" or "UNIQUE KEY"
 +    into skipped_keys_list and removes them from the input string.
 +    Ignoring FOREIGN KEYS constraints when creating the table is ok, because
 +    mysqldump sets foreign_key_checks to 0 anyway.
 +*/
 +
-+static void skip_secondary_keys(char *create_str)
++static void skip_secondary_keys(char *create_str, my_bool has_pk)
 +{
 +  char *ptr, *strend;
 +  char *last_comma = NULL;
++  HASH ignored_columns;
++  my_bool pk_processed= FALSE;
++
++  if (my_hash_init(&ignored_columns, charset_info, 16, 0, 0,
++                   (my_hash_get_key) get_table_key, my_free, 0))
++    exit(EX_EOM);
 +
 +  strend= create_str + strlen(create_str);
 +
 +  ptr= create_str;
 +  while (*ptr)
 +  {
-+    char *tmp, *orig_ptr;
++    char *tmp, *orig_ptr, c;
++    my_bool is_unique= FALSE;
 +
 +    orig_ptr= ptr;
 +    /* Skip leading whitespace */
 +    /* Read the next line */
 +    for (tmp= ptr; *tmp != '\n' && *tmp != '\0'; tmp++);
 +
++    c= *tmp;
++    *tmp= '\0'; /* so strstr() only processes the current line */
++
 +    /* Is it a secondary index definition? */
-+    if (*tmp == '\n' &&
-+        (!strncmp(ptr, "UNIQUE KEY ", sizeof("UNIQUE KEY ") - 1) ||
-+         !strncmp(ptr, "KEY ", sizeof("KEY ") - 1) ||
-+         !strncmp(ptr, "CONSTRAINT ", sizeof("CONSTRAINT ") - 1)))
++    if (c == '\n' &&
++        (((is_unique= !strncmp(ptr, "UNIQUE KEY ", sizeof("UNIQUE KEY ")-1)) &&
++          (pk_processed || !has_pk)) ||
++         !strncmp(ptr, "KEY ", sizeof("KEY ") - 1)) &&
++        !contains_ignored_column(&ignored_columns, ptr))
 +    {
 +      char *data, *end= tmp - 1;
 +
 +      if (last_comma != NULL)
 +      {
 +        *last_comma= ' ';
-+        last_comma = NULL;
 +      }
 +    }
 +    else
 +    {
++      char *end;
++
++      if (last_comma != NULL && *ptr != ')')
++      {
++        /*
++          It's not the last line of CREATE TABLE, so we have skipped a key
++          definition. We have to restore the last removed comma.
++        */
++        *last_comma= ',';
++      }
++
++      if ((has_pk && is_unique && !pk_processed) ||
++          !strncmp(ptr, "PRIMARY KEY ", sizeof("PRIMARY KEY ") - 1))
++        pk_processed= TRUE;
++
++      if (strstr(ptr, "AUTO_INCREMENT") && *ptr == '`')
++      {
++        /*
++          If a secondary key is defined on this column later,
++          it cannot be skipped, as CREATE TABLE would fail on import.
++        */
++        for (end= ptr + 1; *end != '`' && *end != '\0'; end++);
++        if (*end == '`' && end > ptr + 1 &&
++            my_hash_insert(&ignored_columns,
++                           (uchar *) my_strndup(ptr + 1,
++                                                end - ptr - 1, MYF(0))))
++        {
++          exit(EX_EOM);
++        }
++      }
++
++      *tmp= c;
++
 +      if (tmp[-1] == ',')
 +        last_comma= tmp - 1;
 +      ptr= (*tmp == '\0') ? tmp : tmp + 1;
 +    }
 +  }
++
++  my_hash_free(&ignored_columns);
 +}
 +
++/*
++  Check if the table has a primary key defined either explicitly or
++  implicitly (i.e. a unique key on non-nullable columns).
++
++  SYNOPSIS
++    my_bool has_primary_key(const char *table_name)
++
++    table_name  quoted table name
++
++  RETURNS     TRUE if the table has a primary key
++
++  DESCRIPTION
++*/
++
++static my_bool has_primary_key(const char *table_name)
++{
++  MYSQL_RES  *res= NULL;
++  MYSQL_ROW  row;
++  char query_buff[QUERY_LENGTH];
++  my_bool has_pk= TRUE;
++
++  my_snprintf(query_buff, sizeof(query_buff),
++              "SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE "
++              "TABLE_SCHEMA=DATABASE() AND TABLE_NAME='%s' AND "
++              "COLUMN_KEY='PRI'", table_name);
++  if (mysql_query(mysql, query_buff) || !(res= mysql_store_result(mysql)) ||
++      !(row= mysql_fetch_row(res)))
++  {
++    fprintf(stderr, "Warning: Couldn't determine if table %s has a "
++            "primary key (%s). "
++            "--innodb-optimize-keys may work inefficiently.\n",
++            table_name, mysql_error(mysql));
++    goto cleanup;
++  }
++
++  has_pk= atoi(row[0]) > 0;
++
++cleanup:
++  if (res)
++    mysql_free_result(res);
++
++  return has_pk;
++}
++
++
 +/*
    get_table_structure -- retrievs database structure, prints out corresponding
    CREATE statement and fills out insert_pat if the table is the type we will
    be dumping.
-@@ -2478,6 +2559,9 @@
+@@ -2276,6 +2469,7 @@
+   int        len;
+   MYSQL_RES  *result;
+   MYSQL_ROW  row;
++  my_bool    has_pk= FALSE;
+   DBUG_ENTER("get_table_structure");
+   DBUG_PRINT("enter", ("db: %s  table: %s", db, table));
+@@ -2317,6 +2511,9 @@
+   result_table=     quote_name(table, table_buff, 1);
+   opt_quoted_table= quote_name(table, table_buff2, 0);
++  if (opt_innodb_optimize_keys && !strcmp(table_type, "InnoDB"))
++    has_pk= has_primary_key(table);
++
+   if (opt_order_by_primary)
+     order_by= primary_key_fields(result_table);
+@@ -2480,6 +2677,9 @@
  
        row= mysql_fetch_row(result);
  
 +      if (opt_innodb_optimize_keys && !strcmp(table_type, "InnoDB"))
-+        skip_secondary_keys(row[1]);
++        skip_secondary_keys(row[1], has_pk);
 +
        fprintf(sql_file, (opt_compatible_mode & 3) ? "%s;\n" :
                "/*!40101 SET @saved_cs_client     = @@character_set_client */;\n"
                "/*!40101 SET character_set_client = utf8 */;\n"
-@@ -3572,6 +3656,27 @@
+@@ -3574,6 +3774,27 @@
        goto err;
      }
  
      {
 --- /dev/null
 +++ b/mysql-test/r/percona_mysqldump_innodb_optimize_keys.result
-@@ -0,0 +1,109 @@
+@@ -0,0 +1,367 @@
 +#
 +# Test the --innodb-optimize-keys option.
 +#
 +  `a` int(11) DEFAULT NULL,
 +  `b` varchar(255) DEFAULT NULL,
 +  `c` decimal(10,3) DEFAULT NULL,
-+  PRIMARY KEY (`id`) 
++  PRIMARY KEY (`id`),
++  CONSTRAINT `t1_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t2` (`a`) ON DELETE CASCADE
 +) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=latin1;
 +/*!40101 SET character_set_client = @saved_cs_client */;
 +
 +LOCK TABLES `t1` WRITE;
 +/*!40000 ALTER TABLE `t1` DISABLE KEYS */;
 +INSERT INTO `t1` VALUES (1,0,'0',0.000),(2,1,'1',1.100),(3,2,'2',2.200);
-+ALTER TABLE `t1` ADD UNIQUE KEY `uniq` (`c`,`a`), ADD KEY `b` (`b`), ADD KEY `a` (`a`), ADD CONSTRAINT `t1_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t2` (`a`) ON DELETE CASCADE;
++ALTER TABLE `t1` ADD UNIQUE KEY `uniq` (`c`,`a`), ADD KEY `b` (`b`), ADD KEY `a` (`a`);
 +/*!40000 ALTER TABLE `t1` ENABLE KEYS */;
 +UNLOCK TABLES;
 +DROP TABLE IF EXISTS `t2`;
 +
 +######################################
 +DROP TABLE t1, t2;
---- a/mysql-test/suite/innodb/r/innodb.result
-+++ b/mysql-test/suite/innodb/r/innodb.result
-@@ -1673,7 +1673,7 @@
- 71
- SELECT variable_value - @innodb_rows_inserted_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_inserted';
- variable_value - @innodb_rows_inserted_orig
--1066
-+1108
- SELECT variable_value - @innodb_rows_updated_orig FROM information_schema.global_status WHERE LOWER(variable_name) = 'innodb_rows_updated';
- variable_value - @innodb_rows_updated_orig
- 866
---- a/mysql-test/suite/innodb/t/innodb-index.test
-+++ b/mysql-test/suite/innodb/t/innodb-index.test
-@@ -87,6 +87,11 @@
- show create table t1;
- --error ER_MULTIPLE_PRI_KEY
- alter table t1 add primary key (c);
-+# Suppress the error log messages occuring on duplicate key error
-+# during ALTER TABLE when using fast index creation
-+--disable_query_log
-+call mtr.add_suppression("Cannot find index PRIMARY in InnoDB index translation table.");
-+--enable_query_log
- --error ER_DUP_ENTRY
- alter table t1 drop primary key, add primary key (b);
- create unique index c on t1 (c);
---- a/mysql-test/suite/innodb/t/innodb.test
-+++ b/mysql-test/suite/innodb/t/innodb.test
-@@ -21,6 +21,12 @@
- -- source include/have_innodb.inc
-+# Suppress the error log message occuring on duplicate key error
-+# during ALTER TABLE when using fast index creation
-+--disable_query_log
-+call mtr.add_suppression("Cannot find index v_2 in InnoDB index translation table.");
-+--enable_query_log
-+
- let $MYSQLD_DATADIR= `select @@datadir`;
- # Save the original values of some variables in order to be able to
++CREATE TABLE t1 (
++id INT NOT NULL AUTO_INCREMENT,
++KEY (id)
++) ENGINE=InnoDB;
++CREATE TABLE t2 (
++id INT NOT NULL AUTO_INCREMENT,
++UNIQUE KEY (id)
++) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (), (), ();
++INSERT INTO t2 VALUES (), (), ();
++######################################
++
++/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
++/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
++/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
++/*!40101 SET NAMES utf8 */;
++/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;
++/*!40103 SET TIME_ZONE='+00:00' */;
++/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;
++/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;
++/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;
++/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;
++DROP TABLE IF EXISTS `t1`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t1` (
++  `id` int(11) NOT NULL AUTO_INCREMENT,
++  KEY `id` (`id`)
++) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t1` WRITE;
++/*!40000 ALTER TABLE `t1` DISABLE KEYS */;
++INSERT INTO `t1` VALUES (1),(2),(3);
++/*!40000 ALTER TABLE `t1` ENABLE KEYS */;
++UNLOCK TABLES;
++DROP TABLE IF EXISTS `t2`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t2` (
++  `id` int(11) NOT NULL AUTO_INCREMENT,
++  UNIQUE KEY `id` (`id`)
++) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t2` WRITE;
++/*!40000 ALTER TABLE `t2` DISABLE KEYS */;
++INSERT INTO `t2` VALUES (1),(2),(3);
++/*!40000 ALTER TABLE `t2` ENABLE KEYS */;
++UNLOCK TABLES;
++/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;
++
++/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
++/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
++/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
++/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
++/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
++/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
++/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;
++
++######################################
++DROP TABLE t1, t2;
++CREATE TABLE t1 (
++a INT NOT NULL,
++UNIQUE KEY (a)) ENGINE=InnoDB;
++CREATE TABLE t2 (
++a INT NOT NULL,
++b INT NOT NULL,
++UNIQUE KEY (a,b)) ENGINE=InnoDB;
++CREATE TABLE t3 (
++a INT,
++b INT,
++UNIQUE KEY (a,b)) ENGINE=InnoDB;
++CREATE TABLE t4 (
++a INT NOT NULL,
++b INT NOT NULL,
++PRIMARY KEY (a,b),
++UNIQUE KEY(b)) ENGINE=InnoDB;
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++TABLE_SCHEMA=DATABASE() AND
++TABLE_NAME='t1' AND
++COLUMN_KEY='PRI';
++COUNT(*)
++1
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++TABLE_SCHEMA=DATABASE() AND
++TABLE_NAME='t2' AND
++COLUMN_KEY='PRI';
++COUNT(*)
++2
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++TABLE_SCHEMA=DATABASE() AND
++TABLE_NAME='t3' AND
++COLUMN_KEY='PRI';
++COUNT(*)
++0
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++TABLE_SCHEMA=DATABASE() AND
++TABLE_NAME='t4' AND
++COLUMN_KEY='PRI';
++COUNT(*)
++2
++INSERT INTO t1 VALUES (1), (2), (3);
++INSERT INTO t2 VALUES (1,1), (2,2), (3,3);
++INSERT INTO t3 SELECT * FROM t2;
++INSERT INTO t4 SELECT * FROM t2;
++######################################
++
++/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
++/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
++/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
++/*!40101 SET NAMES utf8 */;
++/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;
++/*!40103 SET TIME_ZONE='+00:00' */;
++/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;
++/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;
++/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;
++/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;
++DROP TABLE IF EXISTS `t1`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t1` (
++  `a` int(11) NOT NULL,
++  UNIQUE KEY `a` (`a`)
++) ENGINE=InnoDB DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t1` WRITE;
++/*!40000 ALTER TABLE `t1` DISABLE KEYS */;
++INSERT INTO `t1` VALUES (1),(2),(3);
++/*!40000 ALTER TABLE `t1` ENABLE KEYS */;
++UNLOCK TABLES;
++DROP TABLE IF EXISTS `t2`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t2` (
++  `a` int(11) NOT NULL,
++  `b` int(11) NOT NULL,
++  UNIQUE KEY `a` (`a`,`b`)
++) ENGINE=InnoDB DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t2` WRITE;
++/*!40000 ALTER TABLE `t2` DISABLE KEYS */;
++INSERT INTO `t2` VALUES (1,1),(2,2),(3,3);
++/*!40000 ALTER TABLE `t2` ENABLE KEYS */;
++UNLOCK TABLES;
++DROP TABLE IF EXISTS `t3`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t3` (
++  `a` int(11) DEFAULT NULL,
++  `b` int(11) DEFAULT NULL 
++) ENGINE=InnoDB DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t3` WRITE;
++/*!40000 ALTER TABLE `t3` DISABLE KEYS */;
++INSERT INTO `t3` VALUES (1,1),(2,2),(3,3);
++ALTER TABLE `t3` ADD UNIQUE KEY `a` (`a`,`b`);
++/*!40000 ALTER TABLE `t3` ENABLE KEYS */;
++UNLOCK TABLES;
++DROP TABLE IF EXISTS `t4`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t4` (
++  `a` int(11) NOT NULL,
++  `b` int(11) NOT NULL,
++  PRIMARY KEY (`a`,`b`) 
++) ENGINE=InnoDB DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t4` WRITE;
++/*!40000 ALTER TABLE `t4` DISABLE KEYS */;
++INSERT INTO `t4` VALUES (1,1),(2,2),(3,3);
++ALTER TABLE `t4` ADD UNIQUE KEY `b` (`b`);
++/*!40000 ALTER TABLE `t4` ENABLE KEYS */;
++UNLOCK TABLES;
++/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;
++
++/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
++/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
++/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
++/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
++/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
++/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
++/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;
++
++######################################
++DROP TABLE t1, t2, t3, t4;
++CREATE TABLE t1 (
++id INT NOT NULL PRIMARY KEY
++) ENGINE=InnoDB;
++CREATE TABLE t2 (
++id INT NOT NULL AUTO_INCREMENT,
++a INT NOT NULL,
++PRIMARY KEY (id),
++KEY (a),
++FOREIGN KEY (a) REFERENCES t2 (id)
++) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (1), (2), (3);
++INSERT INTO t2 VALUES (1, 1), (2, 2), (3, 3);
++######################################
++
++/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
++/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
++/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
++/*!40101 SET NAMES utf8 */;
++/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;
++/*!40103 SET TIME_ZONE='+00:00' */;
++/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;
++/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;
++/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;
++/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;
++DROP TABLE IF EXISTS `t1`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t1` (
++  `id` int(11) NOT NULL,
++  PRIMARY KEY (`id`)
++) ENGINE=InnoDB DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t1` WRITE;
++/*!40000 ALTER TABLE `t1` DISABLE KEYS */;
++INSERT INTO `t1` VALUES (1),(2),(3);
++/*!40000 ALTER TABLE `t1` ENABLE KEYS */;
++UNLOCK TABLES;
++DROP TABLE IF EXISTS `t2`;
++/*!40101 SET @saved_cs_client     = @@character_set_client */;
++/*!40101 SET character_set_client = utf8 */;
++CREATE TABLE `t2` (
++  `id` int(11) NOT NULL AUTO_INCREMENT,
++  `a` int(11) NOT NULL,
++  PRIMARY KEY (`id`),
++  CONSTRAINT `t2_ibfk_1` FOREIGN KEY (`a`) REFERENCES `t2` (`id`)
++) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=latin1;
++/*!40101 SET character_set_client = @saved_cs_client */;
++
++LOCK TABLES `t2` WRITE;
++/*!40000 ALTER TABLE `t2` DISABLE KEYS */;
++INSERT INTO `t2` VALUES (1,1),(2,2),(3,3);
++ALTER TABLE `t2` ADD KEY `a` (`a`);
++/*!40000 ALTER TABLE `t2` ENABLE KEYS */;
++UNLOCK TABLES;
++/*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */;
++
++/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
++/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
++/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
++/*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
++/*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
++/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;
++/*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */;
++
++######################################
++DROP TABLE t1, t2;
 --- /dev/null
 +++ b/mysql-test/t/percona_mysqldump_innodb_optimize_keys.test
-@@ -0,0 +1,62 @@
+@@ -0,0 +1,188 @@
 +# Embedded server doesn't support external clients
 +--source include/not_embedded.inc
 +
 +DROP TABLE t1;
 +
 +
-+# Check that for InnoDB tables secondary and foreign keys are created
-+# after the data is dumped
++# Check that for InnoDB tables secondary keys are created after the data is
++# dumped but foreign ones are left in CREATE TABLE
 +
 +CREATE TABLE t2 (a INT PRIMARY KEY) ENGINE=InnoDB;
 +INSERT INTO t2 VALUES (0), (1), (2);
 +
 +DROP TABLE t1, t2;
 +
++########################################################################
++# Bug #812179: AUTO_INCREMENT columns must be skipped by the
++#              --innodb-optimize-keys optimization in mysqldump
++########################################################################
++
++CREATE TABLE t1 (
++  id INT NOT NULL AUTO_INCREMENT,
++  KEY (id)
++) ENGINE=InnoDB;
++
++CREATE TABLE t2 (
++  id INT NOT NULL AUTO_INCREMENT,
++  UNIQUE KEY (id)
++) ENGINE=InnoDB;
++
++INSERT INTO t1 VALUES (), (), ();
++INSERT INTO t2 VALUES (), (), ();
++
++--exec $MYSQL_DUMP --skip-comments --innodb-optimize-keys test t1 t2 >$file
++
++--echo ######################################
++--cat_file $file
++--echo ######################################
++
++# Check that the resulting dump can be imported back
++
++--exec $MYSQL test < $file
++
++--remove_file $file
++
++DROP TABLE t1, t2;
++
++########################################################################
++# Bug #851674: --innodb-optimize-keys does not work correctly with table
++#              without PRIMARY KEY
++########################################################################
++
++CREATE TABLE t1 (
++       a INT NOT NULL,
++       UNIQUE KEY (a)) ENGINE=InnoDB;
++
++CREATE TABLE t2 (
++       a INT NOT NULL,
++       b INT NOT NULL,
++       UNIQUE KEY (a,b)) ENGINE=InnoDB;
++
++CREATE TABLE t3 (
++       a INT,
++       b INT,
++       UNIQUE KEY (a,b)) ENGINE=InnoDB;
++
++CREATE TABLE t4 (
++       a INT NOT NULL,
++       b INT NOT NULL,
++       PRIMARY KEY (a,b),
++       UNIQUE KEY(b)) ENGINE=InnoDB;
++
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++       TABLE_SCHEMA=DATABASE() AND
++       TABLE_NAME='t1' AND
++       COLUMN_KEY='PRI';
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++       TABLE_SCHEMA=DATABASE() AND
++       TABLE_NAME='t2' AND
++       COLUMN_KEY='PRI';
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++       TABLE_SCHEMA=DATABASE() AND
++       TABLE_NAME='t3' AND
++       COLUMN_KEY='PRI';
++SELECT COUNT(*) FROM INFORMATION_SCHEMA.COLUMNS WHERE
++       TABLE_SCHEMA=DATABASE() AND
++       TABLE_NAME='t4' AND
++       COLUMN_KEY='PRI';
++
++INSERT INTO t1 VALUES (1), (2), (3);
++INSERT INTO t2 VALUES (1,1), (2,2), (3,3);
++INSERT INTO t3 SELECT * FROM t2;
++INSERT INTO t4 SELECT * FROM t2;
++
++--exec $MYSQL_DUMP --skip-comments --innodb-optimize-keys test t1 t2 t3 t4 >$file
++
++--echo ######################################
++--cat_file $file
++--echo ######################################
++
++# Check that the resulting dump can be imported back
++
++--exec $MYSQL test < $file
++
++--remove_file $file
++
++DROP TABLE t1, t2, t3, t4;
++
++########################################################################
++# Bug #859078: --innodb-optimize-keys should ignore foreign keys
++########################################################################
++
++CREATE TABLE t1 (
++       id INT NOT NULL PRIMARY KEY
++) ENGINE=InnoDB;
++
++CREATE TABLE t2 (
++       id INT NOT NULL AUTO_INCREMENT,
++       a INT NOT NULL,
++       PRIMARY KEY (id),
++       KEY (a),
++       FOREIGN KEY (a) REFERENCES t2 (id)
++) ENGINE=InnoDB;
++
++INSERT INTO t1 VALUES (1), (2), (3);
++INSERT INTO t2 VALUES (1, 1), (2, 2), (3, 3);
++
++--exec $MYSQL_DUMP --skip-comments --innodb-optimize-keys test t1 t2 >$file
++
++--echo ######################################
++--cat_file $file
++--echo ######################################
++
++# Check that the resulting dump can be imported back
++
++--exec $MYSQL test < $file
++
++--remove_file $file
++
++DROP TABLE t1, t2;
++
 +# Wait till we reached the initial number of concurrent sessions
 +--source include/wait_until_count_sessions.inc
 --- a/sql/sql_lex.cc
 +++ b/sql/sql_lex.cc
-@@ -1630,6 +1630,9 @@
+@@ -1632,6 +1632,9 @@
    alter_list(rhs.alter_list, mem_root),
    key_list(rhs.key_list, mem_root),
    create_list(rhs.create_list, mem_root),
    flags(rhs.flags),
    keys_onoff(rhs.keys_onoff),
    tablespace_op(rhs.tablespace_op),
-@@ -1652,6 +1655,7 @@
+@@ -1654,6 +1657,7 @@
    list_copy_and_replace_each_value(alter_list, mem_root);
    list_copy_and_replace_each_value(key_list, mem_root);
    list_copy_and_replace_each_value(create_list, mem_root);
  
 --- a/sql/sql_lex.h
 +++ b/sql/sql_lex.h
-@@ -1009,6 +1009,9 @@
+@@ -1013,6 +1013,9 @@
    List<Alter_column>            alter_list;
    List<Key>                     key_list;
    List<Create_field>            create_list;
    uint                          flags;
    enum enum_enable_or_disable   keys_onoff;
    enum tablespace_op_type       tablespace_op;
-@@ -1020,6 +1023,8 @@
+@@ -1024,6 +1027,8 @@
  
  
    Alter_info() :
      flags(0),
      keys_onoff(LEAVE_AS_IS),
      tablespace_op(NO_TABLESPACE_OP),
-@@ -1035,6 +1040,9 @@
+@@ -1039,6 +1044,9 @@
      alter_list.empty();
      key_list.empty();
      create_list.empty();
      tablespace_op= NO_TABLESPACE_OP;
 --- a/sql/sql_table.cc
 +++ b/sql/sql_table.cc
-@@ -2776,7 +2776,7 @@
-       file                      The handler for the new table.
-       key_info_buffer     OUT   An array of KEY structs for the indexes.
-       key_count           OUT   The number of elements in the array.
--      select_field_count        The number of fields coming from a select table.
-+      select_field_count        The number of fields coming from a select table. 
-   DESCRIPTION
-     Prepares the table and key structures for table creation.
-@@ -3122,7 +3122,6 @@
-   }
-   /* Create keys */
--
-   List_iterator<Key> key_iterator(alter_info->key_list);
-   List_iterator<Key> key_iterator2(alter_info->key_list);
-   uint key_parts=0, fk_key_count=0;
-@@ -3220,6 +3219,14 @@
+@@ -3220,6 +3220,14 @@
    if (!*key_info_buffer || ! key_part_info)
      DBUG_RETURN(TRUE);                                // Out of memory
  
    key_iterator.rewind();
    key_number=0;
    for (; (key=key_iterator++) ; key_number++)
-@@ -3638,6 +3645,22 @@
+@@ -3638,6 +3646,22 @@
        key_info->comment.str= key->key_create_info.comment.str;
      }
  
      key_info++;
    }
    if (!unique_key && !primary_key &&
-@@ -5256,6 +5279,10 @@
+@@ -5256,6 +5280,10 @@
    List<Create_field> new_create_list;
    /* New key definitions are added here */
    List<Key> new_key_list;
    List_iterator<Alter_drop> drop_it(alter_info->drop_list);
    List_iterator<Create_field> def_it(alter_info->create_list);
    List_iterator<Alter_column> alter_it(alter_info->alter_list);
-@@ -5268,6 +5295,7 @@
+@@ -5268,6 +5296,7 @@
    uint used_fields= create_info->used_fields;
    KEY *key_info=table->key_info;
    bool rc= TRUE;
  
    DBUG_ENTER("mysql_prepare_alter_table");
  
-@@ -5457,7 +5485,23 @@
+@@ -5457,7 +5486,26 @@
    /*
      Collect all keys which isn't in drop list. Add only those
      for which some fields exists.
 +    the InnoDB fast index creation. The following conditions must be
 +    met:
 +
++    - fast_index_creation is enabled for the current session
++    - expand_fast_index_creation is enabled for the current session;
 +    - we are going to create an InnoDB table (this is checked later when the
 +      target engine is known);
 +    - the key most be a non-UNIQUE one;
 +      key constraints in the table.
 +  */
 +
-+  skip_secondary=
++  skip_secondary= thd->variables.online_alter_index &&
++    thd->variables.expand_fast_index_creation &&
 +    !table->file->get_foreign_key_list(thd, &f_key_list) &&
 +    f_key_list.elements == 0;
  
    for (uint i=0 ; i < table->s->keys ; i++,key_info++)
    {
-@@ -5574,6 +5618,8 @@
+@@ -5574,6 +5622,8 @@
                     test(key_info->flags & HA_GENERATED_KEY),
                     key_parts);
        new_key_list.push_back(key);
      }
    }
    {
-@@ -5581,7 +5627,21 @@
+@@ -5581,7 +5631,21 @@
      while ((key=key_it++))                    // Add new keys
      {
        if (key->type != Key::FOREIGN_KEY)
        if (key->name.str &&
          !my_strcasecmp(system_charset_info, key->name.str, primary_key_name))
        {
-@@ -5630,12 +5690,104 @@
+@@ -5630,12 +5694,104 @@
    rc= FALSE;
    alter_info->create_list.swap(new_create_list);
    alter_info->key_list.swap(new_key_list);
    Alter table
  
    SYNOPSIS
-@@ -6428,19 +6580,38 @@
+@@ -6428,19 +6584,38 @@
    */
    if (new_table && !(new_table->file->ha_table_flags() & HA_NO_COPY_ON_ALTER))
    {
    }
    else
    {
+--- /dev/null
++++ b/mysql-test/r/percona_innodb_expand_fast_index_creation.result
+@@ -0,0 +1,64 @@
++CREATE TABLE t1(
++id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
++a CHAR(1) NOT NULL,
++b CHAR(36) NOT NULL) ENGINE=InnoDB;
++INSERT INTO t1(a,b) VALUES ('a','b');
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++ALTER TABLE t1 ADD KEY (a);
++affected rows: 0
++info: Records: 0  Duplicates: 0  Warnings: 0
++EXPLAIN SELECT COUNT(*) FROM t1, t1 t2 WHERE t1.a = t2.a AND t1.b = t2.b;
++id    1
++select_type   SIMPLE
++table t1
++type  ALL
++possible_keys a
++key   NULL
++key_len       NULL
++ref   NULL
++rows  16
++Extra 
++id    1
++select_type   SIMPLE
++table t2
++type  ref
++possible_keys a
++key   a
++key_len       1
++ref   test.t1.a
++rows  1
++Extra Using where
++ALTER TABLE t1 DROP KEY a;
++SET expand_fast_index_creation = 1;
++SELECT @@expand_fast_index_creation;
++@@expand_fast_index_creation
++1
++ALTER TABLE t1 ADD KEY (a);
++affected rows: 0
++info: Records: 0  Duplicates: 0  Warnings: 0
++EXPLAIN SELECT COUNT(*) FROM t1, t1 t2 WHERE t1.a = t2.a AND t1.b = t2.b;
++id    1
++select_type   SIMPLE
++table t1
++type  ALL
++possible_keys a
++key   NULL
++key_len       NULL
++ref   NULL
++rows  16
++Extra 
++id    1
++select_type   SIMPLE
++table t2
++type  ALL
++possible_keys a
++key   NULL
++key_len       NULL
++ref   NULL
++rows  16
++Extra Using where; Using join buffer
++SET expand_fast_index_creation = 0;
++DROP TABLE t1;
+--- /dev/null
++++ b/mysql-test/t/percona_innodb_expand_fast_index_creation.test
+@@ -0,0 +1,45 @@
++--source include/have_innodb.inc
++
++########################################################################
++# Bug #857590: Fast index creation does not update index statistics
++########################################################################
++
++CREATE TABLE t1(
++       id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
++       a CHAR(1) NOT NULL,
++       b CHAR(36) NOT NULL) ENGINE=InnoDB;
++
++INSERT INTO t1(a,b) VALUES ('a','b');
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++INSERT INTO t1(a,b) SELECT a,b FROM t1;
++
++# Check that fast index creation is used
++--enable_info
++ALTER TABLE t1 ADD KEY (a);
++--disable_info
++
++# The default (wrong) plan due to bogus statistics
++--vertical_results
++EXPLAIN SELECT COUNT(*) FROM t1, t1 t2 WHERE t1.a = t2.a AND t1.b = t2.b;
++--horizontal_results
++
++ALTER TABLE t1 DROP KEY a;
++
++SET expand_fast_index_creation = 1;
++SELECT @@expand_fast_index_creation;
++
++# Check that stats are updated with the option enabled
++
++--enable_info
++ALTER TABLE t1 ADD KEY (a);
++--disable_info
++
++--vertical_results
++EXPLAIN SELECT COUNT(*) FROM t1, t1 t2 WHERE t1.a = t2.a AND t1.b = t2.b;
++--horizontal_results
++
++SET expand_fast_index_creation = 0;
++
++DROP TABLE t1;
+--- a/storage/innobase/row/row0merge.c
++++ b/storage/innobase/row/row0merge.c
+@@ -56,6 +56,7 @@
+ #include "log0log.h"
+ #include "ut0sort.h"
+ #include "handler0alter.h"
++#include "ha_prototypes.h"
+ /* Ignore posix_fadvise() on those platforms where it does not exist */
+ #if defined __WIN__
+@@ -2673,6 +2674,9 @@
+               }
+       }
++      if (trx->mysql_thd && thd_expand_fast_index_creation(trx->mysql_thd))
++          dict_update_statistics(new_table, FALSE, TRUE);
++
+ func_exit:
+       row_merge_file_destroy_low(tmpfd);
+--- a/sql/sql_class.h
++++ b/sql/sql_class.h
+@@ -556,6 +556,7 @@
+   double long_query_time_double;
++  my_bool expand_fast_index_creation;
+ } SV;
+--- a/sql/sys_vars.cc
++++ b/sql/sys_vars.cc
+@@ -710,6 +710,14 @@
+        ON_CHECK(event_scheduler_check), ON_UPDATE(event_scheduler_update));
+ #endif
++static Sys_var_mybool Sys_expand_fast_index_creation(
++       "expand_fast_index_creation",
++       "Enable/disable improvements to the InnoDB fast index creation "
++       "functionality. Has no effect when fast index creation is disabled with "
++       "the fast-index-creation option",
++       SESSION_VAR(expand_fast_index_creation), CMD_LINE(OPT_ARG),
++       DEFAULT(FALSE));
++
+ static Sys_var_ulong Sys_expire_logs_days(
+        "expire_logs_days",
+        "If non-zero, binary logs will be purged after expire_logs_days "
+--- a/storage/innobase/handler/ha_innodb.cc
++++ b/storage/innobase/handler/ha_innodb.cc
+@@ -999,6 +999,19 @@
+       return(THDVAR((THD*) thd, flush_log_at_trx_commit));
+ }
++/******************************************************************//**
++Returns true if expand_fast_index_creation is enabled for the current
++session.
++@return       the value of the server's expand_fast_index_creation variable */
++extern "C" UNIV_INTERN
++ibool
++thd_expand_fast_index_creation(
++/*================================*/
++      void*   thd)
++{
++      return((ibool) (((THD*) thd)->variables.expand_fast_index_creation));
++}
++
+ /********************************************************************//**
+ Obtain the InnoDB transaction of a MySQL thread.
+ @return       reference to transaction pointer */
+--- a/storage/innobase/include/ha_prototypes.h
++++ b/storage/innobase/include/ha_prototypes.h
+@@ -303,4 +303,15 @@
+ innobase_get_lower_case_table_names(void);
+ /*=====================================*/
++/******************************************************************//**
++Returns true if innodb_expand_fast_index_creation is enabled for the current
++session.
++@return       the value of the server's innodb_expand_fast_index_creation variable */
++
++ibool
++thd_expand_fast_index_creation(
++/*==================*/
++      void*   thd);   /*!< in: thread handle (THD*) */
++
++
+ #endif
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/r/expand_fast_index_creation_basic.result
+@@ -0,0 +1,6 @@
++SELECT @@global.expand_fast_index_creation;
++@@global.expand_fast_index_creation
++0
++SELECT @@local.expand_fast_index_creation;
++@@local.expand_fast_index_creation
++0
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/t/expand_fast_index_creation_basic.test
+@@ -0,0 +1,2 @@
++SELECT @@global.expand_fast_index_creation;
++SELECT @@local.expand_fast_index_creation;
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -140,6 +140,10 @@
+  and DISABLED (keep the event scheduler completely
+  deactivated, it cannot be activated run-time)
+  -T, --exit-info[=#] Used for debugging. Use at your own risk.
++ --expand-fast-index-creation 
++ Enable/disable improvements to the InnoDB fast index
++ creation functionality. Has no effect when fast index
++ creation is disabled with the fast-index-creation option
+  --expire-logs-days=# 
+  If non-zero, binary logs will be purged after
+  expire_logs_days days; possible purges happen at startup
+@@ -821,6 +825,7 @@
+ div-precision-increment 4
+ engine-condition-pushdown TRUE
+ event-scheduler OFF
++expand-fast-index-creation FALSE
+ expire-logs-days 0
+ external-locking FALSE
+ flush FALSE
+--- a/mysql-test/r/mysqld--help-win.result
++++ b/mysql-test/r/mysqld--help-win.result
+@@ -140,6 +140,10 @@
+  and DISABLED (keep the event scheduler completely
+  deactivated, it cannot be activated run-time)
+  -T, --exit-info[=#] Used for debugging. Use at your own risk.
++ --expand-fast-index-creation 
++ Enable/disable improvements to InnoDB fast index creation
++ functionality. Has no effect when fast index creation is
++ disabled with the fast-index-creation option
+  --expire-logs-days=# 
+  If non-zero, binary logs will be purged after
+  expire_logs_days days; possible purges happen at startup
+@@ -775,6 +779,7 @@
+ div-precision-increment 4
+ engine-condition-pushdown TRUE
+ event-scheduler OFF
++expand-fast-index-creation FALSE
+ expire-logs-days 0
+ external-locking FALSE
+ flush FALSE
index ce589e8f088a6ab7f34ee780092fa5eedd894a65..e4549abdadc8474104ca47b976aa01400c52e97a 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/btr/btr0btr.c
 +++ b/storage/innobase/btr/btr0btr.c
-@@ -837,7 +837,7 @@
+@@ -838,7 +838,7 @@
  /**************************************************************//**
  Creates a new index page (not the root, and also not
  used in page reorganization).  @see btr_page_empty(). */
@@ -16,7 +16,7 @@
  void
  btr_page_create(
  /*============*/
-@@ -1707,7 +1707,7 @@
+@@ -1712,7 +1712,7 @@
  #ifndef UNIV_HOTBACKUP
  /*************************************************************//**
  Empties an index page.  @see btr_page_create(). */
@@ -25,7 +25,7 @@
  void
  btr_page_empty(
  /*===========*/
-@@ -2269,7 +2269,7 @@
+@@ -2274,7 +2274,7 @@
  /**************************************************************//**
  Attaches the halves of an index page on the appropriate level in an
  index tree. */
  #endif /* !UNIV_HOTBACKUP */
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -7388,6 +7388,14 @@
+@@ -7423,6 +7423,14 @@
                err = row_discard_tablespace_for_mysql(dict_table->name, trx);
        } else {
                err = row_import_tablespace_for_mysql(dict_table->name, trx);
        }
  
        err = convert_error_code_to_mysql(err, dict_table->flags, NULL);
-@@ -11665,6 +11673,11 @@
+@@ -11772,6 +11780,11 @@
    "Choose method of innodb_adaptive_flushing. (native, [estimate], keep_average)",
    NULL, innodb_adaptive_flushing_method_update, 1, &adaptive_flushing_method_typelib);
  
  static MYSQL_SYSVAR_ULONG(dict_size_limit, srv_dict_size_limit,
    PLUGIN_VAR_RQCMDARG,
    "Limit the allocated memory for dictionary cache. (0: unlimited)",
-@@ -11738,6 +11751,7 @@
+@@ -11846,6 +11859,7 @@
    MYSQL_SYSVAR(flush_neighbor_pages),
    MYSQL_SYSVAR(read_ahead),
    MYSQL_SYSVAR(adaptive_flushing_method),
    MYSQL_SYSVAR(use_native_aio),
 --- a/storage/innobase/include/btr0btr.h
 +++ b/storage/innobase/include/btr0btr.h
-@@ -219,6 +219,17 @@
+@@ -238,6 +238,17 @@
  @return the uncompressed page frame */
- # define btr_page_get(space,zip_size,page_no,mode,mtr) \
-       buf_block_get_frame(btr_block_get(space,zip_size,page_no,mode,mtr))
+ # define btr_page_get(space,zip_size,page_no,mode,idx,mtr)            \
+       buf_block_get_frame(btr_block_get(space,zip_size,page_no,mode,idx,mtr))
 +/**************************************************************//**
 +Sets the index id field of a page. */
 +UNIV_INLINE
  #endif /* !UNIV_HOTBACKUP */
  /**************************************************************//**
  Gets the index id field of a page.
-@@ -256,6 +267,17 @@
+@@ -275,6 +286,17 @@
        const page_t*   page,   /*!< in: index page */
        mtr_t*          mtr);   /*!< in: mini-transaction handle */
  /********************************************************//**
  Gets the previous index page number.
  @return       prev page number */
  UNIV_INLINE
-@@ -264,6 +286,17 @@
+@@ -283,6 +305,17 @@
  /*==============*/
        const page_t*   page,   /*!< in: index page */
        mtr_t*          mtr);   /*!< in: mini-transaction handle */
  /*************************************************************//**
  Gets pointer to the previous user record in the tree. It is assumed
  that the caller has appropriate latches on the page and its neighbor.
-@@ -309,6 +342,18 @@
+@@ -328,6 +361,18 @@
  /*===========================*/
        const rec_t*    rec,    /*!< in: node pointer record */
        const ulint*    offsets);/*!< in: array returned by rec_get_offsets() */
  /************************************************************//**
  Creates the root node for a new index tree.
  @return       page number of the created root, FIL_NULL if did not succeed */
-@@ -379,6 +424,17 @@
+@@ -397,6 +442,17 @@
        dict_index_t*   index,  /*!< in: record descriptor */
        mtr_t*          mtr);   /*!< in: mtr */
  /*************************************************************//**
  Decides if the page should be split at the convergence point of
  inserts converging to left.
  @return       TRUE if split recommended */
-@@ -437,6 +493,20 @@
+@@ -455,6 +511,20 @@
  # define btr_insert_on_non_leaf_level(i,l,t,m)                                \
        btr_insert_on_non_leaf_level_func(i,l,t,__FILE__,__LINE__,m)
  #endif /* !UNIV_HOTBACKUP */
 +/*==================*/
 +      dict_index_t*   index,          /*!< in: the index tree */
 +      buf_block_t*    block,          /*!< in/out: page to be split */
-+      const rec_t*    split_rec,      /*!< in: first record on upper
++      rec_t*          split_rec,      /*!< in: first record on upper
 +                                      half page */
 +      buf_block_t*    new_block,      /*!< in/out: the new half page */
 +      ulint           direction,      /*!< in: FSP_UP or FSP_DOWN */
  UNIV_INTERN
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -229,6 +229,8 @@
+@@ -234,6 +234,8 @@
  extern ulint  srv_read_ahead;
  extern ulint  srv_adaptive_flushing_method;
  
  
 --- a/storage/innobase/row/row0mysql.c
 +++ b/storage/innobase/row/row0mysql.c
-@@ -2546,6 +2546,11 @@
+@@ -2547,6 +2547,11 @@
  
        current_lsn = log_get_lsn();
  
        /* It is possible, though very improbable, that the lsn's in the
        tablespace to be imported have risen above the current system lsn, if
        a lengthy purge, ibuf merge, or rollback was performed on a backup
-@@ -2657,6 +2662,11 @@
+@@ -2658,6 +2663,11 @@
  
        trx->op_info = "";
  
  
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -416,6 +416,8 @@
+@@ -418,6 +418,8 @@
  UNIV_INTERN ulint     srv_read_ahead = 3; /* 1: random  2: linear  3: Both */
  UNIV_INTERN ulint     srv_adaptive_flushing_method = 0; /* 0: native  1: estimate  2: keep_average */
  
index 33e3755a6ac3f88671db1b4d2782a617e3dc4d98..49603865a4a901b6bdae7fa6e4ecfd6acdd39dd6 100644 (file)
@@ -48,7 +48,7 @@
  
  /*
                IMPLEMENTATION OF THE BUFFER POOL
-@@ -1930,8 +1964,16 @@
+@@ -1931,8 +1965,16 @@
        mutex_t*        block_mutex;
        ibool           must_read;
        unsigned        access_time;
@@ -65,7 +65,7 @@
        buf_pool->stat.n_page_gets++;
  
        for (;;) {
-@@ -1949,7 +1991,7 @@
+@@ -1950,7 +1992,7 @@
                //buf_pool_mutex_exit(buf_pool);
                rw_lock_s_unlock(&buf_pool->page_hash_latch);
  
@@ -74,7 +74,7 @@
  
  #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
                ut_a(++buf_dbg_counter % 37 || buf_validate());
-@@ -2045,6 +2087,13 @@
+@@ -2046,6 +2088,13 @@
                /* Let us wait until the read operation
                completes */
  
@@ -88,7 +88,7 @@
                for (;;) {
                        enum buf_io_fix io_fix;
  
-@@ -2059,6 +2108,12 @@
+@@ -2060,6 +2109,12 @@
                                break;
                        }
                }
        }
  
  #ifdef UNIV_IBUF_COUNT_DEBUG
-@@ -2374,6 +2429,11 @@
+@@ -2375,6 +2430,11 @@
        ibool           must_read;
        ulint           retries = 0;
        mutex_t*        block_mutex = NULL;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
        ut_ad(mtr);
-@@ -2403,6 +2463,9 @@
+@@ -2404,6 +2464,9 @@
              || ibuf_page_low(space, zip_size, offset,
                               FALSE, file, line, NULL));
  #endif
        buf_pool->stat.n_page_gets++;
        fold = buf_page_address_fold(space, offset);
  loop:
-@@ -2473,7 +2536,7 @@
+@@ -2474,9 +2537,9 @@
                        return(NULL);
                }
  
 -              if (buf_read_page(space, zip_size, offset)) {
 +              if (buf_read_page(space, zip_size, offset, trx)) {
+                       buf_read_ahead_random(space, zip_size, offset,
+-                                            ibuf_inside(mtr));
++                                            ibuf_inside(mtr), trx);
                        retries = 0;
                } else if (retries < BUF_PAGE_READ_MAX_RETRIES) {
-                       ++retries;
-@@ -2782,6 +2845,13 @@
+@@ -2786,6 +2849,13 @@
                        /* Let us wait until the read operation
                        completes */
  
                        for (;;) {
                                enum buf_io_fix io_fix;
  
-@@ -2796,6 +2866,12 @@
+@@ -2800,6 +2870,12 @@
                                        break;
                                }
                        }
                }
  
                fix_type = MTR_MEMO_BUF_FIX;
-@@ -2822,13 +2898,17 @@
+@@ -2826,13 +2902,17 @@
                read-ahead */
  
                buf_read_ahead_linear(space, zip_size, offset,
        return(block);
  }
  
-@@ -2852,6 +2932,7 @@
+@@ -2856,6 +2936,7 @@
        unsigned        access_time;
        ibool           success;
        ulint           fix_type;
  
        ut_ad(block);
        ut_ad(mtr);
-@@ -2929,6 +3010,10 @@
+@@ -2933,6 +3014,10 @@
  #if defined UNIV_DEBUG_FILE_ACCESSES || defined UNIV_DEBUG
        ut_a(block->page.file_page_was_freed == FALSE);
  #endif
        if (UNIV_UNLIKELY(!access_time)) {
                /* In the case of a first access, try to apply linear
                read-ahead */
-@@ -2936,7 +3021,7 @@
+@@ -2940,7 +3025,7 @@
                buf_read_ahead_linear(buf_block_get_space(block),
                                      buf_block_get_zip_size(block),
                                      buf_block_get_page_no(block),
        }
  
  #ifdef UNIV_IBUF_COUNT_DEBUG
-@@ -2946,6 +3031,9 @@
+@@ -2950,6 +3035,9 @@
        buf_pool = buf_pool_from_block(block);
        buf_pool->stat.n_page_gets++;
  
        return(TRUE);
  }
  
-@@ -2968,6 +3056,7 @@
+@@ -2972,6 +3060,7 @@
        buf_pool_t*     buf_pool;
        ibool           success;
        ulint           fix_type;
  
        ut_ad(mtr);
        ut_ad(mtr->state == MTR_ACTIVE);
-@@ -3054,6 +3143,11 @@
+@@ -3058,6 +3147,11 @@
  #endif
        buf_pool->stat.n_page_gets++;
  
  
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -77,7 +77,8 @@
+@@ -79,7 +79,8 @@
                        treat the tablespace as dropped; this is a timestamp we
                        use to stop dangling page reads from a tablespace
                        which we have DISCARDed + IMPORTed back */
  {
        buf_page_t*     bpage;
        ulint           wake_later;
-@@ -179,15 +180,15 @@
+@@ -181,15 +182,15 @@
  
        thd_wait_begin(NULL, THD_WAIT_DISKIO);
        if (zip_size) {
        }
        thd_wait_end(NULL);
        ut_a(*err == DB_SUCCESS);
-@@ -213,7 +214,8 @@
+@@ -226,8 +227,9 @@
+                               or 0 */
+       ulint   offset,         /*!< in: page number of a page which
+                               the current thread wants to access */
+-      ibool   inside_ibuf)    /*!< in: TRUE if we are inside ibuf
++      ibool   inside_ibuf,    /*!< in: TRUE if we are inside ibuf
+                               routine */
++      trx_t*  trx)
+ {
+       buf_pool_t*     buf_pool = buf_pool_get(space, offset);
+       ib_int64_t      tablespace_version;
+@@ -330,7 +332,7 @@
+                               &err, FALSE,
+                               ibuf_mode | OS_AIO_SIMULATED_WAKE_LATER,
+                               space, zip_size, FALSE,
+-                              tablespace_version, i);
++                              tablespace_version, i, trx);
+                       if (err == DB_TABLESPACE_DELETED) {
+                               ut_print_timestamp(stderr);
+                               fprintf(stderr,
+@@ -380,7 +382,8 @@
  /*==========*/
        ulint   space,  /*!< in: space id */
        ulint   zip_size,/*!< in: compressed page size in bytes, or 0 */
  {
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
        ib_int64_t      tablespace_version;
-@@ -227,7 +229,7 @@
+@@ -394,7 +397,7 @@
  
        count = buf_read_page_low(&err, TRUE, BUF_READ_ANY_PAGE, space,
                                  zip_size, FALSE,
        srv_buf_pool_reads += count;
        if (err == DB_TABLESPACE_DELETED) {
                ut_print_timestamp(stderr);
-@@ -279,7 +281,8 @@
+@@ -446,7 +449,8 @@
        ulint   space,          /*!< in: space id */
        ulint   zip_size,       /*!< in: compressed page size in bytes, or 0 */
        ulint   offset,         /*!< in: page number; see NOTE 3 above */
  {
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
        ib_int64_t      tablespace_version;
-@@ -498,7 +501,7 @@
+@@ -665,7 +669,7 @@
                        count += buf_read_page_low(
                                &err, FALSE,
                                ibuf_mode,
                        if (err == DB_TABLESPACE_DELETED) {
                                ut_print_timestamp(stderr);
                                fprintf(stderr,
-@@ -591,7 +594,7 @@
+@@ -758,7 +762,7 @@
                buf_read_page_low(&err, sync && (i + 1 == n_stored),
                                  BUF_READ_ANY_PAGE, space_ids[i],
                                  zip_size, TRUE, space_versions[i],
  
                if (UNIV_UNLIKELY(err == DB_TABLESPACE_DELETED)) {
  tablespace_deleted:
-@@ -733,12 +736,12 @@
+@@ -900,12 +904,12 @@
                if ((i + 1 == n_stored) && sync) {
                        buf_read_page_low(&err, TRUE, BUF_READ_ANY_PAGE, space,
                                          zip_size, TRUE, tablespace_version,
  
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -1578,6 +1578,16 @@
+@@ -1584,6 +1584,16 @@
        trx->check_unique_secondary = !thd_test_options(
                thd, OPTION_RELAXED_UNIQUE_CHECKS);
  
        DBUG_VOID_RETURN;
  }
  
-@@ -1632,6 +1642,32 @@
+@@ -1638,6 +1648,32 @@
        return(trx);
  }
  
  /*********************************************************************//**
  Note that a transaction has been registered with MySQL.
  @return true if transaction is registered with MySQL 2PC coordinator */
-@@ -9312,6 +9348,25 @@
+@@ -9409,6 +9445,25 @@
        statement has ended */
  
        if (trx->n_mysql_tables_in_use == 0) {
        ulint   zip_size,/*!< in: compressed page size in bytes, or 0 */
 -      ulint   offset);/*!< in: page number */
 +      ulint   offset, /*!< in: page number */
++      trx_t*  trx);
+ /********************************************************************//**
+ Applies a random read-ahead in buf_pool if there are at least a threshold
+ value of accessed pages from the random read-ahead area. Does not read any
+@@ -65,8 +67,9 @@
+                               or 0 */
+       ulint   offset,         /*!< in: page number of a page which
+                               the current thread wants to access */
+-      ibool   inside_ibuf);   /*!< in: TRUE if we are inside ibuf
++      ibool   inside_ibuf,    /*!< in: TRUE if we are inside ibuf
+                               routine */
 +      trx_t*  trx);
  /********************************************************************//**
  Applies linear read-ahead if in the buf_pool the page is a border page of
  a linear read-ahead area and all the pages in the area have been accessed.
-@@ -73,7 +75,8 @@
+@@ -98,7 +101,8 @@
        ulint   space,          /*!< in: space id */
        ulint   zip_size,       /*!< in: compressed page size in bytes, or 0 */
        ulint   offset,         /*!< in: page number; see NOTE 3 above */
  /* The following counter is incremented whenever there is some user activity
  in the server */
  UNIV_INTERN ulint     srv_activity_count      = 0;
-@@ -1232,6 +1235,10 @@
+@@ -1234,6 +1237,10 @@
        ibool                   has_slept = FALSE;
        srv_conc_slot_t*        slot      = NULL;
        ulint                   i;
  
  #ifdef UNIV_SYNC_DEBUG
        ut_ad(!sync_thread_levels_nonempty_trx(trx->has_search_latch));
-@@ -1312,6 +1319,7 @@
+@@ -1314,6 +1321,7 @@
                switches. */
                if (SRV_THREAD_SLEEP_DELAY > 0) {
                        os_thread_sleep(SRV_THREAD_SLEEP_DELAY);
                }
  
                trx->op_info = "";
-@@ -1371,6 +1379,14 @@
+@@ -1373,6 +1381,14 @@
  #ifdef UNIV_SYNC_DEBUG
        ut_ad(!sync_thread_levels_nonempty_trx(trx->has_search_latch));
  #endif /* UNIV_SYNC_DEBUG */
        trx->op_info = "waiting in InnoDB queue";
  
        thd_wait_begin(trx->mysql_thd, THD_WAIT_USER_LOCK);
-@@ -1379,6 +1395,12 @@
+@@ -1381,6 +1397,12 @@
  
        trx->op_info = "";
  
index 6f77c37517b9260d1110abca9285362f021a44dd..fed745df714ee481094519e4f57b2512035bd009 100644 (file)
@@ -7,9 +7,9 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -11545,6 +11545,7 @@
-   innobase_system_variables, /* system variables */
-   NULL /* reserved */
+@@ -11655,6 +11655,7 @@
+   NULL, /* reserved */
+   0,    /* flags */
  },
 +i_s_innodb_rseg,
  i_s_innodb_trx,
@@ -26,7 +26,7 @@
  }
  
  #define OK(expr)              \
-@@ -1779,3 +1781,166 @@
+@@ -1807,3 +1809,166 @@
  
        DBUG_RETURN(0);
  }
diff --git a/innodb_fake_changes.patch b/innodb_fake_changes.patch
new file mode 100644 (file)
index 0000000..41eb152
--- /dev/null
@@ -0,0 +1,767 @@
+# name       : innodb_fake_changes.patch
+# introduced : 5.5.15
+# maintainer : Yasufumi
+#
+#!!! notice !!!
+# Any small change to this file in the main branch
+# should be done or reviewed by the maintainer!
+--- a/storage/innobase/btr/btr0cur.c
++++ b/storage/innobase/btr/btr0cur.c
+@@ -1173,6 +1173,11 @@
+       rec_t*          rec;
+       roll_ptr_t      roll_ptr;
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip LOCK, UNDO */
++              return(DB_SUCCESS);
++      }
++
+       /* Check if we have to wait for a lock: enqueue an explicit lock
+       request if yes */
+@@ -1304,7 +1309,7 @@
+       }
+ #endif /* UNIV_DEBUG */
+-      ut_ad(mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
+       max_size = page_get_max_insert_size_after_reorganize(page, 1);
+       leaf = page_is_leaf(page);
+@@ -1399,6 +1404,12 @@
+               goto fail_err;
+       }
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip CHANGE, LOG */
++              *big_rec = big_rec_vec;
++              return(err); /* == DB_SUCCESS */
++      }
++
+       page_cursor = btr_cur_get_page_cur(cursor);
+       /* Now, try the insert */
+@@ -1541,10 +1552,10 @@
+       *big_rec = NULL;
+-      ut_ad(mtr_memo_contains(mtr,
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr,
+                               dict_index_get_lock(btr_cur_get_index(cursor)),
+                               MTR_MEMO_X_LOCK));
+-      ut_ad(mtr_memo_contains(mtr, btr_cur_get_block(cursor),
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr, btr_cur_get_block(cursor),
+                               MTR_MEMO_PAGE_X_FIX));
+       /* Try first an optimistic insert; reset the cursor flag: we do not
+@@ -1610,6 +1621,16 @@
+               }
+       }
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip CHANGE, LOG */
++              if (n_extents > 0) {
++                      fil_space_release_free_extents(index->space,
++                                                     n_reserved);
++              }
++              *big_rec = big_rec_vec;
++              return(DB_SUCCESS);
++      }
++
+       if (dict_index_get_page(index)
+           == buf_block_get_page_no(btr_cur_get_block(cursor))) {
+@@ -1666,6 +1687,11 @@
+       ut_ad(cursor && update && thr && roll_ptr);
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip LOCK, UNDO */
++              return(DB_SUCCESS);
++      }
++
+       rec = btr_cur_get_rec(cursor);
+       index = cursor->index;
+@@ -1965,6 +1991,14 @@
+               return(err);
+       }
++      if (trx->fake_changes) {
++              /* skip CHANGE, LOG */
++              if (UNIV_LIKELY_NULL(heap)) {
++                      mem_heap_free(heap);
++              }
++              return(err); /* == DB_SUCCESS */
++      }
++
+       if (!(flags & BTR_KEEP_SYS_FLAG)) {
+               row_upd_rec_sys_fields(rec, NULL,
+                                      index, offsets, trx, roll_ptr);
+@@ -2074,7 +2108,7 @@
+       rec = btr_cur_get_rec(cursor);
+       index = cursor->index;
+       ut_ad(!!page_rec_is_comp(rec) == dict_table_is_comp(index->table));
+-      ut_ad(mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
+       /* The insert buffer tree should never be updated in place. */
+       ut_ad(!dict_index_is_ibuf(index));
+@@ -2187,6 +2221,11 @@
+               goto err_exit;
+       }
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip CHANGE, LOG */
++              goto err_exit; /* == DB_SUCCESS */
++      }
++
+       /* Ok, we may do the replacement. Store on the page infimum the
+       explicit locks on rec, before deleting rec (see the comment in
+       btr_cur_pessimistic_update). */
+@@ -2337,9 +2376,9 @@
+       rec = btr_cur_get_rec(cursor);
+       index = cursor->index;
+-      ut_ad(mtr_memo_contains(mtr, dict_index_get_lock(index),
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr, dict_index_get_lock(index),
+                               MTR_MEMO_X_LOCK));
+-      ut_ad(mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
++      ut_ad((thr && thr_get_trx(thr)->fake_changes) || mtr_memo_contains(mtr, block, MTR_MEMO_PAGE_X_FIX));
+ #ifdef UNIV_ZIP_DEBUG
+       ut_a(!page_zip || page_zip_validate(page_zip, page));
+ #endif /* UNIV_ZIP_DEBUG */
+@@ -2427,6 +2466,9 @@
+               ut_ad(big_rec_vec == NULL);
++              /* fake_changes should not cause undo. so never reaches here */
++              ut_ad(!(trx->fake_changes));
++
+               btr_rec_free_updated_extern_fields(
+                       index, rec, page_zip, offsets, update,
+                       trx_is_recv(trx) ? RB_RECOVERY : RB_NORMAL, mtr);
+@@ -2461,6 +2503,12 @@
+               }
+       }
++      if (trx->fake_changes) {
++              /* skip CHANGE, LOG */
++              err = DB_SUCCESS;
++              goto return_after_reservations;
++      }
++
+       /* Store state of explicit locks on rec on the page infimum record,
+       before deleting rec. The page infimum acts as a dummy carrier of the
+       locks, taking care also of lock releases, before we can move the locks
+@@ -2763,6 +2811,11 @@
+       ut_ad(dict_index_is_clust(index));
+       ut_ad(!rec_get_deleted_flag(rec, rec_offs_comp(offsets)));
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip LOCK, UNDO, CHANGE, LOG */
++              return(DB_SUCCESS);
++      }
++
+       err = lock_clust_rec_modify_check_and_lock(flags, block,
+                                                  rec, index, offsets, thr);
+@@ -2897,6 +2950,11 @@
+       rec_t*          rec;
+       ulint           err;
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              /* skip LOCK, CHANGE, LOG */
++              return(DB_SUCCESS);
++      }
++
+       block = btr_cur_get_block(cursor);
+       rec = btr_cur_get_rec(cursor);
+--- a/storage/innobase/handler/ha_innodb.cc
++++ b/storage/innobase/handler/ha_innodb.cc
+@@ -488,6 +488,12 @@
+   " or 2 (write at commit, flush once per second).",
+   NULL, NULL, 1, 0, 2, 0);
++static MYSQL_THDVAR_BOOL(fake_changes, PLUGIN_VAR_OPCMDARG,
++  "In the transaction after enabled, UPDATE, INSERT and DELETE only move the cursor to the records "
++  "and do nothing other operations (no changes, no ibuf, no undo, no transaction log) in the transaction. "
++  "This is to cause replication prefetch IO. ATTENTION: the transaction started after enabled is affected.",
++  NULL, NULL, FALSE);
++
+ static handler *innobase_create_handler(handlerton *hton,
+                                         TABLE_SHARE *table,
+@@ -1689,6 +1695,8 @@
+       trx->check_unique_secondary = !thd_test_options(
+               thd, OPTION_RELAXED_UNIQUE_CHECKS);
++      trx->fake_changes = THDVAR(thd, fake_changes);
++
+ #ifdef EXTENDED_SLOWLOG
+       if (thd_log_slow_verbosity(thd) & SLOG_V_INNODB) {
+               trx->take_stats = TRUE;
+@@ -3196,6 +3204,11 @@
+               trx_search_latch_release_if_reserved(trx);
+       }
++      if (trx->fake_changes && (all || (!thd_test_options(thd, OPTION_NOT_AUTOCOMMIT | OPTION_BEGIN)))) {
++              innobase_rollback(hton, thd, all); /* rollback implicitly */
++              thd->stmt_da->reset_diagnostics_area(); /* because debug assertion code complains, if something left */
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
+       /* Transaction is deregistered only in a commit or a rollback. If
+       it is deregistered we know there cannot be resources to be freed
+       and we could return immediately.  For the time being, we play safe
+@@ -7545,6 +7558,12 @@
+       trx = innobase_trx_allocate(thd);
++      if (trx->fake_changes) {
++              innobase_commit_low(trx);
++              trx_free_for_mysql(trx);
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       /* Latch the InnoDB data dictionary exclusively so that no deadlocks
+       or lock waits can happen in it during a table create operation.
+       Drop table etc. do this latching in row0mysql.c. */
+@@ -7765,6 +7784,10 @@
+               DBUG_RETURN(HA_ERR_CRASHED);
+       }
++      if (prebuilt->trx->fake_changes) {
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       /* Truncate the table in InnoDB */
+       error = row_truncate_table_for_mysql(prebuilt->table, prebuilt->trx);
+@@ -7821,6 +7844,12 @@
+       trx = innobase_trx_allocate(thd);
++      if (trx->fake_changes) {
++              innobase_commit_low(trx);
++              trx_free_for_mysql(trx);
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       name_len = strlen(name);
+       ut_a(name_len < 1000);
+@@ -7907,6 +7936,12 @@
+       trx->mysql_thd = NULL;
+ #else
+       trx = innobase_trx_allocate(thd);
++      if (trx->fake_changes) {
++              my_free(namebuf);
++              innobase_commit_low(trx);
++              trx_free_for_mysql(trx);
++              return; /* ignore */
++      }
+ #endif
+       row_drop_database_for_mysql(namebuf, trx);
+       my_free(namebuf);
+@@ -8012,6 +8047,11 @@
+       trx_search_latch_release_if_reserved(parent_trx);
+       trx = innobase_trx_allocate(thd);
++      if (trx->fake_changes) {
++              innobase_commit_low(trx);
++              trx_free_for_mysql(trx);
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
+       error = innobase_rename_table(trx, from, to, TRUE);
+@@ -10872,6 +10912,10 @@
+               return(0);
+       }
++      if (trx->fake_changes) {
++              return(0);
++      }
++
+       thd_get_xid(thd, (MYSQL_XID*) &trx->xid);
+       /* Release a possible FIFO ticket and search latch. Since we will
+@@ -12420,6 +12464,7 @@
+   MYSQL_SYSVAR(rollback_segments),
+   MYSQL_SYSVAR(corrupt_table_action),
+   MYSQL_SYSVAR(lazy_drop_table),
++  MYSQL_SYSVAR(fake_changes),
+   NULL
+ };
+--- a/storage/innobase/handler/handler0alter.cc
++++ b/storage/innobase/handler/handler0alter.cc
+@@ -695,6 +695,10 @@
+       possible adaptive hash latch to avoid deadlocks of threads. */
+       trx_search_latch_release_if_reserved(prebuilt->trx);
++      if (prebuilt->trx->fake_changes) {
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       /* Check if the index name is reserved. */
+       if (innobase_index_name_is_reserved(user_thd, key_info, num_of_keys)) {
+               DBUG_RETURN(-1);
+@@ -732,6 +736,13 @@
+       /* Create a background transaction for the operations on
+       the data dictionary tables. */
+       trx = innobase_trx_allocate(user_thd);
++      if (trx->fake_changes) {
++              mem_heap_free(heap);
++              trx_general_rollback_for_mysql(trx, NULL);
++              trx_free_for_mysql(trx);
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       trx_start_if_not_started(trx);
+       /* Create table containing all indexes to be built in this
+@@ -1092,6 +1103,10 @@
+       trx_search_latch_release_if_reserved(prebuilt->trx);
+       trx = prebuilt->trx;
++      if (trx->fake_changes) {
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       /* Test and mark all the indexes to be dropped */
+       row_mysql_lock_data_dictionary(trx);
+@@ -1296,6 +1311,12 @@
+       /* Create a background transaction for the operations on
+       the data dictionary tables. */
+       trx = innobase_trx_allocate(user_thd);
++      if (trx->fake_changes) {
++              trx_general_rollback_for_mysql(trx, NULL);
++              trx_free_for_mysql(trx);
++              DBUG_RETURN(HA_ERR_WRONG_COMMAND);
++      }
++
+       trx_start_if_not_started(trx);
+       /* Flag this transaction as a dictionary operation, so that
+--- a/storage/innobase/ibuf/ibuf0ibuf.c
++++ b/storage/innobase/ibuf/ibuf0ibuf.c
+@@ -3496,6 +3496,8 @@
+       ut_a(trx_sys_multiple_tablespace_format);
++      ut_ad(!(thr_get_trx(thr)->fake_changes));
++
+       do_merge = FALSE;
+       /* Perform dirty reads of ibuf->size and ibuf->max_size, to
+--- a/storage/innobase/include/trx0trx.h
++++ b/storage/innobase/include/trx0trx.h
+@@ -512,6 +512,7 @@
+                                       FALSE, one can save CPU time and about
+                                       150 bytes in the undo log size as then
+                                       we skip XA steps */
++      ulint           fake_changes;
+       ulint           flush_log_later;/* In 2PC, we hold the
+                                       prepare_commit mutex across
+                                       both phases. In that case, we
+--- a/storage/innobase/lock/lock0lock.c
++++ b/storage/innobase/lock/lock0lock.c
+@@ -3912,6 +3912,10 @@
+       trx = thr_get_trx(thr);
++      if (trx->fake_changes && mode == LOCK_IX) {
++              mode = LOCK_IS;
++      }
++
+       lock_mutex_enter_kernel();
+       /* Look for stronger locks the same trx already has on the table */
+@@ -5114,6 +5118,11 @@
+       }
+       trx = thr_get_trx(thr);
++
++      if (trx->fake_changes) {
++              return(DB_SUCCESS);
++      }
++
+       next_rec = page_rec_get_next_const(rec);
+       next_rec_heap_no = page_rec_get_heap_no(next_rec);
+@@ -5282,6 +5291,10 @@
+               return(DB_SUCCESS);
+       }
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              return(DB_SUCCESS);
++      }
++
+       heap_no = rec_offs_comp(offsets)
+               ? rec_get_heap_no_new(rec)
+               : rec_get_heap_no_old(rec);
+@@ -5340,6 +5353,10 @@
+               return(DB_SUCCESS);
+       }
++      if (thr && thr_get_trx(thr)->fake_changes) {
++              return(DB_SUCCESS);
++      }
++
+       heap_no = page_rec_get_heap_no(rec);
+       /* Another transaction cannot have an implicit lock on the record,
+@@ -5427,6 +5444,10 @@
+               return(DB_SUCCESS);
+       }
++      if (thr && thr_get_trx(thr)->fake_changes && mode == LOCK_X) {
++              mode = LOCK_S;
++      }
++
+       heap_no = page_rec_get_heap_no(rec);
+       lock_mutex_enter_kernel();
+@@ -5503,6 +5524,10 @@
+               return(DB_SUCCESS);
+       }
++      if (thr && thr_get_trx(thr)->fake_changes && mode == LOCK_X) {
++              mode = LOCK_S;
++      }
++
+       heap_no = page_rec_get_heap_no(rec);
+       lock_mutex_enter_kernel();
+--- a/storage/innobase/que/que0que.c
++++ b/storage/innobase/que/que0que.c
+@@ -1417,6 +1417,12 @@
+       ut_a(trx->error_state == DB_SUCCESS);
++      if (trx->fake_changes) {
++              /* fake_changes should not access to system tables */
++              fprintf(stderr, "InnoDB: ERROR: innodb_fake_changes tried to access to system tables.\n");
++              return(DB_ERROR);
++      }
++
+       if (reserve_dict_mutex) {
+               mutex_enter(&dict_sys->mutex);
+       }
+--- a/storage/innobase/row/row0ins.c
++++ b/storage/innobase/row/row0ins.c
+@@ -1502,6 +1502,11 @@
+       if (UNIV_LIKELY_NULL(heap)) {
+               mem_heap_free(heap);
+       }
++
++      if (trx->fake_changes) {
++              err = DB_SUCCESS;
++      }
++
+       return(err);
+ }
+@@ -2007,7 +2012,7 @@
+       }
+       btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE,
+-                                  search_mode,
++                                  thr_get_trx(thr)->fake_changes ? BTR_SEARCH_LEAF : search_mode,
+                                   &cursor, 0, __FILE__, __LINE__, &mtr);
+       if (cursor.flag == BTR_CUR_INSERT_TO_IBUF) {
+@@ -2067,7 +2072,7 @@
+                       btr_cur_search_to_nth_level(index, 0, entry,
+                                                   PAGE_CUR_LE,
+-                                                  mode | BTR_INSERT,
++                                                  thr_get_trx(thr)->fake_changes ? BTR_SEARCH_LEAF : (mode | BTR_INSERT),
+                                                   &cursor, 0,
+                                                   __FILE__, __LINE__, &mtr);
+               }
+@@ -2121,6 +2126,22 @@
+       if (UNIV_LIKELY_NULL(big_rec)) {
+               rec_t*  rec;
+               ulint*  offsets;
++
++              if (thr_get_trx(thr)->fake_changes) {
++                      /* skip store extern */
++                      if (modify) {
++                              dtuple_big_rec_free(big_rec);
++                      } else {
++                              dtuple_convert_back_big_rec(index, entry, big_rec);
++                      }
++
++                      if (UNIV_LIKELY_NULL(heap)) {
++                              mem_heap_free(heap);
++                      }
++
++                      return(err);
++              }
++
+               mtr_start(&mtr);
+               btr_cur_search_to_nth_level(index, 0, entry, PAGE_CUR_LE,
+--- a/storage/innobase/row/row0mysql.c
++++ b/storage/innobase/row/row0mysql.c
+@@ -1246,6 +1246,7 @@
+               prebuilt->table->stat_n_rows--;
+       }
++      if (!(trx->fake_changes))
+       row_update_statistics_if_needed(prebuilt->table);
+       trx->op_info = "";
+@@ -1505,6 +1506,7 @@
+       that changes indexed columns, UPDATEs that change only non-indexed
+       columns would not affect statistics. */
+       if (node->is_delete || !(node->cmpl_info & UPD_NODE_NO_ORD_CHANGE)) {
++              if (!(trx->fake_changes))
+               row_update_statistics_if_needed(prebuilt->table);
+       }
+@@ -1722,6 +1724,7 @@
+               srv_n_rows_updated++;
+       }
++      if (!(trx->fake_changes))
+       row_update_statistics_if_needed(table);
+       return(err);
+--- a/storage/innobase/row/row0upd.c
++++ b/storage/innobase/row/row0upd.c
+@@ -1603,7 +1603,8 @@
+               mode |= BTR_DELETE_MARK;
+       }
+-      search_result = row_search_index_entry(index, entry, mode,
++      search_result = row_search_index_entry(index, entry,
++                                             trx->fake_changes ? BTR_SEARCH_LEAF : mode,
+                                              &pcur, &mtr);
+       btr_cur = btr_pcur_get_btr_cur(&pcur);
+@@ -1850,9 +1851,11 @@
+               the previous invocation of this function. Mark the
+               off-page columns in the entry inherited. */
++              if (!(trx->fake_changes)) {
+               change_ownership = row_upd_clust_rec_by_insert_inherit(
+                       NULL, NULL, entry, node->update);
+               ut_a(change_ownership);
++              }
+               /* fall through */
+       case UPD_NODE_INSERT_CLUSTERED:
+               /* A lock wait occurred in row_ins_index_entry() in
+@@ -1882,7 +1885,7 @@
+               delete-marked old record, mark them disowned by the
+               old record and owned by the new entry. */
+-              if (rec_offs_any_extern(offsets)) {
++              if (rec_offs_any_extern(offsets) && !(trx->fake_changes)) {
+                       change_ownership = row_upd_clust_rec_by_insert_inherit(
+                               rec, offsets, entry, node->update);
+@@ -2012,7 +2015,8 @@
+       the same transaction do not modify the record in the meantime.
+       Therefore we can assert that the restoration of the cursor succeeds. */
+-      ut_a(btr_pcur_restore_position(BTR_MODIFY_TREE, pcur, mtr));
++      ut_a(btr_pcur_restore_position(thr_get_trx(thr)->fake_changes ? BTR_SEARCH_LEAF : BTR_MODIFY_TREE,
++                                     pcur, mtr));
+       ut_ad(!rec_get_deleted_flag(btr_pcur_get_rec(pcur),
+                                   dict_table_is_comp(index->table)));
+@@ -2022,7 +2026,8 @@
+                                        node->cmpl_info, thr, mtr);
+       mtr_commit(mtr);
+-      if (err == DB_SUCCESS && big_rec) {
++      /* skip store extern for fake_changes */
++      if (err == DB_SUCCESS && big_rec && !(thr_get_trx(thr)->fake_changes)) {
+               ulint           offsets_[REC_OFFS_NORMAL_SIZE];
+               rec_t*          rec;
+               rec_offs_init(offsets_);
+@@ -2146,7 +2151,8 @@
+       ut_a(pcur->rel_pos == BTR_PCUR_ON);
+-      success = btr_pcur_restore_position(BTR_MODIFY_LEAF, pcur, mtr);
++      success = btr_pcur_restore_position(thr_get_trx(thr)->fake_changes ? BTR_SEARCH_LEAF : BTR_MODIFY_LEAF,
++                                          pcur, mtr);
+       if (!success) {
+               err = DB_RECORD_NOT_FOUND;
+--- a/storage/innobase/trx/trx0trx.c
++++ b/storage/innobase/trx/trx0trx.c
+@@ -121,6 +121,8 @@
+       trx->support_xa = TRUE;
++      trx->fake_changes = FALSE;
++
+       trx->check_foreigns = TRUE;
+       trx->check_unique_secondary = TRUE;
+--- /dev/null
++++ b/mysql-test/r/percona_innodb_fake_changes.result
+@@ -0,0 +1,55 @@
++DROP TABLE IF EXISTS t1;
++# Checking variables
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++Variable_name Value
++innodb_fake_changes   OFF
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++VARIABLE_VALUE
++OFF
++SET innodb_fake_changes=1;
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++Variable_name Value
++innodb_fake_changes   ON
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++VARIABLE_VALUE
++ON
++SET innodb_fake_changes=default;
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++Variable_name Value
++innodb_fake_changes   OFF
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++VARIABLE_VALUE
++OFF
++# Explicit COMMIT should fail when innodb_fake_changes is enabled
++# DML should be fine
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (1);
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++INSERT INTO t1 VALUES (2);
++UPDATE t1 SET a=0;
++DELETE FROM t1 LIMIT 1;
++SELECT * FROM t1;
++a
++1
++COMMIT;
++ERROR HY000: Got error 131 during COMMIT
++SET innodb_fake_changes=default;
++DROP TABLE t1;
++# DDL must result in error
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++CREATE TABLE t2 (a INT) ENGINE=InnoDB;
++ERROR HY000: Can't create table 'test.t2' (errno: 131)
++DROP TABLE t1;
++ERROR 42S02: Unknown table 't1'
++TRUNCATE TABLE t1;
++ERROR HY000: Got error 131 during COMMIT
++ALTER TABLE t1 ENGINE=MyISAM;
++ERROR HY000: Got error 131 during COMMIT
++ROLLBACK;
++SET innodb_fake_changes=default;
++DROP TABLE t1;
+--- /dev/null
++++ b/mysql-test/r/percona_innodb_fake_changes_locks.result
+@@ -0,0 +1,19 @@
++DROP TABLE IF EXISTS t1;
++# Verifying that X_LOCK not acquired
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (1);
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++SELECT * FROM t1 FOR UPDATE;
++a
++1
++SET innodb_lock_wait_timeout=3;
++UPDATE t1 SET a=2;
++ERROR HY000: Lock wait timeout exceeded; try restarting transaction
++SELECT * FROM t1 LOCK IN SHARE MODE;
++a
++1
++ROLLBACK;
++SET innodb_fake_changes=default;
++DROP TABLE t1;
+--- /dev/null
++++ b/mysql-test/t/percona_innodb_fake_changes.test
+@@ -0,0 +1,49 @@
++--source include/have_innodb.inc
++
++--disable_warnings
++DROP TABLE IF EXISTS t1;
++--enable_warnings
++
++
++--echo # Checking variables
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++SET innodb_fake_changes=1;
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++SET innodb_fake_changes=default;
++SHOW VARIABLES LIKE 'innodb_fake_changes';
++SELECT VARIABLE_VALUE FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE VARIABLE_NAME='innodb_fake_changes';
++
++--echo # Explicit COMMIT should fail when innodb_fake_changes is enabled
++--echo # DML should be fine
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (1);
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++INSERT INTO t1 VALUES (2);
++UPDATE t1 SET a=0;
++DELETE FROM t1 LIMIT 1;
++SELECT * FROM t1;
++--error 1180
++COMMIT;
++SET innodb_fake_changes=default;
++DROP TABLE t1;
++
++--echo # DDL must result in error
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++--error 1005
++CREATE TABLE t2 (a INT) ENGINE=InnoDB;
++--error 1051
++DROP TABLE t1;
++--error 1180
++TRUNCATE TABLE t1;
++--error 1180
++ALTER TABLE t1 ENGINE=MyISAM;
++ROLLBACK;
++SET innodb_fake_changes=default;
++DROP TABLE t1;
+--- /dev/null
++++ b/mysql-test/t/percona_innodb_fake_changes_locks.test
+@@ -0,0 +1,24 @@
++--source include/have_innodb.inc
++
++--disable_warnings
++DROP TABLE IF EXISTS t1;
++--enable_warnings
++
++--echo # Verifying that X_LOCK not acquired
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++INSERT INTO t1 VALUES (1);
++--connect (conn1,localhost,root,,)
++--connection conn1
++SET autocommit=0;
++SET innodb_fake_changes=1;
++BEGIN;
++SELECT * FROM t1 FOR UPDATE;
++--connection default
++SET innodb_lock_wait_timeout=3;
++--error 1205
++UPDATE t1 SET a=2;
++SELECT * FROM t1 LOCK IN SHARE MODE;
++--connection conn1
++ROLLBACK;
++SET innodb_fake_changes=default;
++DROP TABLE t1;
index b93538853942785c60cb34e5f1fa8a792113b4d1..382c401bc8921956b5e4bb218fa5635d41274e05 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -511,6 +511,27 @@
+@@ -512,6 +512,27 @@
        return(checksum);
  }
  
@@ -35,7 +35,7 @@
  /********************************************************************//**
  In versions < 4.0.14 and < 4.1.1 there was a bug that the checksum only
  looked at the first few bytes of the page. This calculates that old
-@@ -627,9 +648,21 @@
+@@ -628,9 +649,21 @@
                /* InnoDB versions < 4.0.14 and < 4.1.1 stored the space id
                (always equal to 0), to FIL_PAGE_SPACE_OR_CHKSUM */
  
@@ -58,7 +58,7 @@
                    != buf_calc_page_new_checksum(read_buf)) {
  
                        return(TRUE);
-@@ -653,6 +686,7 @@
+@@ -654,6 +687,7 @@
        dict_index_t*   index;
  #endif /* !UNIV_HOTBACKUP */
        ulint           checksum;
@@ -66,7 +66,7 @@
        ulint           old_checksum;
        ulint           size    = zip_size;
  
-@@ -739,12 +773,14 @@
+@@ -740,12 +774,14 @@
  
        checksum = srv_use_checksums
                ? buf_calc_page_new_checksum(read_buf) : BUF_NO_CHECKSUM_MAGIC;
@@ -82,7 +82,7 @@
                " checksum %lu\n"
                "InnoDB: stored checksum %lu, prior-to-4.0.14-form"
                " stored checksum %lu\n"
-@@ -753,7 +789,7 @@
+@@ -754,7 +790,7 @@
                "InnoDB: Page number (if stored to page already) %lu,\n"
                "InnoDB: space id (if created with >= MySQL-4.1.1"
                " and stored already) %lu\n",
  static my_bool        innobase_recovery_stats                 = TRUE;
  static my_bool        innobase_locks_unsafe_for_binlog        = FALSE;
  static my_bool        innobase_overwrite_relay_log_info       = FALSE;
-@@ -2625,6 +2626,7 @@
+@@ -2656,6 +2657,7 @@
  
        srv_use_doublewrite_buf = (ibool) innobase_use_doublewrite;
        srv_use_checksums = (ibool) innobase_use_checksums;
 +      srv_fast_checksum = (ibool) innobase_fast_checksum;
  
- #ifdef HAVE_LARGE_PAGES
-         if ((os_use_large_pages = (ibool) my_use_large_pages))
-@@ -11432,6 +11434,15 @@
+       srv_blocking_lru_restore = (ibool) innobase_blocking_lru_restore;
+@@ -11533,6 +11535,15 @@
    "Disable with --skip-innodb-checksums.",
    NULL, NULL, TRUE);
  
  static MYSQL_SYSVAR_STR(data_home_dir, innobase_data_home_dir,
    PLUGIN_VAR_READONLY,
    "The common part for InnoDB table spaces.",
-@@ -11946,6 +11957,7 @@
+@@ -12064,6 +12075,7 @@
    MYSQL_SYSVAR(buffer_pool_size),
    MYSQL_SYSVAR(buffer_pool_instances),
    MYSQL_SYSVAR(checksums),
    MYSQL_SYSVAR(data_file_path),
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -643,6 +643,11 @@
+@@ -634,6 +634,11 @@
  buf_calc_page_new_checksum(
  /*=======================*/
        const byte*     page);  /*!< in: buffer page */
  #define FIL_PAGE_END_LSN_OLD_CHKSUM 8 /*!< the low 4 bytes of this are used
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -224,6 +224,7 @@
+@@ -229,6 +229,7 @@
  
  extern ibool  srv_use_doublewrite_buf;
  extern ibool  srv_use_checksums;
 +}
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -414,6 +414,7 @@
+@@ -419,6 +419,7 @@
  
  UNIV_INTERN ibool     srv_use_doublewrite_buf = TRUE;
  UNIV_INTERN ibool     srv_use_checksums = TRUE;
index ba531fe539b3f749676e88ad02bfcfa5e752391b..dde4b9da64745454304524fadf955ee14ae1c886 100644 (file)
  static my_bool innobase_thread_concurrency_timer_based;
  static long long innobase_buffer_pool_size, innobase_log_file_size;
  
-@@ -2321,6 +2324,65 @@
+@@ -2352,6 +2355,65 @@
        }
  #endif /* DBUG_OFF */
  
  #ifndef MYSQL_SERVER
        innodb_overwrite_relay_log_info = FALSE;
  #endif
-@@ -7252,9 +7314,9 @@
+@@ -7291,9 +7353,9 @@
                                | DICT_TF_COMPACT
                                | DICT_TF_FORMAT_ZIP
                                << DICT_TF_FORMAT_SHIFT;
                }
        }
  
-@@ -11443,6 +11505,16 @@
+@@ -11544,6 +11606,16 @@
    "#### Attention: The checksum is not compatible for normal or disabled version! ####",
    NULL, NULL, FALSE);
  
  static MYSQL_SYSVAR_STR(data_home_dir, innobase_data_home_dir,
    PLUGIN_VAR_READONLY,
    "The common part for InnoDB table spaces.",
-@@ -11952,6 +12024,8 @@
+@@ -12070,6 +12142,8 @@
    NULL, NULL, 0, &corrupt_table_action_typelib);
  
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(buffer_pool_size),
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1722,7 +1722,7 @@
+@@ -1715,7 +1715,7 @@
        time_t          last_printout_time;
                                        /*!< when buf_print_io was last time
                                        called */
                                        /*!< Statistics of buddy system,
                                        indexed by block size */
        buf_pool_stat_t stat;           /*!< current statistics */
-@@ -1820,7 +1820,7 @@
+@@ -1813,7 +1813,7 @@
        UT_LIST_BASE_NODE_T(buf_page_t) zip_clean;
                                        /*!< unmodified compressed pages */
  #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */
                                        /*!< buddy free lists */
  
        buf_page_t                      watch[BUF_POOL_WATCH_SIZE];
-@@ -1828,9 +1828,9 @@
+@@ -1821,9 +1821,9 @@
                                        pool watches. Protected by
                                        buf_pool->mutex. */
  
  #define TRX_SYS_MYSQL_MASTER_LOG_INFO (UNIV_PAGE_SIZE - 2000)
 --- a/storage/innobase/include/univ.i
 +++ b/storage/innobase/include/univ.i
-@@ -310,9 +310,13 @@
+@@ -313,9 +313,13 @@
  */
  
  /* The 2-logarithm of UNIV_PAGE_SIZE: */
  
  /* Maximum number of parallel threads in a parallelized operation */
  #define UNIV_MAX_PARALLELISM  32
-@@ -431,7 +435,7 @@
+@@ -434,7 +438,7 @@
  stored part of the field in the tablespace. The length field then
  contains the sum of the following flag and the locally stored len. */
  
  
  /* Some macros to improve branch prediction and reduce cache misses */
  #if defined(__GNUC__) && (__GNUC__ > 2) && ! defined(__INTEL_COMPILER)
-@@ -534,4 +538,6 @@
+@@ -537,4 +541,6 @@
        UNIV_MEM_ALLOC(addr, size);                     \
  } while (0)
  
  
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -234,6 +234,13 @@
- UNIV_INTERN ulint     srv_n_read_io_threads   = ULINT_MAX;
- UNIV_INTERN ulint     srv_n_write_io_threads  = ULINT_MAX;
+@@ -236,6 +236,14 @@
  
+ /* Switch to enable random read ahead. */
+ UNIV_INTERN my_bool   srv_random_read_ahead   = FALSE;
++
 +/* The universal page size of the database */
 +UNIV_INTERN ulint     srv_page_size_shift     = 0;
 +UNIV_INTERN ulint     srv_page_size           = 0;
  readahead request. */
 --- a/storage/innobase/srv/srv0start.c
 +++ b/storage/innobase/srv/srv0start.c
-@@ -1561,11 +1561,13 @@
+@@ -1562,11 +1562,13 @@
        }
  #endif /* UNIV_LOG_ARCHIVE */
  
  
                return(DB_ERROR);
        }
-@@ -1574,7 +1576,7 @@
+@@ -1575,7 +1577,7 @@
  
        for (i = 0; i < srv_n_data_files; i++) {
  #ifndef __WIN__
index 794ed60449a6669058723dd73d460104e5c5739d..981ea10bbda5574eb6a33a918b6909e59768da79 100644 (file)
@@ -12,7 +12,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -2040,6 +2040,27 @@
+@@ -2041,6 +2041,27 @@
  #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */
        }
  
@@ -40,7 +40,7 @@
        if (UNIV_UNLIKELY(!bpage->zip.data)) {
                /* There is no compressed page. */
  err_exit:
-@@ -2549,6 +2570,27 @@
+@@ -2550,6 +2571,27 @@
                block = (buf_block_t*) buf_page_hash_get_low(
                        buf_pool, space, offset, fold);
                if (block) {
@@ -68,7 +68,7 @@
                        block_mutex = buf_page_get_mutex_enter((buf_page_t*)block);
                        ut_a(block_mutex);
                }
-@@ -3467,11 +3509,28 @@
+@@ -3472,11 +3514,28 @@
  
        fold = buf_page_address_fold(space, offset);
  
@@ -97,7 +97,7 @@
        if (watch_page && !buf_pool_watch_is_sentinel(buf_pool, watch_page)) {
                /* The page is already in the buffer pool. */
                watch_page = NULL;
-@@ -3602,6 +3661,7 @@
+@@ -3607,6 +3666,7 @@
                bpage->state    = BUF_BLOCK_ZIP_PAGE;
                bpage->space    = space;
                bpage->offset   = offset;
  
  #ifdef UNIV_DEBUG
                bpage->in_page_hash = FALSE;
-@@ -3686,6 +3746,7 @@
+@@ -3691,6 +3751,7 @@
  
        fold = buf_page_address_fold(space, offset);
  
        //buf_pool_mutex_enter(buf_pool);
        mutex_enter(&buf_pool->LRU_list_mutex);
        rw_lock_x_lock(&buf_pool->page_hash_latch);
-@@ -3693,6 +3754,21 @@
+@@ -3698,6 +3759,21 @@
        block = (buf_block_t*) buf_page_hash_get_low(
                buf_pool, space, offset, fold);
  
        if (block
            && buf_page_in_file(&block->page)
            && !buf_pool_watch_is_sentinel(buf_pool, &block->page)) {
-@@ -3984,8 +4060,11 @@
+@@ -4051,8 +4127,11 @@
        }
  
        if (io_type == BUF_IO_WRITE
        ut_a(ret);
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -12023,6 +12023,12 @@
+@@ -12141,6 +12141,12 @@
    "except for the deletion.",
    NULL, NULL, 0, &corrupt_table_action_typelib);
  
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(page_size),
    MYSQL_SYSVAR(log_block_size),
-@@ -12114,6 +12120,7 @@
+@@ -12235,6 +12241,7 @@
    MYSQL_SYSVAR(purge_batch_size),
    MYSQL_SYSVAR(rollback_segments),
    MYSQL_SYSVAR(corrupt_table_action),
    NULL
  };
  
-@@ -12123,7 +12130,7 @@
+@@ -12244,7 +12251,7 @@
    &innobase_storage_engine,
    innobase_hton_name,
    plugin_author,
    NULL, /* Plugin Deinit */
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1477,6 +1477,7 @@
+@@ -1468,6 +1468,7 @@
                                        0 if the block was never accessed
                                        in the buffer pool */
        /* @} */
        ibool           file_page_was_freed;
 --- a/storage/innobase/include/buf0buf.ic
 +++ b/storage/innobase/include/buf0buf.ic
-@@ -408,6 +408,7 @@
+@@ -426,6 +426,7 @@
        buf_block_set_state(block, BUF_BLOCK_FILE_PAGE);
        block->page.space = space;
        block->page.offset = page_no;
  
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -244,6 +244,8 @@
+@@ -249,6 +249,8 @@
  extern ulint  srv_pass_corrupt_table;
  
  extern ulint  srv_dict_size_limit;
  extern ulint  srv_n_rows_inserted;
 --- a/storage/innobase/include/sync0sync.h
 +++ b/storage/innobase/include/sync0sync.h
-@@ -693,6 +693,7 @@
+@@ -690,6 +690,7 @@
  #define       SYNC_BUF_POOL           150     /* Buffer pool mutex */
  #define       SYNC_BUF_FLUSH_LIST     145     /* Buffer flush list mutex */
  #define SYNC_DOUBLEWRITE      140
 +#define       SYNC_OUTER_ANY_LATCH    136
  #define       SYNC_ANY_LATCH          135
- #define SYNC_THR_LOCAL                133
  #define       SYNC_MEM_HASH           131
+ #define       SYNC_MEM_POOL           130
 --- a/storage/innobase/include/univ.i
 +++ b/storage/innobase/include/univ.i
-@@ -52,6 +52,11 @@
+@@ -53,6 +53,11 @@
  #define INNODB_VERSION_MINOR  1
  #define INNODB_VERSION_BUGFIX 8
  
  /* The following is the InnoDB version as shown in
  SELECT plugin_version FROM information_schema.plugins;
  calculated in make_version_string() in sql/sql_show.cc like this:
-@@ -64,7 +69,8 @@
+@@ -65,7 +70,8 @@
  #define INNODB_VERSION_STR                    \
        IB_TO_STR(INNODB_VERSION_MAJOR) "."     \
        IB_TO_STR(INNODB_VERSION_MINOR) "."     \
  
  /** Provide optional 4.x backwards compatibility for 5.0 and above */
  UNIV_INTERN ibool     row_rollback_on_timeout = FALSE;
-@@ -1191,6 +1192,13 @@
+@@ -1192,6 +1193,13 @@
  
        thr = que_fork_get_first_thr(prebuilt->ins_graph);
  
        if (prebuilt->sql_stat_start) {
                node->state = INS_NODE_SET_IX_LOCK;
                prebuilt->sql_stat_start = FALSE;
-@@ -2575,10 +2583,29 @@
+@@ -2576,10 +2584,29 @@
  
                        err = DB_ERROR;
                } else {
                }
        }
  
-@@ -2927,6 +2954,19 @@
+@@ -2928,6 +2955,19 @@
                        table->space = space;
                        index = dict_table_get_first_index(table);
                        do {
                        } while (index);
 --- a/storage/innobase/row/row0sel.c
 +++ b/storage/innobase/row/row0sel.c
-@@ -3367,6 +3367,7 @@
+@@ -3418,6 +3418,7 @@
        ulint           offsets_[REC_OFFS_NORMAL_SIZE];
        ulint*          offsets                         = offsets_;
        ibool           table_lock_waited               = FALSE;
  
        rec_offs_init(offsets_);
  
-@@ -3738,6 +3739,17 @@
+@@ -3796,6 +3797,17 @@
  
        /* Do some start-of-statement preparations */
  
        if (!prebuilt->sql_stat_start) {
                /* No need to set an intention lock or assign a read view */
  
-@@ -3748,6 +3760,18 @@
+@@ -3806,6 +3818,18 @@
                              " perform a consistent read\n"
                              "InnoDB: but the read view is not assigned!\n",
                              stderr);
                        ut_error;
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -441,6 +441,8 @@
+@@ -447,6 +447,8 @@
  UNIV_INTERN ulint     srv_pass_corrupt_table = 0; /* 0:disable 1:enable */
  
  UNIV_INTERN ulint     srv_dict_size_limit = 0;
  UNIV_INTERN ulong     srv_n_free_tickets_to_enter = 500;
 --- a/storage/innobase/srv/srv0start.c
 +++ b/storage/innobase/srv/srv0start.c
-@@ -2161,7 +2161,7 @@
+@@ -2167,7 +2167,7 @@
        if (srv_print_verbose_log) {
                ut_print_timestamp(stderr);
                fprintf(stderr,
        }
 --- a/storage/innobase/sync/sync0sync.c
 +++ b/storage/innobase/sync/sync0sync.c
-@@ -1225,6 +1225,7 @@
+@@ -1219,6 +1219,7 @@
+       case SYNC_LOG:
        case SYNC_LOG_FLUSH_ORDER:
-       case SYNC_THR_LOCAL:
        case SYNC_ANY_LATCH:
 +      case SYNC_OUTER_ANY_LATCH:
        case SYNC_FILE_FORMAT_TAG:
index 9f57852bd18503a8480d5561d4a5458dd84e3306..8ffa03c16580c29bd25b64d41fb03d718881ee04 100644 (file)
@@ -45,8 +45,8 @@
  
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -260,6 +260,10 @@
-               = BUF_READ_AHEAD_LINEAR_AREA(buf_pool);
+@@ -427,6 +427,10 @@
+               = BUF_READ_AHEAD_AREA(buf_pool);
        ulint           threshold;
  
 +      if (!(srv_read_ahead & 2)) {
  
  static handler *innobase_create_handler(handlerton *hton,
                                          TABLE_SHARE *table,
-@@ -839,6 +845,17 @@
+@@ -841,6 +847,17 @@
        }
  }
  
  /********************************************************************//**
  Obtain the InnoDB transaction of a MySQL thread.
  @return       reference to transaction pointer */
-@@ -2442,6 +2459,9 @@
+@@ -2471,6 +2488,9 @@
        srv_n_read_io_threads = (ulint) innobase_read_io_threads;
        srv_n_write_io_threads = (ulint) innobase_write_io_threads;
  
        srv_force_recovery = (ulint) innobase_force_recovery;
  
        srv_use_doublewrite_buf = (ibool) innobase_use_doublewrite;
-@@ -11036,7 +11056,7 @@
+@@ -11133,7 +11153,7 @@
    PLUGIN_VAR_OPCMDARG | PLUGIN_VAR_READONLY,
    "Purge threads can be either 0 or 1.",
    NULL, NULL,
    0,                  /* Minimum value */
    1, 0);              /* Maximum value */
  
-@@ -11078,12 +11098,18 @@
+@@ -11175,12 +11195,18 @@
    innodb_file_format_max_validate,
    innodb_file_format_max_update, "Antelope");
  
  
  static MYSQL_SYSVAR_STR(flush_method, innobase_file_flush_method,
    PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
-@@ -11183,7 +11209,7 @@
+@@ -11285,7 +11311,7 @@
  static MYSQL_SYSVAR_LONGLONG(buffer_pool_size, innobase_buffer_pool_size,
    PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
    "The size of the memory buffer InnoDB uses to cache data and indexes of its tables.",
  
  static MYSQL_SYSVAR_LONG(buffer_pool_instances, innobase_buffer_pool_instances,
    PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
-@@ -11335,6 +11361,95 @@
+@@ -11442,6 +11468,95 @@
    "trigger a readahead.",
    NULL, NULL, 56, 0, 64, 0);
  
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(additional_mem_pool_size),
    MYSQL_SYSVAR(autoextend_increment),
-@@ -11355,6 +11470,7 @@
+@@ -11462,6 +11577,7 @@
    MYSQL_SYSVAR(file_format_check),
    MYSQL_SYSVAR(file_format_max),
    MYSQL_SYSVAR(flush_log_at_trx_commit),
    MYSQL_SYSVAR(flush_method),
    MYSQL_SYSVAR(force_recovery),
    MYSQL_SYSVAR(large_prefix),
-@@ -11393,6 +11509,13 @@
+@@ -11501,6 +11617,13 @@
    MYSQL_SYSVAR(show_verbose_locks),
    MYSQL_SYSVAR(show_locks_held),
    MYSQL_SYSVAR(version),
  
 --- a/storage/innobase/include/buf0rea.h
 +++ b/storage/innobase/include/buf0rea.h
-@@ -124,8 +124,7 @@
+@@ -149,8 +149,7 @@
  
  /** The size in pages of the area which the read-ahead algorithms read if
  invoked */
 +extern char   srv_use_global_flush_log_at_trx_commit;
  extern char   srv_adaptive_flushing;
  
-@@ -216,6 +217,16 @@
+ /* If this flag is TRUE, then we will load the indexes' (and tables') metadata
+@@ -221,6 +222,16 @@
  extern ulong  srv_max_purge_lag;
  
  extern ulong  srv_replication_delay;
  /*-------------------------------------------*/
  
  extern ulint  srv_n_rows_inserted;
-@@ -394,8 +405,9 @@
+@@ -399,8 +410,9 @@
                                when writing data files, but do flush
                                after writing to log files */
        SRV_UNIX_NOSYNC,        /*!< do not flush after writing */
  
  /* Try to flush dirty pages so as to avoid IO bursts at
  the checkpoints. */
-@@ -402,6 +403,17 @@
+@@ -404,6 +405,17 @@
  
  UNIV_INTERN ulong     srv_replication_delay           = 0;
  
  /*-------------------------------------------*/
  UNIV_INTERN ulong     srv_n_spin_wait_rounds  = 30;
  UNIV_INTERN ulong     srv_n_free_tickets_to_enter = 500;
-@@ -2709,7 +2721,7 @@
+@@ -2713,7 +2725,7 @@
  
        ut_ad(!mutex_own(&kernel_mutex));
  
  
        do {
                /* Check for shutdown and change in purge config. */
-@@ -2742,6 +2754,7 @@
+@@ -2746,6 +2758,7 @@
        ulint           n_pages_purged  = 0;
        ulint           n_bytes_merged;
        ulint           n_pages_flushed;
        ulint           n_bytes_archived;
        ulint           n_tables_to_drop;
        ulint           n_ios;
-@@ -2749,7 +2762,20 @@
+@@ -2753,7 +2766,20 @@
        ulint           n_ios_very_old;
        ulint           n_pend_ios;
        ulint           next_itr_time;
  
  #ifdef UNIV_DEBUG_THREAD_CREATION
        fprintf(stderr, "Master thread starts, id %lu\n",
-@@ -2771,6 +2797,9 @@
+@@ -2775,6 +2801,9 @@
  
        mutex_exit(&kernel_mutex);
  
  loop:
        /*****************************************************************/
        /* ---- When there is database activity by users, we cycle in this
-@@ -2801,9 +2830,13 @@
+@@ -2805,9 +2834,13 @@
        /* Sleep for 1 second on entrying the for loop below the first time. */
        next_itr_time = ut_time_ms() + 1000;
  
                /* ALTER TABLE in MySQL requires on Unix that the table handler
                can drop tables lazily after there no longer are SELECT
                queries to them. */
-@@ -2827,6 +2860,7 @@
+@@ -2831,6 +2864,7 @@
                srv_main_thread_op_info = "sleeping";
                srv_main_1_second_loops++;
  
                if (next_itr_time > cur_time
                    && srv_shutdown_state == SRV_SHUTDOWN_NONE) {
  
-@@ -2837,10 +2871,26 @@
+@@ -2841,10 +2875,26 @@
                                        (next_itr_time - cur_time)
                                         * 1000));
                        srv_main_sleeps++;
  
                /* Flush logs if needed */
                srv_sync_log_buffer_in_background();
-@@ -2860,7 +2910,7 @@
+@@ -2864,7 +2914,7 @@
                if (n_pend_ios < SRV_PEND_IO_THRESHOLD
                    && (n_ios - n_ios_old < SRV_RECENT_IO_ACTIVITY)) {
                        srv_main_thread_op_info = "doing insert buffer merge";
  
                        /* Flush logs if needed */
                        srv_sync_log_buffer_in_background();
-@@ -2877,7 +2927,11 @@
+@@ -2881,7 +2931,11 @@
                        n_pages_flushed = buf_flush_list(
                                PCT_IO(100), IB_ULONGLONG_MAX);
  
  
                        /* Try to keep the rate of flushing of dirty
                        pages such that redo log generation does not
-@@ -2893,6 +2947,224 @@
+@@ -2897,6 +2951,224 @@
                                                n_flush,
                                                IB_ULONGLONG_MAX);
                        }
                }
  
                if (srv_activity_count == old_activity_count) {
-@@ -2941,12 +3213,12 @@
+@@ -2945,12 +3217,12 @@
        even if the server were active */
  
        srv_main_thread_op_info = "doing insert buffer merge";
                srv_main_thread_op_info = "master purging";
  
                srv_master_do_purge();
-@@ -3024,7 +3296,7 @@
+@@ -3028,7 +3300,7 @@
                }
        }
  
                srv_main_thread_op_info = "master purging";
  
                srv_master_do_purge();
-@@ -3049,7 +3321,7 @@
+@@ -3053,7 +3325,7 @@
                buf_flush_list below. Otherwise, the system favors
                clean pages over cleanup throughput. */
                n_bytes_merged = ibuf_contract_for_n_pages(FALSE,
        }
  
        srv_main_thread_op_info = "reserving kernel mutex";
-@@ -3189,6 +3461,7 @@
+@@ -3193,6 +3465,7 @@
        srv_slot_t*     slot;
        ulint           retries = 0;
        ulint           n_total_purged = ULINT_UNDEFINED;
  
        ut_a(srv_n_purge_threads == 1);
  
-@@ -3209,9 +3482,12 @@
+@@ -3213,9 +3486,12 @@
  
        mutex_exit(&kernel_mutex);
  
  
                /* If there are very few records to purge or the last
                purge didn't purge any records then wait for activity.
-@@ -3258,6 +3534,16 @@
+@@ -3262,6 +3538,16 @@
                } while (n_pages_purged > 0 && !srv_fast_shutdown);
  
                srv_sync_log_buffer_in_background();
diff --git a/innodb_kill_idle_transaction.patch b/innodb_kill_idle_transaction.patch
new file mode 100644 (file)
index 0000000..eb7334b
--- /dev/null
@@ -0,0 +1,455 @@
+# name       : innodb_kill_idle_transaction.patch
+# introduced : 5.5.15
+# maintainer : Yasufumi
+#
+#!!! notice !!!
+# Any small change to this file in the main branch
+# should be done or reviewed by the maintainer!
+--- a/include/mysql/plugin.h
++++ b/include/mysql/plugin.h
+@@ -634,6 +634,12 @@
+ */
+ void thd_set_ha_data(MYSQL_THD thd, const struct handlerton *hton,
+                      const void *ha_data);
++
++int thd_command(const MYSQL_THD thd);
++long long thd_start_time(const MYSQL_THD thd);
++void thd_kill(unsigned long id);
++#define EXTENDED_FOR_KILLIDLE
++
+ #ifdef __cplusplus
+ }
+ #endif
+--- a/include/mysql/plugin_audit.h.pp
++++ b/include/mysql/plugin_audit.h.pp
+@@ -196,6 +196,9 @@
+ void *thd_get_ha_data(const void* thd, const struct handlerton *hton);
+ void thd_set_ha_data(void* thd, const struct handlerton *hton,
+                      const void *ha_data);
++int thd_command(const void* thd);
++long long thd_start_time(const void* thd);
++void thd_kill(unsigned long id);
+ struct mysql_event_general
+ {
+   unsigned int event_subclass;
+--- a/include/mysql/plugin_auth.h.pp
++++ b/include/mysql/plugin_auth.h.pp
+@@ -196,6 +196,9 @@
+ void *thd_get_ha_data(const void* thd, const struct handlerton *hton);
+ void thd_set_ha_data(void* thd, const struct handlerton *hton,
+                      const void *ha_data);
++int thd_command(const void* thd);
++long long thd_start_time(const void* thd);
++void thd_kill(unsigned long id);
+ #include <mysql/plugin_auth_common.h>
+ typedef struct st_plugin_vio_info
+ {
+--- a/include/mysql/plugin_ftparser.h.pp
++++ b/include/mysql/plugin_ftparser.h.pp
+@@ -149,6 +149,9 @@
+ void *thd_get_ha_data(const void* thd, const struct handlerton *hton);
+ void thd_set_ha_data(void* thd, const struct handlerton *hton,
+                      const void *ha_data);
++int thd_command(const void* thd);
++long long thd_start_time(const void* thd);
++void thd_kill(unsigned long id);
+ enum enum_ftparser_mode
+ {
+   MYSQL_FTPARSER_SIMPLE_MODE= 0,
+--- a/sql/sql_class.cc
++++ b/sql/sql_class.cc
+@@ -713,6 +713,42 @@
+   return buffer;
+ }
++/* extend for kill session of idle transaction from engine */
++extern "C"
++int thd_command(const THD* thd)
++{
++  return (int) thd->command;
++}
++
++extern "C"
++long long thd_start_time(const THD* thd)
++{
++  return (long long) thd->start_time;
++}
++
++extern "C"
++void thd_kill(ulong id)
++{
++  THD *tmp;
++  mysql_mutex_lock(&LOCK_thread_count);
++  I_List_iterator<THD> it(threads);
++  while ((tmp=it++))
++  {
++    if (tmp->command == COM_DAEMON)
++      continue;
++    if (tmp->thread_id == id)
++    {
++      mysql_mutex_lock(&tmp->LOCK_thd_data);
++      break;
++    }
++  }
++  mysql_mutex_unlock(&LOCK_thread_count);
++  if (tmp)
++  {
++    tmp->awake(THD::KILL_CONNECTION);
++    mysql_mutex_unlock(&tmp->LOCK_thd_data);
++  }
++}
+ /**
+   Implementation of Drop_table_error_handler::handle_condition().
+--- a/storage/innobase/handler/ha_innodb.cc
++++ b/storage/innobase/handler/ha_innodb.cc
+@@ -2860,6 +2860,10 @@
+       innobase_commit_concurrency_init_default();
++#ifndef EXTENDED_FOR_KILLIDLE
++      srv_kill_idle_transaction = 0;
++#endif
++
+ #ifdef HAVE_PSI_INTERFACE
+       /* Register keys with MySQL performance schema */
+       if (PSI_server) {
+@@ -11686,6 +11690,57 @@
+       return(false);
+ }
++/***********************************************************************
++functions for kill session of idle transaction */
++extern "C"
++ibool
++innobase_thd_is_idle(
++/*=================*/
++      const void*     thd)    /*!< in: thread handle (THD*) */
++{
++#ifdef EXTENDED_FOR_KILLIDLE
++      return(thd_command((const THD*) thd) == COM_SLEEP);
++#else
++      return(FALSE);
++#endif
++}
++
++extern "C"
++ib_int64_t
++innobase_thd_get_start_time(
++/*========================*/
++      const void*     thd)    /*!< in: thread handle (THD*) */
++{
++#ifdef EXTENDED_FOR_KILLIDLE
++      return((ib_int64_t)thd_start_time((const THD*) thd));
++#else
++      return(0); /*dummy value*/
++#endif
++}
++
++extern "C"
++void
++innobase_thd_kill(
++/*==============*/
++      ulong   thd_id)
++{
++#ifdef EXTENDED_FOR_KILLIDLE
++      thd_kill(thd_id);
++#else
++      return;
++#endif
++}
++
++extern "C"
++ulong
++innobase_thd_get_thread_id(
++/*=======================*/
++      const void*     thd)
++{
++      return(thd_get_thread_id((const THD*) thd));
++}
++
++
+ static SHOW_VAR innodb_status_variables_export[]= {
+   {"Innodb",                   (char*) &show_innodb_vars, SHOW_FUNC},
+   {NullS, NullS, SHOW_LONG}
+@@ -11977,6 +12032,15 @@
+   "Number of times a thread is allowed to enter InnoDB within the same SQL query after it has once got the ticket",
+   NULL, NULL, 500L, 1L, ~0L, 0);
++static MYSQL_SYSVAR_LONG(kill_idle_transaction, srv_kill_idle_transaction,
++  PLUGIN_VAR_RQCMDARG,
++#ifdef EXTENDED_FOR_KILLIDLE
++  "If non-zero value, the idle session with transaction which is idle over the value in seconds is killed by InnoDB.",
++#else
++  "No effect for this build.",
++#endif
++  NULL, NULL, 0, 0, LONG_MAX, 0);
++
+ static MYSQL_SYSVAR_LONG(file_io_threads, innobase_file_io_threads,
+   PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY | PLUGIN_VAR_NOSYSVAR,
+   "Number of file I/O threads in InnoDB.",
+@@ -12279,6 +12343,7 @@
+   MYSQL_SYSVAR(fast_checksum),
+   MYSQL_SYSVAR(commit_concurrency),
+   MYSQL_SYSVAR(concurrency_tickets),
++  MYSQL_SYSVAR(kill_idle_transaction),
+   MYSQL_SYSVAR(data_file_path),
+   MYSQL_SYSVAR(doublewrite_file),
+   MYSQL_SYSVAR(data_home_dir),
+--- a/storage/innobase/include/srv0srv.h
++++ b/storage/innobase/include/srv0srv.h
+@@ -296,6 +296,7 @@
+ extern ulint  srv_activity_count;
+ extern ulint  srv_fatal_semaphore_wait_threshold;
+ extern ulint  srv_dml_needed_delay;
++extern lint   srv_kill_idle_transaction;
+ extern mutex_t*       kernel_mutex_temp;/* mutex protecting the server, trx structs,
+                               query threads, and lock table: we allocate
+--- a/storage/innobase/include/trx0trx.h
++++ b/storage/innobase/include/trx0trx.h
+@@ -594,6 +594,8 @@
+                                       replication has processed */
+       const char*     mysql_relay_log_file_name;
+       ib_int64_t      mysql_relay_log_pos;
++      time_t          idle_start;
++      ib_int64_t      last_stmt_start;
+       /*------------------------------*/
+       ulint           n_mysql_tables_in_use; /* number of Innobase tables
+                                       used in the processing of the current
+--- a/storage/innobase/srv/srv0srv.c
++++ b/storage/innobase/srv/srv0srv.c
+@@ -87,6 +87,12 @@
+ #include "mysql/plugin.h"
+ #include "mysql/service_thd_wait.h"
++/* prototypes of new functions added to ha_innodb.cc for kill_idle_transaction */
++ibool         innobase_thd_is_idle(const void* thd);
++ib_int64_t    innobase_thd_get_start_time(const void* thd);
++void          innobase_thd_kill(ulong thd_id);
++ulong         innobase_thd_get_thread_id(const void* thd);
++
+ /* prototypes for new functions added to ha_innodb.cc */
+ ibool innobase_get_slow_log();
+@@ -97,6 +103,9 @@
+ /* The following is the maximum allowed duration of a lock wait. */
+ UNIV_INTERN ulint     srv_fatal_semaphore_wait_threshold = 600;
++/**/
++UNIV_INTERN lint      srv_kill_idle_transaction = 0;
++
+ /* How much data manipulation language (DML) statements need to be delayed,
+ in microseconds, in order to reduce the lagging of the purge thread. */
+ UNIV_INTERN ulint     srv_dml_needed_delay = 0;
+@@ -2834,6 +2843,36 @@
+               old_sema = sema;
+       }
++      if (srv_kill_idle_transaction && trx_sys) {
++              trx_t*  trx;
++              time_t  now;
++rescan_idle:
++              now = time(NULL);
++              mutex_enter(&kernel_mutex);
++              trx = UT_LIST_GET_FIRST(trx_sys->mysql_trx_list);
++              while (trx) {
++                      if (trx->conc_state == TRX_ACTIVE
++                          && trx->mysql_thd
++                          && innobase_thd_is_idle(trx->mysql_thd)) {
++                              ib_int64_t      start_time = innobase_thd_get_start_time(trx->mysql_thd);
++                              ulong           thd_id = innobase_thd_get_thread_id(trx->mysql_thd);
++
++                              if (trx->last_stmt_start != start_time) {
++                                      trx->idle_start = now;
++                                      trx->last_stmt_start = start_time;
++                              } else if (difftime(now, trx->idle_start)
++                                         > srv_kill_idle_transaction) {
++                                      /* kill the session */
++                                      mutex_exit(&kernel_mutex);
++                                      innobase_thd_kill(thd_id);
++                                      goto rescan_idle;
++                              }
++                      }
++                      trx = UT_LIST_GET_NEXT(mysql_trx_list, trx);
++              }
++              mutex_exit(&kernel_mutex);
++      }
++
+       /* Flush stderr so that a database user gets the output
+       to possible MySQL error file */
+--- a/storage/innobase/trx/trx0trx.c
++++ b/storage/innobase/trx/trx0trx.c
+@@ -143,6 +143,9 @@
+       trx->mysql_relay_log_file_name = "";
+       trx->mysql_relay_log_pos = 0;
++      trx->idle_start = 0;
++      trx->last_stmt_start = 0;
++
+       mutex_create(trx_undo_mutex_key, &trx->undo_mutex, SYNC_TRX_UNDO);
+       trx->rseg = NULL;
+--- /dev/null
++++ b/mysql-test/r/percona_innodb_kill_idle_trx.result
+@@ -0,0 +1,41 @@
++DROP TABLE IF EXISTS t1;
++SET autocommit=0;
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  0
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  0
++SET GLOBAL innodb_kill_idle_transaction=1;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  1
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  1
++BEGIN;
++INSERT INTO t1 VALUES (1),(2),(3);
++COMMIT;
++SELECT * FROM t1;
++a
++1
++2
++3
++BEGIN;
++INSERT INTO t1 VALUES (4),(5),(6);
++SELECT * FROM t1;
++ERROR HY000: MySQL server has gone away
++SELECT * FROM t1;
++a
++1
++2
++3
++DROP TABLE t1;
++SET GLOBAL innodb_kill_idle_transaction=0;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  0
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  0
+--- /dev/null
++++ b/mysql-test/r/percona_innodb_kill_idle_trx_locks.result
+@@ -0,0 +1,45 @@
++DROP TABLE IF EXISTS t1;
++SET autocommit=0;
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  0
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  0
++SET GLOBAL innodb_kill_idle_transaction=5;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  5
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  5
++BEGIN;
++INSERT INTO t1 VALUES (1),(2),(3);
++COMMIT;
++SELECT * FROM t1;
++a
++1
++2
++3
++### Locking rows. Lock should be released when idle trx is killed.
++BEGIN;
++SELECT * FROM t1 FOR UPDATE;
++a
++1
++2
++3
++UPDATE t1 set a=4;
++SELECT * FROM t1;
++a
++4
++4
++4
++DROP TABLE t1;
++SET GLOBAL innodb_kill_idle_transaction=0;
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++Variable_name Value
++innodb_kill_idle_transaction  0
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
++VARIABLE_NAME VARIABLE_VALUE
++INNODB_KILL_IDLE_TRANSACTION  0
+--- /dev/null
++++ b/mysql-test/t/percona_innodb_kill_idle_trx.test
+@@ -0,0 +1,28 @@
++--source include/have_innodb.inc
++--disable_warnings
++DROP TABLE IF EXISTS t1; 
++--enable_warnings
++
++SET autocommit=0;
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++
++--source include/percona_innodb_kill_idle_trx_show.inc
++SET GLOBAL innodb_kill_idle_transaction=1;
++--source include/percona_innodb_kill_idle_trx_show.inc
++
++BEGIN;
++INSERT INTO t1 VALUES (1),(2),(3);
++COMMIT;
++SELECT * FROM t1;
++
++BEGIN;
++INSERT INTO t1 VALUES (4),(5),(6);
++sleep 3;
++
++--enable_reconnect
++--error 2006 --error CR_SERVER_GONE_ERROR
++SELECT * FROM t1;
++SELECT * FROM t1;
++DROP TABLE t1;
++SET GLOBAL innodb_kill_idle_transaction=0;
++--source include/percona_innodb_kill_idle_trx_show.inc
+--- /dev/null
++++ b/mysql-test/t/percona_innodb_kill_idle_trx_locks.test
+@@ -0,0 +1,31 @@
++--source include/have_innodb.inc
++--disable_warnings
++DROP TABLE IF EXISTS t1;
++--enable_warnings
++
++SET autocommit=0;
++CREATE TABLE t1 (a INT) ENGINE=InnoDB;
++
++--source include/percona_innodb_kill_idle_trx_show.inc
++SET GLOBAL innodb_kill_idle_transaction=5;
++--source include/percona_innodb_kill_idle_trx_show.inc
++
++connect (conn1,localhost,root,,);
++connection conn1;
++
++BEGIN;
++INSERT INTO t1 VALUES (1),(2),(3);
++COMMIT;
++SELECT * FROM t1;
++
++--echo ### Locking rows. Lock should be released when idle trx is killed.
++BEGIN;
++SELECT * FROM t1 FOR UPDATE;
++
++connection default;
++UPDATE t1 set a=4;
++
++SELECT * FROM t1;
++DROP TABLE t1;
++SET GLOBAL innodb_kill_idle_transaction=0;
++--source include/percona_innodb_kill_idle_trx_show.inc
+--- /dev/null
++++ b/mysql-test/include/percona_innodb_kill_idle_trx_show.inc
+@@ -0,0 +1,2 @@
++SHOW GLOBAL VARIABLES LIKE 'innodb_kill_idle_transaction';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='innodb_kill_idle_transaction';
index 060b243c7fb23b263b7e50378a19f5c79842ef1b..ed753f7649f272dd694641bdd72fd6d7066b1f56 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0lru.c
 +++ b/storage/innobase/buf/buf0lru.c
-@@ -2167,6 +2167,284 @@
+@@ -2183,6 +2183,289 @@
        memset(&buf_LRU_stat_cur, 0, sizeof buf_LRU_stat_cur);
  }
  
 +                      " InnoDB: cannot open %s\n", LRU_DUMP_FILE);
 +              goto end;
 +      }
++
++      ut_print_timestamp(stderr);
++      fprintf(stderr, " InnoDB: Restoring buffer pool pages from %s\n",
++              LRU_DUMP_FILE);
++
 +      if (size == 0 || size_high > 0 || size % 8) {
 +              fprintf(stderr, " InnoDB: broken LRU dump file\n");
 +              goto end;
 +
 +      ut_print_timestamp(stderr);
 +      fprintf(stderr,
-+              " InnoDB: reading pages based on the dumped LRU list was done."
++              " InnoDB: Completed reading buffer pool pages"
 +              " (requested: %lu, read: %lu)\n", req, reads);
 +      ret = TRUE;
 +end:
  Validates the LRU list for one buffer pool instance. */
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -58,7 +58,7 @@
+@@ -60,7 +60,7 @@
  which case it is never read into the pool, or if the tablespace does
  not exist or is being dropped 
  @return 1 if read request is issued. 0 if it is not */
  Waits for an aio operation to complete. This function is used to write the
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -11809,6 +11809,12 @@
+@@ -196,6 +196,8 @@
+ static char*  innodb_version_str = (char*) INNODB_VERSION_STR;
++static my_bool        innobase_blocking_lru_restore           = FALSE;
++
+ /** Possible values for system variable "innodb_stats_method". The values
+ are defined the same as its corresponding MyISAM system variable
+ "myisam_stats_method"(see "myisam_stats_method_names"), for better usability */
+@@ -2652,6 +2654,8 @@
+       srv_use_doublewrite_buf = (ibool) innobase_use_doublewrite;
+       srv_use_checksums = (ibool) innobase_use_checksums;
++      srv_blocking_lru_restore = (ibool) innobase_blocking_lru_restore;
++
+ #ifdef HAVE_LARGE_PAGES
+         if ((os_use_large_pages = (ibool) my_use_large_pages))
+               os_large_page_size = (ulint) opt_large_page_size;
+@@ -11916,6 +11920,19 @@
    "Limit the allocated memory for dictionary cache. (0: unlimited)",
    NULL, NULL, 0, 0, LONG_MAX, 0);
  
 +  "Time in seconds between automatic buffer pool dumps. "
 +  "0 (the default) disables automatic dumps.",
 +  NULL, NULL, 0, 0, UINT_MAX32, 0);
++
++static MYSQL_SYSVAR_BOOL(blocking_buffer_pool_restore,
++  innobase_blocking_lru_restore,
++  PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
++  "Block XtraDB startup process until buffer pool is full restored from a "
++  "dump file (if present). Disabled by default.",
++  NULL, NULL, FALSE);
 +
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(additional_mem_pool_size),
    MYSQL_SYSVAR(autoextend_increment),
-@@ -11891,6 +11897,7 @@
- #endif /* UNIV_DEBUG || UNIV_IBUF_DEBUG */
+@@ -12000,6 +12017,8 @@
+   MYSQL_SYSVAR(random_read_ahead),
    MYSQL_SYSVAR(read_ahead_threshold),
    MYSQL_SYSVAR(io_capacity),
 +  MYSQL_SYSVAR(buffer_pool_restore_at_startup),
++  MYSQL_SYSVAR(blocking_buffer_pool_restore),
    MYSQL_SYSVAR(purge_threads),
    MYSQL_SYSVAR(purge_batch_size),
    MYSQL_SYSVAR(rollback_segments),
  }
  
  #define OK(expr)              \
-@@ -4270,6 +4271,36 @@
+@@ -4298,6 +4299,36 @@
                        "Hello!");
                goto end_func;
        }
 +buf_LRU_file_restore(void);
 +/*======================*/
  
- #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
- /**********************************************************************//**
+ /******************************************************************//**
+ Remove one page from LRU list and put it to free list */
 --- a/storage/innobase/include/buf0rea.h
 +++ b/storage/innobase/include/buf0rea.h
 @@ -31,6 +31,37 @@
  handler for completed requests. The aio array of pending requests is divided
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -356,6 +356,9 @@
+@@ -361,6 +361,12 @@
  reading of a disk page */
  extern ulint srv_buf_pool_reads;
  
 +/** Time in seconds between automatic buffer pool dumps */
 +extern uint srv_auto_lru_dump;
++
++/** Whether startup should be blocked until buffer pool is fully restored */
++extern ibool srv_blocking_lru_restore;
 +
  /** Status variables to be passed to MySQL */
  typedef struct export_var_struct export_struc;
  
-@@ -661,6 +664,16 @@
+@@ -666,6 +672,16 @@
  /*=====================*/
        void*   arg);   /*!< in: a dummy parameter required by
                        os_thread_create */
  @return FALSE if not all information printed
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -330,6 +330,9 @@
+@@ -332,6 +332,12 @@
  reading of a disk page */
  UNIV_INTERN ulint srv_buf_pool_reads = 0;
  
 +/** Time in seconds between automatic buffer pool dumps */
 +UNIV_INTERN uint srv_auto_lru_dump = 0;
++
++/** Whether startup should be blocked until buffer pool is fully restored */
++UNIV_INTERN ibool srv_blocking_lru_restore;
 +
  /* structure to pass status variables to MySQL */
  UNIV_INTERN export_struc export_vars;
  
-@@ -2706,6 +2709,56 @@
+@@ -2710,6 +2716,58 @@
        OS_THREAD_DUMMY_RETURN;
  }
  
 +              os_thread_pf(os_thread_get_curr_id()));
 +#endif
 +
-+      if (srv_auto_lru_dump)
++      /* If srv_blocking_lru_restore is TRUE, restore will be done
++      synchronously on startup. */
++      if (srv_auto_lru_dump && !srv_blocking_lru_restore)
 +              buf_LRU_file_restore();
 +
 +      last_dump_time = time(NULL);
  @return FALSE if all are are suspended or have exited. */
 --- a/storage/innobase/srv/srv0start.c
 +++ b/storage/innobase/srv/srv0start.c
-@@ -120,9 +120,9 @@
+@@ -87,6 +87,7 @@
+ # include "btr0pcur.h"
+ # include "os0sync.h" /* for INNODB_RW_LOCKS_USE_ATOMICS */
+ # include "zlib.h" /* for ZLIB_VERSION */
++# include "buf0lru.h" /* for buf_LRU_file_restore() */
+ /** Log sequence number immediately after startup */
+ UNIV_INTERN ib_uint64_t       srv_start_lsn;
+@@ -120,9 +121,9 @@
  static os_file_t      files[1000];
  
  /** io_handler_thread parameters for thread identification */
  
  /** We use this mutex to test the return value of pthread_mutex_trylock
     on successful locking. HP-UX does NOT return 0, though Linux et al do. */
-@@ -1821,6 +1821,10 @@
+@@ -1821,6 +1822,15 @@
        os_thread_create(&srv_monitor_thread, NULL,
                         thread_ids + 4 + SRV_MAX_N_IO_THREADS);
  
 +      /* Create the thread which automaticaly dumps/restore buffer pool */
 +      os_thread_create(&srv_LRU_dump_restore_thread, NULL,
 +                       thread_ids + 5 + SRV_MAX_N_IO_THREADS);
++
++      /* If srv_blocking_lru_restore is TRUE, load buffer pool contents
++      synchronously */
++      if (srv_auto_lru_dump && srv_blocking_lru_restore)
++              buf_LRU_file_restore();
 +
        srv_is_being_started = FALSE;
  
        err = dict_create_or_check_foreign_constraint_tables();
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/r/innodb_blocking_buffer_pool_restore_basic.result
+@@ -0,0 +1,3 @@
++SELECT @@global.innodb_blocking_buffer_pool_restore;
++@@global.innodb_blocking_buffer_pool_restore
++0
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/t/innodb_blocking_buffer_pool_restore_basic.test
+@@ -0,0 +1 @@
++SELECT @@global.innodb_blocking_buffer_pool_restore;
index b894c1c8ba35e6e32a9e809e0f94a82e51a5a4a7..029cd62e6c6140df797342c28f37360585f214e6 100644 (file)
@@ -18,7 +18,7 @@
                ut_a(buf_page_get_state(bpage) == BUF_BLOCK_ZIP_FREE);
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -881,9 +881,9 @@
+@@ -882,9 +882,9 @@
        block->page.in_zip_hash = FALSE;
        block->page.in_flush_list = FALSE;
        block->page.in_free_list = FALSE;
@@ -29,7 +29,7 @@
  #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG
        block->n_pointers = 0;
  #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
-@@ -1428,7 +1428,7 @@
+@@ -1429,7 +1429,7 @@
  
        memcpy(dpage, bpage, sizeof *dpage);
  
@@ -38,7 +38,7 @@
        ut_d(bpage->in_page_hash = FALSE);
  
        /* relocate buf_pool->LRU */
-@@ -3279,8 +3279,8 @@
+@@ -3284,8 +3284,8 @@
                bpage->in_zip_hash = FALSE;
                bpage->in_flush_list = FALSE;
                bpage->in_free_list = FALSE;
@@ -48,7 +48,7 @@
  
                ut_d(bpage->in_page_hash = TRUE);
  
-@@ -3445,7 +3445,7 @@
+@@ -3450,7 +3450,7 @@
        ibuf_merge_or_delete_for_page(NULL, space, offset, zip_size, TRUE);
  
        /* Flush pages from the end of the LRU list if necessary */
  
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -200,7 +200,7 @@
+@@ -367,7 +367,7 @@
        }
  
        /* Flush pages from the end of the LRU list if necessary */
  
        /* Increment number of I/O operations used for LRU policy. */
        buf_LRU_stat_inc_io();
-@@ -474,7 +474,7 @@
+@@ -641,7 +641,7 @@
        os_aio_simulated_wake_handler_threads();
  
        /* Flush pages from the end of the LRU list if necessary */
  
  #ifdef UNIV_DEBUG
        if (buf_debug_prints && (count > 0)) {
-@@ -562,7 +562,7 @@
+@@ -729,7 +729,7 @@
        os_aio_simulated_wake_handler_threads();
  
        /* Flush pages from the end of all the LRU lists if necessary */
  
  #ifdef UNIV_DEBUG
        if (buf_debug_prints) {
-@@ -656,7 +656,7 @@
+@@ -823,7 +823,7 @@
        os_aio_simulated_wake_handler_threads();
  
        /* Flush pages from the end of all the LRU lists if necessary */
        if (buf_debug_prints) {
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1426,11 +1426,11 @@
+@@ -1417,11 +1417,11 @@
  
        UT_LIST_NODE_T(buf_page_t) LRU;
                                        /*!< node of the LRU list */
index 40a6273a0aafc2e824f4d661095c3ecb9f50174b..fc89718ffd43d8107ddf4ea80af0140ad23494df 100644 (file)
@@ -55,7 +55,7 @@
  static my_bool        innobase_rollback_on_timeout            = FALSE;
  static my_bool        innobase_create_status_file             = FALSE;
  static my_bool        innobase_stats_on_metadata              = TRUE;
-@@ -2253,6 +2273,89 @@
+@@ -2282,6 +2302,89 @@
        }
  #endif /* DBUG_OFF */
  
        /* Check that values don't overflow on 32-bit systems. */
        if (sizeof(ulint) == 4) {
                if (innobase_buffer_pool_size > UINT_MAX32) {
-@@ -2551,6 +2654,76 @@
+@@ -2580,6 +2683,76 @@
                goto mem_free_and_error;
        }
  
        innobase_old_blocks_pct = buf_LRU_old_ratio_update(
                innobase_old_blocks_pct, TRUE);
  
-@@ -2665,6 +2838,25 @@
+@@ -2694,6 +2867,25 @@
        trx_t*  trx)    /*!< in: transaction handle */
  {
        if (trx_is_started(trx)) {
  
                trx_commit_for_mysql(trx);
        }
-@@ -11025,6 +11217,12 @@
+@@ -11122,6 +11314,12 @@
    "The common part for InnoDB table spaces.",
    NULL, NULL, NULL);
  
  static MYSQL_SYSVAR_BOOL(doublewrite, innobase_use_doublewrite,
    PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
    "Enable InnoDB doublewrite buffer (enabled by default). "
-@@ -11491,6 +11689,7 @@
+@@ -11599,6 +11797,7 @@
    MYSQL_SYSVAR(old_blocks_pct),
    MYSQL_SYSVAR(old_blocks_time),
    MYSQL_SYSVAR(open_files),
index 2eb782857e4996c0bf112ba88c71db6ed02d02a4..bab55719966c42352a003db62345d79189210144 100644 (file)
@@ -7,10 +7,10 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/btr/btr0btr.c
 +++ b/storage/innobase/btr/btr0btr.c
-@@ -691,6 +691,12 @@
-       root_page_no = dict_index_get_page(index);
+@@ -692,6 +692,12 @@
  
-       block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH, mtr);
+       block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH,
+                             index, mtr);
 +
 +      if (srv_pass_corrupt_table && !block) {
 +              return(0);
@@ -20,7 +20,7 @@
        ut_a((ibool)!!page_is_comp(buf_block_get_frame(block))
             == dict_table_is_comp(index->table));
  #ifdef UNIV_BTR_DEBUG
-@@ -977,6 +983,12 @@
+@@ -978,6 +984,12 @@
  
        root = btr_root_get(index, &mtr);
  
        if (flag == BTR_N_LEAF_PAGES) {
                seg_header = root + PAGE_HEADER + PAGE_BTR_SEG_LEAF;
  
-@@ -1433,6 +1445,13 @@
-       mtr_start(&mtr);
+@@ -1437,6 +1449,13 @@
  
-       root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr);
+       root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH,
+                           NULL, &mtr);
 +
 +      if (srv_pass_corrupt_table && !root) {
 +              mtr_commit(&mtr);
 +              return;
 +      }
 +      ut_a(root);
-+      
++
  #ifdef UNIV_BTR_DEBUG
        ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_LEAF
                                    + root, space));
-@@ -1455,6 +1474,12 @@
-       mtr_start(&mtr);
+@@ -1460,6 +1479,12 @@
  
-       root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH, &mtr);
+       root = btr_page_get(space, zip_size, root_page_no, RW_X_LATCH,
+                           NULL, &mtr);
 +
 +      if (srv_pass_corrupt_table && !root) {
 +              mtr_commit(&mtr);
@@ -60,9 +60,9 @@
  #ifdef UNIV_BTR_DEBUG
        ut_a(btr_root_fseg_validate(FIL_PAGE_DATA + PAGE_BTR_SEG_TOP
                                    + root, space));
-@@ -1488,6 +1513,11 @@
-       block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH, mtr);
+@@ -1493,6 +1518,11 @@
+       block = btr_block_get(space, zip_size, root_page_no, RW_X_LATCH,
+                             NULL, mtr);
  
 +      if (srv_pass_corrupt_table && !block) {
 +              return;
        header = buf_block_get_frame(block) + PAGE_HEADER + PAGE_BTR_SEG_TOP;
 --- a/storage/innobase/btr/btr0cur.c
 +++ b/storage/innobase/btr/btr0cur.c
-@@ -250,6 +250,11 @@
-       case BTR_MODIFY_LEAF:
+@@ -251,6 +251,11 @@
                mode = latch_mode == BTR_SEARCH_LEAF ? RW_S_LATCH : RW_X_LATCH;
-               get_block = btr_block_get(space, zip_size, page_no, mode, mtr);
+               get_block = btr_block_get(
+                       space, zip_size, page_no, mode, cursor->index, mtr);
 +
 +              if (srv_pass_corrupt_table && !get_block) {
 +                      return;
  #ifdef UNIV_BTR_DEBUG
                ut_a(page_is_comp(get_block->frame) == page_is_comp(page));
  #endif /* UNIV_BTR_DEBUG */
-@@ -263,6 +268,11 @@
-                       get_block = btr_block_get(space, zip_size,
-                                                 left_page_no,
-                                                 RW_X_LATCH, mtr);
+@@ -264,6 +269,11 @@
+                       get_block = btr_block_get(
+                               space, zip_size, left_page_no,
+                               RW_X_LATCH, cursor->index, mtr);
 +
 +                      if (srv_pass_corrupt_table && !get_block) {
 +                              return;
  #ifdef UNIV_BTR_DEBUG
                        ut_a(page_is_comp(get_block->frame)
                             == page_is_comp(page));
-@@ -274,6 +284,11 @@
-               get_block = btr_block_get(space, zip_size, page_no,
-                                         RW_X_LATCH, mtr);
+@@ -276,6 +286,11 @@
+               get_block = btr_block_get(
+                       space, zip_size, page_no,
+                       RW_X_LATCH, cursor->index, mtr);
 +
 +              if (srv_pass_corrupt_table && !get_block) {
 +                      return;
  #ifdef UNIV_BTR_DEBUG
                ut_a(page_is_comp(get_block->frame) == page_is_comp(page));
  #endif /* UNIV_BTR_DEBUG */
-@@ -285,6 +300,11 @@
-                       get_block = btr_block_get(space, zip_size,
-                                                 right_page_no,
-                                                 RW_X_LATCH, mtr);
+@@ -287,6 +302,11 @@
+                       get_block = btr_block_get(
+                               space, zip_size, right_page_no,
+                               RW_X_LATCH, cursor->index, mtr);
 +
 +                      if (srv_pass_corrupt_table && !get_block) {
 +                              return;
  #ifdef UNIV_BTR_DEBUG
                        ut_a(page_is_comp(get_block->frame)
                             == page_is_comp(page));
-@@ -306,6 +326,11 @@
-                       get_block = btr_block_get(space, zip_size,
-                                                 left_page_no, mode, mtr);
+@@ -309,6 +329,11 @@
+                               space, zip_size,
+                               left_page_no, mode, cursor->index, mtr);
                        cursor->left_block = get_block;
 +
 +                      if (srv_pass_corrupt_table && !get_block) {
  #ifdef UNIV_BTR_DEBUG
                        ut_a(page_is_comp(get_block->frame)
                             == page_is_comp(page));
-@@ -316,6 +341,11 @@
-               }
+@@ -320,6 +345,11 @@
  
-               get_block = btr_block_get(space, zip_size, page_no, mode, mtr);
+               get_block = btr_block_get(
+                       space, zip_size, page_no, mode, cursor->index, mtr);
 +
 +              if (srv_pass_corrupt_table && !get_block) {
 +                      return;
  #ifdef UNIV_BTR_DEBUG
                ut_a(page_is_comp(get_block->frame) == page_is_comp(page));
  #endif /* UNIV_BTR_DEBUG */
-@@ -588,6 +618,19 @@
+@@ -592,6 +622,19 @@
                file, line, mtr);
  
        if (block == NULL) {
                /* This must be a search to perform an insert/delete
                mark/ delete; try using the insert/delete buffer */
  
-@@ -662,6 +705,16 @@
+@@ -666,6 +709,16 @@
        block->check_index_page_at_flush = TRUE;
        page = buf_block_get_frame(block);
  
        if (rw_latch != RW_NO_LATCH) {
  #ifdef UNIV_ZIP_DEBUG
                const page_zip_des_t*   page_zip
-@@ -866,6 +919,17 @@
+@@ -872,6 +925,17 @@
                                         RW_NO_LATCH, NULL, BUF_GET,
                                         file, line, mtr);
                page = buf_block_get_frame(block);
                ut_ad(index->id == btr_page_get_index_id(page));
  
                block->check_index_page_at_flush = TRUE;
-@@ -986,6 +1050,14 @@
+@@ -992,6 +1056,14 @@
                                         RW_NO_LATCH, NULL, BUF_GET,
                                         file, line, mtr);
                page = buf_block_get_frame(block);
                ut_ad(index->id == btr_page_get_index_id(page));
  
                if (height == ULINT_UNDEFINED) {
-@@ -1199,6 +1271,12 @@
+@@ -1205,6 +1277,12 @@
        *big_rec = NULL;
  
        block = btr_cur_get_block(cursor);
        page = buf_block_get_frame(block);
        index = cursor->index;
        zip_size = buf_block_get_zip_size(block);
-@@ -2988,6 +3066,11 @@
+@@ -2937,6 +3015,11 @@
  
        block = btr_cur_get_block(cursor);
  
        ut_ad(page_is_leaf(buf_block_get_frame(block)));
  
        rec = btr_cur_get_rec(cursor);
-@@ -3701,6 +3784,11 @@
+@@ -3650,6 +3733,11 @@
  
                page = btr_cur_get_page(&cursor);
  
        index = btr_cur_get_index(btr_pcur_get_btr_cur(cursor));
  
        page_cursor = btr_pcur_get_page_cur(cursor);
-@@ -419,6 +425,15 @@
-       next_block = btr_block_get(space, zip_size, next_page_no,
-                                  cursor->latch_mode, mtr);
+@@ -395,6 +401,15 @@
+                                  cursor->latch_mode,
+                                  btr_pcur_get_btr_cur(cursor)->index, mtr);
        next_page = buf_block_get_frame(next_block);
 +
 +      if (srv_pass_corrupt_table && !next_page) {
  
  /* prototypes for new functions added to ha_innodb.cc */
  trx_t* innobase_get_trx();
-@@ -1135,6 +1136,11 @@
+@@ -1136,6 +1137,11 @@
                        ready = buf_flush_ready_for_replace(&block->page);
                        mutex_exit(&block->mutex);
  
                        if (!ready) {
  
                                return(block);
-@@ -2006,6 +2012,13 @@
+@@ -2007,6 +2013,13 @@
                return(NULL);
        }
  
        block_mutex = buf_page_get_mutex_enter(bpage);
  
        rw_lock_s_unlock(&buf_pool->page_hash_latch);
-@@ -2583,6 +2596,13 @@
+@@ -2587,6 +2600,13 @@
                return(NULL);
        }
  
        switch (buf_block_get_state(block)) {
                buf_page_t*     bpage;
                ibool           success;
-@@ -3257,6 +3277,7 @@
+@@ -3261,6 +3281,7 @@
        bpage->newest_modification = 0;
        bpage->oldest_modification = 0;
        HASH_INVALIDATE(bpage, hash);
  #if defined UNIV_DEBUG_FILE_ACCESSES || defined UNIV_DEBUG
        bpage->file_page_was_freed = FALSE;
  #endif /* UNIV_DEBUG_FILE_ACCESSES || UNIV_DEBUG */
-@@ -3841,6 +3862,7 @@
+@@ -3899,6 +3920,7 @@
                                (ulong) bpage->offset);
                }
  
                /* From version 3.23.38 up we store the page checksum
                to the 4 first bytes of the page end lsn field */
  
-@@ -3882,6 +3904,23 @@
+@@ -3940,6 +3962,23 @@
                              REFMAN "forcing-innodb-recovery.html\n"
                              "InnoDB: about forcing recovery.\n", stderr);
  
 +                              bpage->is_corrupt = TRUE;
 +                      } else
                        if (srv_force_recovery < SRV_FORCE_IGNORE_CORRUPT) {
-                               fputs("InnoDB: Ending processing because of"
-                                     " a corrupt database page.\n",
-@@ -3889,6 +3928,7 @@
-                               exit(1);
+                               /* If page space id is larger than TRX_SYS_SPACE
+                               (0), we will attempt to mark the corresponding
+@@ -3956,6 +3995,7 @@
+                               }
                        }
                }
 +              } /**/
  
                if (recv_recovery_is_on()) {
                        /* Pages must be uncompressed for crash recovery. */
-@@ -3898,8 +3938,11 @@
+@@ -3965,8 +4005,11 @@
  
                if (uncompressed && !recv_no_ibuf_operations) {
                        ibuf_merge_or_delete_for_page(
        }
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -193,7 +193,14 @@
+@@ -195,7 +195,14 @@
                              ((buf_block_t*) bpage)->frame, bpage, trx);
        }
        thd_wait_end(NULL);
                /* The i/o is already completed when we arrive from
 --- a/storage/innobase/dict/dict0dict.c
 +++ b/storage/innobase/dict/dict0dict.c
-@@ -54,6 +54,7 @@
- #include "row0merge.h"
+@@ -55,6 +55,7 @@
  #include "m_ctype.h" /* my_isspace() */
  #include "ha_prototypes.h" /* innobase_strcasecmp(), innobase_casedn_str()*/
+ #include "row0upd.h"
 +#include "srv0start.h" /* SRV_LOG_SPACE_FIRST_ID */
  
  #include <ctype.h>
                        goto next_loop;
  
                cached_foreign_tables = 0;
-@@ -4366,6 +4367,12 @@
+@@ -4367,6 +4368,12 @@
        heap = mem_heap_create(1000);
  
        while (index) {
                size = btr_get_size(index, BTR_TOTAL_SIZE);
  
                index->stat_index_size = size;
-@@ -4513,6 +4520,12 @@
+@@ -4514,6 +4521,12 @@
        heap = mem_heap_create(1000);
  
        while (index) {
  /*===========================================*/
  {
        dict_table_t*   sys_stats;
-@@ -4705,6 +4718,13 @@
+@@ -4706,6 +4719,13 @@
                     || (srv_force_recovery < SRV_FORCE_NO_LOG_REDO
                         && dict_index_is_clust(index)))) {
                        ulint   size;
                        size = btr_get_size(index, BTR_TOTAL_SIZE);
  
                        index->stat_index_size = size;
-@@ -5501,4 +5521,42 @@
-               rw_lock_free(&dict_table_stats_latches[i]);
-       }
+@@ -5685,4 +5705,42 @@
+       index->type |= DICT_CORRUPT;
  }
 +
 +/*************************************************************************
        if (descr != NULL) {
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -3979,6 +3979,12 @@
+@@ -4012,6 +4012,12 @@
                DBUG_RETURN(1);
        }
  
        /* Create buffers for packing the fields of a record. Why
        table->reclength did not work here? Obviously, because char
        fields when packed actually became 1 byte longer, when we also
-@@ -4006,6 +4012,19 @@
+@@ -4039,6 +4045,19 @@
        /* Get pointer to a table object in InnoDB dictionary cache */
        ib_table = dict_table_get(norm_name, TRUE);
        
 +              DBUG_RETURN(HA_ERR_CRASHED_ON_USAGE);
 +      }
 +
-+      if (share->ib_table) {
-+              ut_a(share->ib_table == ib_table);
-+      } else {
-+              share->ib_table = ib_table;
-+      }
++      share->ib_table = ib_table;
++
++
++
++
 +
        if (NULL == ib_table) {
                if (is_part && retries < 10) {
                        ++retries;
-@@ -5174,6 +5193,10 @@
+@@ -5188,6 +5207,10 @@
  
        ha_statistic_increment(&SSV::ha_write_count);
  
        if (table->timestamp_field_type & TIMESTAMP_AUTO_SET_ON_INSERT)
                table->timestamp_field->set_time();
  
-@@ -5391,6 +5414,10 @@
+@@ -5405,6 +5428,10 @@
  func_exit:
        innobase_active_small();
  
        DBUG_RETURN(error_result);
  }
  
-@@ -5567,6 +5594,10 @@
+@@ -5581,6 +5608,10 @@
  
        ha_statistic_increment(&SSV::ha_update_count);
  
        if (table->timestamp_field_type & TIMESTAMP_AUTO_SET_ON_UPDATE)
                table->timestamp_field->set_time();
  
-@@ -5656,6 +5687,10 @@
+@@ -5670,6 +5701,10 @@
  
        innobase_active_small();
  
        DBUG_RETURN(error);
  }
  
-@@ -5677,6 +5712,10 @@
+@@ -5691,6 +5726,10 @@
  
        ha_statistic_increment(&SSV::ha_delete_count);
  
        if (!prebuilt->upd_node) {
                row_get_prebuilt_update_vector(prebuilt);
        }
-@@ -5703,6 +5742,10 @@
+@@ -5717,6 +5756,10 @@
  
        innobase_active_small();
  
        DBUG_RETURN(error);
  }
  
-@@ -5942,6 +5985,10 @@
+@@ -5956,6 +5999,10 @@
  
        ha_statistic_increment(&SSV::ha_read_key_count);
  
 +
        index = prebuilt->index;
  
-       if (UNIV_UNLIKELY(index == NULL)) {
-@@ -6007,6 +6054,10 @@
+       if (UNIV_UNLIKELY(index == NULL) || dict_index_is_corrupted(index)) {
+@@ -6023,6 +6070,10 @@
                ret = DB_UNSUPPORTED;
        }
  
        switch (ret) {
        case DB_SUCCESS:
                error = 0;
-@@ -6122,6 +6173,10 @@
+@@ -6138,6 +6189,10 @@
  {
        DBUG_ENTER("change_active_index");
  
        ut_ad(user_thd == ha_thd());
        ut_a(prebuilt->trx == thd_to_trx(user_thd));
  
-@@ -6212,6 +6267,10 @@
+@@ -6251,6 +6306,10 @@
  
        DBUG_ENTER("general_fetch");
  
        ut_a(prebuilt->trx == thd_to_trx(user_thd));
  
        innodb_srv_conc_enter_innodb(prebuilt->trx);
-@@ -6221,6 +6280,10 @@
+@@ -6260,6 +6319,10 @@
  
        innodb_srv_conc_exit_innodb(prebuilt->trx);
  
        switch (ret) {
        case DB_SUCCESS:
                error = 0;
-@@ -7487,10 +7550,18 @@
+@@ -7526,10 +7589,18 @@
  
        update_thd(ha_thd());
  
        error = convert_error_code_to_mysql(error, prebuilt->table->flags,
                                            NULL);
  
-@@ -7991,6 +8062,16 @@
+@@ -8034,6 +8105,16 @@
        return(ranges + (double) rows / (double) total_rows * time_for_scan);
  }
  
  /*********************************************************************//**
  Calculates the key number used inside MySQL for an Innobase index. We will
  first check the "index translation table" for a match of the index to get
-@@ -8168,7 +8249,7 @@
+@@ -8211,7 +8292,7 @@
        ib_table = prebuilt->table;
  
        if (flag & HA_STATUS_TIME) {
                        /* In sql_show we call with this flag: update
                        then statistics so that they are up-to-date */
  
-@@ -8461,10 +8542,18 @@
+@@ -8511,10 +8592,18 @@
        THD*            thd,            /*!< in: connection thread handle */
        HA_CHECK_OPT*   check_opt)      /*!< in: currently ignored */
  {
        return(0);
  }
  
-@@ -8646,6 +8735,10 @@
+@@ -8747,6 +8836,10 @@
                my_error(ER_QUERY_INTERRUPTED, MYF(0));
        }
  
        DBUG_RETURN(is_ok ? HA_ADMIN_OK : HA_ADMIN_CORRUPT);
  }
  
-@@ -9416,6 +9509,10 @@
+@@ -9517,6 +9610,10 @@
  
        update_thd(thd);
  
        if (prebuilt->table->ibd_file_missing && !thd_tablespace_op(thd)) {
                ut_print_timestamp(stderr);
                fprintf(stderr,
-@@ -11823,6 +11920,26 @@
-   "0 (the default) disables automatic dumps.",
-   NULL, NULL, 0, 0, UINT_MAX32, 0);
+@@ -11941,6 +12038,26 @@
+   "dump file (if present). Disabled by default.",
+   NULL, NULL, FALSE);
  
 +const char *corrupt_table_action_names[]=
 +{
  static struct st_mysql_sys_var* innobase_system_variables[]= {
    MYSQL_SYSVAR(additional_mem_pool_size),
    MYSQL_SYSVAR(autoextend_increment),
-@@ -11910,6 +12027,7 @@
+@@ -12031,6 +12148,7 @@
    MYSQL_SYSVAR(purge_threads),
    MYSQL_SYSVAR(purge_batch_size),
    MYSQL_SYSVAR(rollback_segments),
  #define BTR_MAX_NODE_LEVEL    50      /*!< Maximum B-tree page level
                                        (not really a hard limit).
                                        Used in debug assertions
-@@ -55,7 +55,9 @@
+@@ -59,7 +59,9 @@
        block = buf_page_get_gen(space, zip_size, page_no, mode,
                                 NULL, BUF_GET, file, line, mtr);
  
 +
 +      if (block && mode != RW_NO_LATCH) {
  
-               buf_block_dbg_add_level(block, SYNC_TREE_NODE);
-       }
+               buf_block_dbg_add_level(
+                       block, index != NULL && dict_index_is_ibuf(index)
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -1025,7 +1025,7 @@
+@@ -1016,7 +1016,7 @@
        const buf_block_t*      block)  /*!< in: pointer to the control block */
        __attribute__((pure));
  #else /* UNIV_DEBUG */
  #endif /* UNIV_DEBUG */
  /*********************************************************************//**
  Gets the space id of a block.
-@@ -1472,6 +1472,7 @@
+@@ -1463,6 +1463,7 @@
                                        0 if the block was never accessed
                                        in the buffer pool */
        /* @} */
  /*********************************************************************//**
  Gets the current size of buffer buf_pool in bytes.
  @return size in bytes */
-@@ -619,6 +619,12 @@
+@@ -637,6 +637,12 @@
  /*================*/
        const buf_block_t*      block)  /*!< in: pointer to the control block */
  {
        switch (buf_block_get_state(block)) {
 --- a/storage/innobase/include/dict0dict.h
 +++ b/storage/innobase/include/dict0dict.h
-@@ -1258,6 +1258,15 @@
- dict_close(void);
/*============*/
+@@ -1326,6 +1326,15 @@
+ /*========================*/
      ulint           space_id);      /*!< in: space ID */
  
 +/*************************************************************************
 +set is_corrupt flag by space_id*/
  #endif
 --- a/storage/innobase/include/dict0mem.h
 +++ b/storage/innobase/include/dict0mem.h
-@@ -666,6 +666,7 @@
+@@ -670,6 +670,7 @@
                                the AUTOINC lock on this table. */
                                /* @} */
        /*----------------------*/
        buf_block_dbg_add_level(block, SYNC_NO_ORDER_CHECK);
 --- a/storage/innobase/include/page0page.h
 +++ b/storage/innobase/include/page0page.h
-@@ -527,7 +527,7 @@
+@@ -497,7 +497,7 @@
  page_is_leaf(
  /*=========*/
        const page_t*   page)   /*!< in: page */
  Decompress a page.  This function should tolerate errors on the compressed
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -240,6 +240,7 @@
+@@ -245,6 +245,7 @@
  extern ulint  srv_adaptive_flushing_method;
  
  extern ulint  srv_expand_import;
        ut_ad(page_simple_validate_new((page_t*) page));
 --- a/storage/innobase/row/row0ins.c
 +++ b/storage/innobase/row/row0ins.c
-@@ -1335,6 +1335,12 @@
+@@ -1338,6 +1338,12 @@
                const rec_t*            rec = btr_pcur_get_rec(&pcur);
                const buf_block_t*      block = btr_pcur_get_block(&pcur);
  
  
 --- a/storage/innobase/row/row0sel.c
 +++ b/storage/innobase/row/row0sel.c
-@@ -3854,6 +3854,13 @@
+@@ -3912,6 +3912,13 @@
        /* PHASE 4: Look for matching records in a loop */
  
        rec = btr_pcur_get_rec(pcur);
        ut_ad(!!page_rec_is_comp(rec) == comp);
  #ifdef UNIV_SEARCH_DEBUG
        /*
-@@ -3931,7 +3938,13 @@
+@@ -3989,7 +3996,13 @@
        if (UNIV_UNLIKELY(next_offs >= UNIV_PAGE_SIZE - PAGE_DIR)) {
  
  wrong_offs:
                        ut_print_timestamp(stderr);
                        buf_page_print(page_align(rec), 0);
                        fprintf(stderr,
-@@ -3982,7 +3995,8 @@
+@@ -4040,7 +4053,8 @@
  
        offsets = rec_get_offsets(rec, index, offsets, ULINT_UNDEFINED, &heap);
  
                        fprintf(stderr,
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -430,6 +430,7 @@
+@@ -435,6 +435,7 @@
  UNIV_INTERN ulint     srv_adaptive_flushing_method = 0; /* 0: native  1: estimate  2: keep_average */
  
  UNIV_INTERN ulint     srv_expand_import = 0; /* 0:disable 1:enable */
  /*-------------------------------------------*/
 --- a/storage/innobase/srv/srv0start.c
 +++ b/storage/innobase/srv/srv0start.c
-@@ -2149,6 +2149,13 @@
+@@ -2155,6 +2155,13 @@
  
        os_fast_mutex_free(&srv_os_test_mutex);
  
index 0ee2be3cde1d3ecc624475a354da46c3dfc68606..9be9df15235b6cbee535c3bc9194a7e955aa060b 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -122,6 +122,46 @@
+@@ -124,6 +124,46 @@
        bpage = buf_page_init_for_read(err, mode, space, zip_size, unzip,
                                       tablespace_version, offset);
        if (bpage == NULL) {
@@ -54,7 +54,7 @@
  
                return(0);
        }
-@@ -610,6 +650,50 @@
+@@ -777,6 +817,50 @@
                /* It is a single table tablespace and the .ibd file is
                missing: do nothing */
  
  static my_bool        innobase_locks_unsafe_for_binlog        = FALSE;
  static my_bool        innobase_overwrite_relay_log_info       = FALSE;
  static my_bool        innobase_rollback_on_timeout            = FALSE;
-@@ -2581,6 +2582,8 @@
+@@ -2610,6 +2611,8 @@
  
        srv_force_recovery = (ulint) innobase_force_recovery;
  
        srv_use_doublewrite_buf = (ibool) innobase_use_doublewrite;
        srv_use_checksums = (ibool) innobase_use_checksums;
  
-@@ -11285,6 +11288,11 @@
+@@ -11382,6 +11385,11 @@
    "The common part for InnoDB table spaces.",
    NULL, NULL, NULL);
  
  static MYSQL_SYSVAR_BOOL(recovery_update_relay_log, innobase_overwrite_relay_log_info,
    PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
    "During InnoDB crash recovery on slave overwrite relay-log.info "
-@@ -11763,6 +11771,7 @@
+@@ -11870,6 +11878,7 @@
    MYSQL_SYSVAR(data_file_path),
    MYSQL_SYSVAR(data_home_dir),
    MYSQL_SYSVAR(doublewrite),
index 34ca8857e4b39cac45361272f922bf58d8937cef..c1f258164bbe9420fc31c718c778934814ee6124 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -3810,7 +3810,8 @@
+@@ -3868,7 +3868,8 @@
                read_space_id = mach_read_from_4(
                        frame + FIL_PAGE_ARCH_LOG_NO_OR_SPACE_ID);
  
@@ -50,7 +50,7 @@
        and in recovery we will find them in the doublewrite buffer
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -88,7 +88,9 @@
+@@ -90,7 +90,9 @@
        wake_later = mode & OS_AIO_SIMULATED_WAKE_LATER;
        mode = mode & ~OS_AIO_SIMULATED_WAKE_LATER;
  
@@ -71,7 +71,7 @@
  
  
  /** Following are six InnoDB system tables */
-@@ -811,7 +812,7 @@
+@@ -816,7 +817,7 @@
  
                mtr_commit(&mtr);
  
@@ -80,7 +80,7 @@
                        /* The system tablespace always exists. */
                } else if (in_crash_recovery) {
                        /* Check that the tablespace (the .ibd file) really
-@@ -1682,7 +1683,7 @@
+@@ -1727,7 +1728,7 @@
        space = mach_read_from_4(field);
  
        /* Check if the tablespace exists and has the right name */
@@ -89,7 +89,7 @@
                flags = dict_sys_tables_get_flags(rec);
  
                if (UNIV_UNLIKELY(flags == ULINT_UNDEFINED)) {
-@@ -1835,7 +1836,7 @@
+@@ -1880,7 +1881,7 @@
                goto err_exit;
        }
  
  
  /* The highest file format being used in the database. The value can be
  set by user, however, it will be adjusted to the newer file format if
-@@ -2477,6 +2478,8 @@
+@@ -2508,6 +2509,8 @@
                goto error;
        }
  
        srv_use_sys_stats_table = (ibool) innobase_use_sys_stats_table;
  
        /* -------------- Log files ---------------------------*/
-@@ -11657,6 +11660,11 @@
+@@ -11763,6 +11766,11 @@
    "Path to individual files and their sizes.",
    NULL, NULL, NULL);
  
  static MYSQL_SYSVAR_LONG(autoinc_lock_mode, innobase_autoinc_lock_mode,
    PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
    "The AUTOINC lock modes supported by InnoDB:               "
-@@ -11824,6 +11832,7 @@
+@@ -11942,6 +11950,7 @@
    MYSQL_SYSVAR(commit_concurrency),
    MYSQL_SYSVAR(concurrency_tickets),
    MYSQL_SYSVAR(data_file_path),
  UNIV_INLINE
 --- a/storage/innobase/row/row0mysql.c
 +++ b/storage/innobase/row/row0mysql.c
-@@ -3425,7 +3425,7 @@
+@@ -3436,7 +3436,7 @@
                /* Do not drop possible .ibd tablespace if something went
                wrong: we do not want to delete valuable data of the user */
  
  /* if TRUE, then we auto-extend the last data file */
 --- a/storage/innobase/srv/srv0start.c
 +++ b/storage/innobase/srv/srv0start.c
-@@ -714,6 +714,7 @@
+@@ -715,6 +715,7 @@
  /*======================*/
        ibool*          create_new_db,  /*!< out: TRUE if new database should be
                                        created */
  #ifdef UNIV_LOG_ARCHIVE
        ulint*          min_arch_log_no,/*!< out: min of archived log
                                        numbers in data files */
-@@ -746,6 +747,7 @@
+@@ -747,6 +748,7 @@
        *sum_of_new_sizes = 0;
  
        *create_new_db = FALSE;
  
        srv_normalize_path_for_win(srv_data_home);
  
-@@ -983,6 +985,142 @@
+@@ -984,6 +986,142 @@
                                srv_data_file_is_raw_partition[i] != 0);
        }
  
        return(DB_SUCCESS);
  }
  
-@@ -996,6 +1134,7 @@
+@@ -997,6 +1135,7 @@
  /*====================================*/
  {
        ibool           create_new_db;
        ibool           log_file_created;
        ibool           log_created     = FALSE;
        ibool           log_opened      = FALSE;
-@@ -1461,6 +1600,7 @@
+@@ -1462,6 +1601,7 @@
        }
  
        err = open_or_create_data_files(&create_new_db,
  #ifdef UNIV_LOG_ARCHIVE
                                        &min_arch_log_no, &max_arch_log_no,
  #endif /* UNIV_LOG_ARCHIVE */
-@@ -1628,6 +1768,14 @@
+@@ -1629,6 +1769,14 @@
                after the double write buffer has been created. */
                trx_sys_create();
  
                dict_create();
  
                srv_startup_is_before_trx_rollback_phase = FALSE;
-@@ -1661,6 +1809,13 @@
+@@ -1662,6 +1810,13 @@
                recv_recovery_from_archive_finish();
  #endif /* UNIV_LOG_ARCHIVE */
        } else {
  
                /* Check if we support the max format that is stamped
                on the system tablespace. 
-@@ -1747,6 +1902,17 @@
+@@ -1748,6 +1903,17 @@
                we have finished the recovery process so that the
                image of TRX_SYS_PAGE_NO is not stale. */
                trx_sys_file_format_tag_init();
index 0bfda2bc848131554f200bb26fa845bbd731aa14..d544a043b95183d401b8e083e6ab3fa7ffa92544 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -9604,9 +9604,8 @@
+@@ -9701,9 +9701,8 @@
                        rw_lock_wait_time += mutex->lspent_time;
                }
  #else /* UNIV_DEBUG */
@@ -19,7 +19,7 @@
                buf2len= (uint) my_snprintf(buf2, sizeof(buf2), "os_waits=%lu",
                                     (ulong) mutex->count_os_wait);
  
-@@ -9621,10 +9620,8 @@
+@@ -9718,10 +9717,8 @@
  
        if (block_mutex) {
                buf1len = (uint) my_snprintf(buf1, sizeof buf1,
@@ -32,7 +32,7 @@
                buf2len = (uint) my_snprintf(buf2, sizeof buf2,
                                             "os_waits=%lu",
                                             (ulong) block_mutex_oswait_count);
-@@ -9653,9 +9650,8 @@
+@@ -9750,9 +9747,8 @@
                        continue;
                }
  
@@ -44,7 +44,7 @@
                buf2len = my_snprintf(buf2, sizeof buf2, "os_waits=%lu",
                                      (ulong) lock->count_os_wait);
  
-@@ -9669,10 +9665,8 @@
+@@ -9766,10 +9762,8 @@
  
        if (block_lock) {
                buf1len = (uint) my_snprintf(buf1, sizeof buf1,
  /******************************************************************//**
  NOTE! Please use the corresponding macro mutex_enter(), not directly
  this function!
-@@ -733,9 +733,9 @@
+@@ -729,9 +729,9 @@
        ulint   line;           /*!< Line where the mutex was locked */
        ulint   level;          /*!< Level in the global latching order */
  #endif /* UNIV_SYNC_DEBUG */
        os_thread_id_t thread_id; /*!< The thread id of the thread
                                which locked the mutex. */
        ulint           magic_n;        /*!< MUTEX_MAGIC_N */
-@@ -750,9 +750,9 @@
+@@ -746,9 +746,9 @@
        ulong           count_os_yield; /*!< count of os_wait */
        ulonglong       lspent_time;    /*!< mutex os_wait timer msec */
        ulonglong       lmax_spent_time;/*!< mutex os_wait timer msec */
                                        instrumentation hook */
 --- a/storage/innobase/include/sync0sync.ic
 +++ b/storage/innobase/include/sync0sync.ic
-@@ -321,13 +321,13 @@
+@@ -320,13 +320,13 @@
        mysql_pfs_key_t key,            /*!< in: Performance Schema key */
        mutex_t*        mutex,          /*!< in: pointer to memory */
  # ifdef UNIV_DEBUG
  {
        mutex->pfs_psi = (PSI_server && PFS_IS_INSTRUMENTED(key))
                                ? PSI_server->init_mutex(key, mutex)
-@@ -335,13 +335,13 @@
+@@ -334,13 +334,13 @@
  
        mutex_create_func(mutex,
  # ifdef UNIV_DEBUG
index 0be7859ed3b458e9fd3e2e44359a6bf76a60624d..2522447a54ca798226933973aa1f6708c4b31a0b 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/buf/buf0buf.c
 +++ b/storage/innobase/buf/buf0buf.c
-@@ -4365,6 +4365,7 @@
+@@ -4426,6 +4426,7 @@
        }
  
        total_info->pool_size += pool_info->pool_size;
@@ -15,7 +15,7 @@
        total_info->lru_len += pool_info->lru_len;
        total_info->old_lru_len += pool_info->old_lru_len;
        total_info->free_list_len += pool_info->free_list_len;
-@@ -4428,6 +4429,8 @@
+@@ -4491,6 +4492,8 @@
  
        pool_info->pool_size = buf_pool->curr_size;
  
@@ -24,7 +24,7 @@
        pool_info->lru_len = UT_LIST_GET_LEN(buf_pool->LRU);
  
        pool_info->old_lru_len = buf_pool->LRU_old_len;
-@@ -4544,14 +4547,16 @@
+@@ -4612,14 +4615,16 @@
        ut_ad(pool_info);
  
        fprintf(file,
    {"buffer_pool_pages_free",
    (char*) &export_vars.innodb_buffer_pool_pages_free,   SHOW_LONG},
  #ifdef UNIV_DEBUG
-@@ -11097,6 +11099,16 @@
+@@ -11199,6 +11201,16 @@
    "Force InnoDB to not use next-key locking, to use only row-level locking.",
    NULL, NULL, FALSE);
  
  #ifdef UNIV_LOG_ARCHIVE
  static MYSQL_SYSVAR_STR(log_arch_dir, innobase_log_arch_dir,
    PLUGIN_VAR_RQCMDARG | PLUGIN_VAR_READONLY,
-@@ -11284,7 +11296,7 @@
+@@ -11386,7 +11398,7 @@
  
  static MYSQL_SYSVAR_STR(version, innodb_version_str,
    PLUGIN_VAR_NOCMDOPT | PLUGIN_VAR_READONLY,
  
  static MYSQL_SYSVAR_BOOL(use_sys_malloc, srv_use_sys_malloc,
    PLUGIN_VAR_NOCMDARG | PLUGIN_VAR_READONLY,
-@@ -11378,6 +11390,8 @@
+@@ -11486,6 +11498,8 @@
    MYSQL_SYSVAR(thread_concurrency),
    MYSQL_SYSVAR(thread_sleep_delay),
    MYSQL_SYSVAR(autoinc_lock_mode),
  Create a consistent cursor view for mysql to be used in cursors. In this
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -142,6 +142,9 @@
- extern char   srv_adaptive_flushing;
+@@ -146,6 +146,9 @@
+ corrupted index and table */
+ extern my_bool        srv_load_corrupted;
  
 +extern ulint    srv_show_locks_held;
 +extern ulint    srv_show_verbose_locks;
  /* The sort order table of the MySQL latin1_swedish_ci character set
  collation */
  extern const byte*    srv_latin1_ordering;
-@@ -323,6 +326,8 @@
+@@ -328,6 +331,8 @@
  buffer pool to disk */
  extern ulint srv_buf_pool_flushed;
  
  /** Number of buffer pool reads that led to the
  reading of a disk page */
  extern ulint srv_buf_pool_reads;
-@@ -702,6 +707,7 @@
+@@ -707,6 +712,7 @@
        ulint innodb_buffer_pool_reads;         /*!< srv_buf_pool_reads */
        ulint innodb_buffer_pool_wait_free;     /*!< srv_buf_pool_wait_free */
        ulint innodb_buffer_pool_pages_flushed; /*!< srv_buf_pool_flushed */
 +      ulint innodb_buffer_pool_pages_LRU_flushed;     /*!< buf_lru_flush_page_count */
        ulint innodb_buffer_pool_write_requests;/*!< srv_buf_pool_write_requests */
+       ulint innodb_buffer_pool_read_ahead_rnd;/*!< srv_read_ahead_rnd */
        ulint innodb_buffer_pool_read_ahead;    /*!< srv_read_ahead */
-       ulint innodb_buffer_pool_read_ahead_evicted;/*!< srv_read_ahead evicted*/
 --- a/storage/innobase/lock/lock0lock.c
 +++ b/storage/innobase/lock/lock0lock.c
 @@ -4377,6 +4377,7 @@
  /** Maximum number of times allowed to conditionally acquire
  mutex before switching to blocking wait on the mutex */
  #define MAX_MUTEX_NOWAIT      20
-@@ -314,6 +318,7 @@
+@@ -316,6 +320,7 @@
  /* variable to count the number of pages that were written from buffer
  pool to the disk */
  UNIV_INTERN ulint srv_buf_pool_flushed = 0;
  
  /** Number of buffer pool reads that led to the
  reading of a disk page */
-@@ -1823,6 +1828,13 @@
+@@ -1825,6 +1830,13 @@
        ulint   n_reserved;
        ibool   ret;
  
        mutex_enter(&srv_innodb_monitor_mutex);
  
        current_time = time(NULL);
-@@ -1871,31 +1883,6 @@
+@@ -1873,31 +1885,6 @@
  
        mutex_exit(&dict_foreign_err_mutex);
  
        fputs("--------\n"
              "FILE I/O\n"
              "--------\n", file);
-@@ -1926,10 +1913,78 @@
+@@ -1928,10 +1915,78 @@
              "BUFFER POOL AND MEMORY\n"
              "----------------------\n", file);
        fprintf(file,
        fprintf(file, "Dictionary memory allocated " ULINTPF "\n",
                dict_sys->size);
  
-@@ -1945,6 +2000,16 @@
+@@ -1947,6 +2002,16 @@
        fprintf(file, "%lu read views open inside InnoDB\n",
                UT_LIST_GET_LEN(trx_sys->view_list));
  
        n_reserved = fil_space_get_n_reserved_extents(0);
        if (n_reserved > 0) {
                fprintf(file,
-@@ -1988,6 +2053,31 @@
+@@ -1990,6 +2055,31 @@
        srv_n_rows_deleted_old = srv_n_rows_deleted;
        srv_n_rows_read_old = srv_n_rows_read;
  
        fputs("----------------------------\n"
              "END OF INNODB MONITOR OUTPUT\n"
              "============================\n", file);
-@@ -2031,6 +2121,7 @@
+@@ -2033,6 +2123,7 @@
                = srv_buf_pool_write_requests;
        export_vars.innodb_buffer_pool_wait_free = srv_buf_pool_wait_free;
        export_vars.innodb_buffer_pool_pages_flushed = srv_buf_pool_flushed;
 +      export_vars.innodb_buffer_pool_pages_LRU_flushed = buf_lru_flush_page_count;
        export_vars.innodb_buffer_pool_reads = srv_buf_pool_reads;
-       export_vars.innodb_buffer_pool_read_ahead
-               = stat.n_ra_pages_read;
+       export_vars.innodb_buffer_pool_read_ahead_rnd
+               = stat.n_ra_pages_read_rnd;
 --- a/storage/innobase/sync/sync0arr.c
 +++ b/storage/innobase/sync/sync0arr.c
 @@ -478,7 +478,7 @@
index 2faeff7a0b77e18b7356c77f6ba3d51207a4b1e6..8e9cabe0972d8791c15dddf5b2c7d92ecea67095 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -639,6 +639,16 @@
+@@ -641,6 +641,16 @@
        trx_t*  trx);   /*!< in: transaction handle */
  
  static SHOW_VAR innodb_status_variables[]= {
@@ -24,7 +24,7 @@
    {"buffer_pool_pages_data",
    (char*) &export_vars.innodb_buffer_pool_pages_data,   SHOW_LONG},
    {"buffer_pool_pages_dirty",
-@@ -653,8 +663,14 @@
+@@ -655,8 +665,14 @@
    {"buffer_pool_pages_latched",
    (char*) &export_vars.innodb_buffer_pool_pages_latched,  SHOW_LONG},
  #endif /* UNIV_DEBUG */
@@ -38,8 +38,8 @@
 +  (char*) &export_vars.innodb_buffer_pool_pages_old,    SHOW_LONG},
    {"buffer_pool_pages_total",
    (char*) &export_vars.innodb_buffer_pool_pages_total,          SHOW_LONG},
-   {"buffer_pool_read_ahead",
-@@ -669,6 +685,12 @@
+   {"buffer_pool_read_ahead_rnd",
+@@ -673,6 +689,12 @@
    (char*) &export_vars.innodb_buffer_pool_wait_free,    SHOW_LONG},
    {"buffer_pool_write_requests",
    (char*) &export_vars.innodb_buffer_pool_write_requests, SHOW_LONG},
@@ -52,7 +52,7 @@
    {"data_fsyncs",
    (char*) &export_vars.innodb_data_fsyncs,              SHOW_LONG},
    {"data_pending_fsyncs",
-@@ -695,12 +717,66 @@
+@@ -699,12 +721,66 @@
    (char*) &export_vars.innodb_dict_tables,              SHOW_LONG},
    {"have_atomic_builtins",
    (char*) &export_vars.innodb_have_atomic_builtins,     SHOW_BOOL},
    {"os_log_fsyncs",
    (char*) &export_vars.innodb_os_log_fsyncs,            SHOW_LONG},
    {"os_log_pending_fsyncs",
-@@ -717,8 +793,14 @@
+@@ -721,8 +797,14 @@
    (char*) &export_vars.innodb_pages_read,               SHOW_LONG},
    {"pages_written",
    (char*) &export_vars.innodb_pages_written,            SHOW_LONG},
    {"row_lock_time",
    (char*) &export_vars.innodb_row_lock_time,            SHOW_LONGLONG},
    {"row_lock_time_avg",
-@@ -735,8 +817,20 @@
+@@ -739,8 +821,20 @@
    (char*) &export_vars.innodb_rows_read,                SHOW_LONG},
    {"rows_updated",
    (char*) &export_vars.innodb_rows_updated,             SHOW_LONG},
  /** The lock system */
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -731,6 +731,11 @@
+@@ -739,6 +739,11 @@
  
  /** Status variables to be passed to MySQL */
  struct export_var_struct{
        ulint innodb_data_pending_reads;        /*!< Pending reads */
        ulint innodb_data_pending_writes;       /*!< Pending writes */
        ulint innodb_data_pending_fsyncs;       /*!< Pending fsyncs */
-@@ -748,6 +753,9 @@
+@@ -756,6 +761,9 @@
  #ifdef UNIV_DEBUG
        ulint innodb_buffer_pool_pages_latched; /*!< Latched pages */
  #endif /* UNIV_DEBUG */
        ulint innodb_buffer_pool_read_requests; /*!< buf_pool->stat.n_page_gets */
        ulint innodb_buffer_pool_reads;         /*!< srv_buf_pool_reads */
        ulint innodb_buffer_pool_wait_free;     /*!< srv_buf_pool_wait_free */
-@@ -756,13 +764,43 @@
-       ulint innodb_buffer_pool_write_requests;/*!< srv_buf_pool_write_requests */
+@@ -765,13 +773,43 @@
+       ulint innodb_buffer_pool_read_ahead_rnd;/*!< srv_read_ahead_rnd */
        ulint innodb_buffer_pool_read_ahead;    /*!< srv_read_ahead */
        ulint innodb_buffer_pool_read_ahead_evicted;/*!< srv_read_ahead evicted*/
 +      ulint innodb_checkpoint_age;
        ulint innodb_os_log_written;            /*!< srv_os_log_written */
        ulint innodb_os_log_fsyncs;             /*!< fil_n_log_flushes */
        ulint innodb_os_log_pending_writes;     /*!< srv_os_log_pending_writes */
-@@ -771,6 +809,8 @@
+@@ -780,6 +818,8 @@
        ulint innodb_pages_created;             /*!< buf_pool->stat.n_pages_created */
        ulint innodb_pages_read;                /*!< buf_pool->stat.n_pages_read */
        ulint innodb_pages_written;             /*!< buf_pool->stat.n_pages_written */
        ulint innodb_row_lock_waits;            /*!< srv_n_lock_wait_count */
        ulint innodb_row_lock_current_waits;    /*!< srv_n_lock_wait_current_count */
        ib_int64_t innodb_row_lock_time;        /*!< srv_n_lock_wait_time
-@@ -780,11 +820,18 @@
+@@ -789,11 +829,18 @@
                                                / srv_n_lock_wait_count */
        ulint innodb_row_lock_time_max;         /*!< srv_n_lock_max_wait_time
                                                / 1000 */
  /** Thread slot in the thread table */
 --- a/storage/innobase/include/sync0sync.h
 +++ b/storage/innobase/include/sync0sync.h
-@@ -771,6 +771,10 @@
+@@ -767,6 +767,10 @@
  
  #define       SYNC_SPIN_ROUNDS        srv_n_spin_wait_rounds
  
  }
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -2253,12 +2253,49 @@
+@@ -2259,12 +2259,49 @@
        ulint           LRU_len;
        ulint           free_len;
        ulint           flush_list_len;
        export_vars.innodb_data_pending_reads
                = os_n_pending_reads;
        export_vars.innodb_data_pending_writes
-@@ -2295,6 +2332,92 @@
+@@ -2303,6 +2340,92 @@
  
        export_vars.innodb_buffer_pool_pages_misc
                = buf_pool_get_n_pages() - LRU_len - free_len;
index ce986ab3ba5319dee45aa67d5bee5533208149ee..6e793d763a221e784af352b1e86f66df4e5fc886 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/dict/dict0load.c
 +++ b/storage/innobase/dict/dict0load.c
-@@ -437,7 +437,7 @@
+@@ -442,7 +442,7 @@
  
  }
  
@@ -16,7 +16,7 @@
  /********************************************************************//**
  This function parses a SYS_FOREIGN record and populate a dict_foreign_t
  structure with the information from the record. For detail information
-@@ -513,9 +513,9 @@
+@@ -518,9 +518,9 @@
  
        return(NULL);
  }
@@ -28,7 +28,7 @@
  /********************************************************************//**
  This function parses a SYS_FOREIGN_COLS record and extract necessary
  information from the record and return to caller.
-@@ -579,7 +579,7 @@
+@@ -584,7 +584,7 @@
  
        return(NULL);
  }
@@ -39,7 +39,7 @@
  Determine the flags of a table described in SYS_TABLES.
 --- a/storage/innobase/handler/ha_innodb.cc
 +++ b/storage/innobase/handler/ha_innodb.cc
-@@ -11789,7 +11789,14 @@
+@@ -11899,7 +11899,14 @@
  i_s_innodb_cmp,
  i_s_innodb_cmp_reset,
  i_s_innodb_cmpmem,
@@ -69,7 +69,7 @@
  #include "dict0mem.h"
  #include "dict0types.h"
  #include "ha_prototypes.h" /* for innobase_convert_name() */
-@@ -1784,6 +1786,1675 @@
+@@ -1812,6 +1814,1675 @@
        DBUG_RETURN(0);
  }
  
index 4cb6509265de8d4d9c924785ff0d1e0ff78f6ebc..9fbd5eed31c95dcc729f5ce4945ecc6f70171d5e 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/storage/innobase/btr/btr0cur.c
 +++ b/storage/innobase/btr/btr0cur.c
-@@ -4142,7 +4142,8 @@
+@@ -4091,7 +4091,8 @@
  
        mtr_commit(mtr);
  
@@ -17,7 +17,7 @@
        mutex_enter(&block->mutex);
  
        /* Only free the block if it is still allocated to
-@@ -4153,16 +4154,21 @@
+@@ -4102,16 +4103,21 @@
            && buf_block_get_space(block) == space
            && buf_block_get_page_no(block) == page_no) {
  
@@ -45,7 +45,7 @@
  
 --- a/storage/innobase/btr/btr0sea.c
 +++ b/storage/innobase/btr/btr0sea.c
-@@ -1943,7 +1943,7 @@
+@@ -1944,7 +1944,7 @@
        rec_offs_init(offsets_);
  
        rw_lock_x_lock(&btr_search_latch);
@@ -54,7 +54,7 @@
  
        cell_count = hash_get_n_cells(btr_search_sys->hash_index);
  
-@@ -1951,11 +1951,11 @@
+@@ -1952,11 +1952,11 @@
                /* We release btr_search_latch every once in a while to
                give other queries a chance to run. */
                if ((i != 0) && ((i % chunk_size) == 0)) {
@@ -68,7 +68,7 @@
                }
  
                node = hash_get_nth_cell(btr_search_sys->hash_index, i)->node;
-@@ -2066,11 +2066,11 @@
+@@ -2067,11 +2067,11 @@
                /* We release btr_search_latch every once in a while to
                give other queries a chance to run. */
                if (i != 0) {
@@ -82,7 +82,7 @@
                }
  
                if (!ha_validate(btr_search_sys->hash_index, i, end_index)) {
-@@ -2078,7 +2078,7 @@
+@@ -2079,7 +2079,7 @@
                }
        }
  
  {
        buf_page_t*     bpage;
        const ulint     size    = BUF_BUDDY_LOW << i;
-@@ -335,13 +362,20 @@
+@@ -334,13 +361,20 @@
        ulint           space;
        ulint           page_no;
  
        /* We assume that all memory from buf_buddy_alloc()
        is used for compressed page frames. */
  
-@@ -375,6 +409,11 @@
+@@ -374,6 +408,11 @@
                added to buf_pool->page_hash yet.  Obviously,
                it cannot be relocated. */
  
                return(FALSE);
        }
  
-@@ -384,18 +423,27 @@
+@@ -383,18 +422,27 @@
                For the sake of simplicity, give up. */
                ut_ad(page_zip_get_size(&bpage->zip) < size);
  
 -      if (buf_page_can_relocate(bpage)) {
 +      if (mutex && buf_page_can_relocate(bpage)) {
                /* Relocate the compressed page. */
+               ullint  usec    = ut_time_us(NULL);
                ut_a(bpage->zip.data == src);
-               memcpy(dst, src, size);
 @@ -409,10 +457,22 @@
                        buddy_stat->relocated_usec
                                += ut_time_us(NULL) - usec;
  UNIV_INTERN mysql_pfs_key_t   flush_list_mutex_key;
  #endif /* UNIV_PFS_MUTEX */
  
-@@ -881,9 +886,13 @@
+@@ -882,9 +887,13 @@
        block->page.in_zip_hash = FALSE;
        block->page.in_flush_list = FALSE;
        block->page.in_free_list = FALSE;
  #if defined UNIV_AHI_DEBUG || defined UNIV_DEBUG
        block->n_pointers = 0;
  #endif /* UNIV_AHI_DEBUG || UNIV_DEBUG */
-@@ -981,9 +990,11 @@
+@@ -982,9 +991,11 @@
                memset(block->frame, '\0', UNIV_PAGE_SIZE);
  #endif
                /* Add the block to the free list */
                ut_ad(buf_pool_from_block(block) == buf_pool);
  
                block++;
-@@ -1038,7 +1049,8 @@
+@@ -1039,7 +1050,8 @@
        buf_chunk_t*    chunk = buf_pool->chunks;
  
        ut_ad(buf_pool);
        for (n = buf_pool->n_chunks; n--; chunk++) {
  
                buf_block_t* block = buf_chunk_contains_zip(chunk, data);
-@@ -1144,9 +1156,21 @@
+@@ -1145,9 +1157,21 @@
        ------------------------------- */
        mutex_create(buf_pool_mutex_key,
                     &buf_pool->mutex, SYNC_BUF_POOL);
        buf_pool_mutex_enter(buf_pool);
  
        if (buf_pool_size > 0) {
-@@ -1159,6 +1183,8 @@
+@@ -1160,6 +1184,8 @@
                        mem_free(chunk);
                        mem_free(buf_pool);
  
                        buf_pool_mutex_exit(buf_pool);
  
                        return(DB_ERROR);
-@@ -1189,6 +1215,8 @@
+@@ -1190,6 +1216,8 @@
  
        /* All fields are initialized by mem_zalloc(). */
  
        buf_pool_mutex_exit(buf_pool);
  
        return(DB_SUCCESS);
-@@ -1401,7 +1429,11 @@
+@@ -1402,7 +1430,11 @@
        ulint           fold;
        buf_pool_t*     buf_pool = buf_pool_from_bpage(bpage);
  
        ut_ad(mutex_own(buf_page_get_mutex(bpage)));
        ut_a(buf_page_get_io_fix(bpage) == BUF_IO_NONE);
        ut_a(bpage->buf_fix_count == 0);
-@@ -1512,21 +1544,32 @@
+@@ -1513,21 +1545,32 @@
        buf_page_t*     bpage;
        ulint           i;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
        for (i = 0; i < BUF_POOL_WATCH_SIZE; i++) {
                bpage = &buf_pool->watch[i];
  
-@@ -1550,10 +1593,12 @@
+@@ -1551,10 +1594,12 @@
                        bpage->space = space;
                        bpage->offset = offset;
                        bpage->buf_fix_count = 1;
                        return(NULL);
                case BUF_BLOCK_ZIP_PAGE:
                        ut_ad(bpage->in_page_hash);
-@@ -1571,6 +1616,8 @@
+@@ -1572,6 +1617,8 @@
        ut_error;
  
        /* Fix compiler warning */
        return(NULL);
  }
  
-@@ -1588,7 +1635,11 @@
+@@ -1589,7 +1636,11 @@
                                        space, offset) */
        buf_page_t*     watch)          /*!< in/out: sentinel for watch */
  {
  
        HASH_DELETE(buf_page_t, hash, buf_pool->page_hash, fold, watch);
        ut_d(watch->in_page_hash = FALSE);
-@@ -1610,28 +1661,31 @@
+@@ -1611,28 +1662,31 @@
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
        ulint           fold = buf_page_address_fold(space, offset);
  
  }
  
  /****************************************************************//**
-@@ -1651,14 +1705,16 @@
+@@ -1652,14 +1706,16 @@
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
        ulint           fold    = buf_page_address_fold(space, offset);
  
  
        return(ret);
  }
-@@ -1675,13 +1731,15 @@
+@@ -1676,13 +1732,15 @@
  {
        buf_pool_t*     buf_pool = buf_pool_from_bpage(bpage);
  
  }
  
  /********************************************************************//**
-@@ -1705,14 +1763,20 @@
+@@ -1706,14 +1764,20 @@
        ut_a(buf_page_in_file(bpage));
  
        if (buf_page_peek_if_too_old(bpage)) {
        }
  }
  
-@@ -1729,7 +1793,8 @@
+@@ -1730,7 +1794,8 @@
        buf_block_t*    block;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
  
        block = (buf_block_t*) buf_page_hash_get(buf_pool, space, offset);
  
-@@ -1738,7 +1803,8 @@
+@@ -1739,7 +1804,8 @@
                block->check_index_page_at_flush = FALSE;
        }
  
  }
  
  /********************************************************************//**
-@@ -1757,7 +1823,8 @@
+@@ -1758,7 +1824,8 @@
        ibool           is_hashed;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
  
        block = (buf_block_t*) buf_page_hash_get(buf_pool, space, offset);
  
-@@ -1768,7 +1835,8 @@
+@@ -1769,7 +1836,8 @@
                is_hashed = block->is_hashed;
        }
  
  
        return(is_hashed);
  }
-@@ -1790,7 +1858,8 @@
+@@ -1791,7 +1859,8 @@
        buf_page_t*     bpage;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
  
        bpage = buf_page_hash_get(buf_pool, space, offset);
  
-@@ -1801,7 +1870,8 @@
+@@ -1802,7 +1871,8 @@
                bpage->file_page_was_freed = TRUE;
        }
  
  
        return(bpage);
  }
-@@ -1822,7 +1892,8 @@
+@@ -1823,7 +1893,8 @@
        buf_page_t*     bpage;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
  
        bpage = buf_page_hash_get(buf_pool, space, offset);
  
-@@ -1831,7 +1902,8 @@
+@@ -1832,7 +1903,8 @@
                bpage->file_page_was_freed = FALSE;
        }
  
  
        return(bpage);
  }
-@@ -1863,8 +1935,9 @@
+@@ -1864,8 +1936,9 @@
        buf_pool->stat.n_page_gets++;
  
        for (;;) {
                bpage = buf_page_hash_get(buf_pool, space, offset);
                if (bpage) {
                        ut_ad(!buf_pool_watch_is_sentinel(buf_pool, bpage));
-@@ -1873,7 +1946,8 @@
+@@ -1874,7 +1947,8 @@
  
                /* Page not in buf_pool: needs to be read from file */
  
  
                buf_read_page(space, zip_size, offset);
  
-@@ -1885,10 +1959,15 @@
+@@ -1886,10 +1960,15 @@
        if (UNIV_UNLIKELY(!bpage->zip.data)) {
                /* There is no compressed page. */
  err_exit:
        ut_ad(!buf_pool_watch_is_sentinel(buf_pool, bpage));
  
        switch (buf_page_get_state(bpage)) {
-@@ -1897,24 +1976,43 @@
+@@ -1898,24 +1977,43 @@
        case BUF_BLOCK_MEMORY:
        case BUF_BLOCK_REMOVE_HASH:
        case BUF_BLOCK_ZIP_FREE:
                buf_block_buf_fix_inc((buf_block_t*) bpage,
                                      __FILE__, __LINE__);
                goto got_block;
-@@ -1927,7 +2025,7 @@
+@@ -1928,7 +2026,7 @@
        must_read = buf_page_get_io_fix(bpage) == BUF_IO_READ;
        access_time = buf_page_is_accessed(bpage);
  
  
        mutex_exit(block_mutex);
  
-@@ -2239,7 +2337,7 @@
+@@ -2240,7 +2338,7 @@
        const buf_block_t*      block)          /*!< in: pointer to block,
                                                not dereferenced */
  {
  
        if (UNIV_UNLIKELY((((ulint) block) % sizeof *block) != 0)) {
                /* The pointer should be aligned. */
-@@ -2275,6 +2373,7 @@
+@@ -2276,6 +2374,7 @@
        ulint           fix_type;
        ibool           must_read;
        ulint           retries = 0;
        buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
        ut_ad(mtr);
-@@ -2308,18 +2407,24 @@
+@@ -2309,18 +2408,24 @@
        fold = buf_page_address_fold(space, offset);
  loop:
        block = guess;
                        block = guess = NULL;
                } else {
                        ut_ad(!block->page.in_zip_hash);
-@@ -2328,12 +2433,19 @@
+@@ -2329,12 +2434,19 @@
        }
  
        if (block == NULL) {
                block = NULL;
        }
  
-@@ -2345,12 +2457,14 @@
+@@ -2346,12 +2458,14 @@
                                space, offset, fold);
  
                        if (UNIV_LIKELY_NULL(block)) {
  
                if (mode == BUF_GET_IF_IN_POOL
                    || mode == BUF_PEEK_IF_IN_POOL
-@@ -2400,7 +2514,8 @@
+@@ -2404,7 +2518,8 @@
                /* The page is being read to buffer pool,
                but we cannot wait around for the read to
                complete. */
  
                return(NULL);
        }
-@@ -2410,38 +2525,49 @@
+@@ -2414,38 +2529,49 @@
                ibool           success;
  
        case BUF_BLOCK_FILE_PAGE:
  
                {
                        buf_page_t*     hash_bpage;
-@@ -2454,35 +2580,47 @@
+@@ -2458,35 +2584,47 @@
                                while buf_pool->mutex was released.
                                Free the block that was allocated. */
  
                buf_block_init_low(block);
                block->lock_hash_val = lock_rec_hash(space, offset);
  
-@@ -2492,7 +2630,7 @@
+@@ -2496,7 +2634,7 @@
                if (buf_page_get_state(&block->page)
                    == BUF_BLOCK_ZIP_PAGE) {
  #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
                                       &block->page);
  #endif /* UNIV_DEBUG || UNIV_BUF_DEBUG */
                        ut_ad(!block->page.in_flush_list);
-@@ -2510,18 +2648,23 @@
+@@ -2514,18 +2652,23 @@
                /* Insert at the front of unzip_LRU list */
                buf_unzip_LRU_add_block(block, FALSE);
  
                buf_page_free_descriptor(bpage);
  
                /* Decompress the page and apply buffered operations
-@@ -2535,12 +2678,15 @@
+@@ -2539,12 +2682,15 @@
                }
  
                /* Unfix and unlatch the block. */
                rw_lock_x_unlock(&block->lock);
  
                break;
-@@ -2556,7 +2702,7 @@
+@@ -2560,7 +2706,7 @@
  
        ut_ad(buf_block_get_state(block) == BUF_BLOCK_FILE_PAGE);
  
  #if UNIV_WORD_SIZE == 4
        /* On 32-bit systems, there is no padding in buf_page_t.  On
        other systems, Valgrind could complain about uninitialized pad
-@@ -2569,8 +2715,8 @@
+@@ -2573,8 +2719,8 @@
                /* Try to evict the block from the buffer pool, to use the
                insert buffer (change buffer) as much as possible. */
  
                        if (mode == BUF_GET_IF_IN_POOL_OR_WATCH) {
                                /* Set the watch, as it would have
                                been set if the page were not in the
-@@ -2579,6 +2725,9 @@
+@@ -2583,6 +2729,9 @@
                                        space, offset, fold);
  
                                if (UNIV_LIKELY_NULL(block)) {
  
                                        /* The page entered the buffer
                                        pool for some reason. Try to
-@@ -2586,7 +2735,7 @@
+@@ -2590,7 +2739,7 @@
                                        goto got_block;
                                }
                        }
                        fprintf(stderr,
                                "innodb_change_buffering_debug evict %u %u\n",
                                (unsigned) space, (unsigned) offset);
-@@ -2608,13 +2757,14 @@
+@@ -2612,13 +2761,14 @@
        ut_a(mode == BUF_GET_POSSIBLY_FREED
             || !block->page.file_page_was_freed);
  #endif
  
        if (UNIV_LIKELY(mode != BUF_PEEK_IF_IN_POOL)) {
                buf_page_set_accessed_make_young(&block->page, access_time);
-@@ -2847,9 +2997,11 @@
+@@ -2851,9 +3001,11 @@
        buf_pool = buf_pool_from_block(block);
  
        if (mode == BUF_MAKE_YOUNG && buf_page_peek_if_too_old(&block->page)) {
        } else if (!buf_page_is_accessed(&block->page)) {
                /* Above, we do a dirty read on purpose, to avoid
                mutex contention.  The field buf_page_t::access_time
-@@ -2857,9 +3009,11 @@
+@@ -2861,9 +3013,11 @@
                field must be protected by mutex, however. */
                ulint   time_ms = ut_time_ms();
  
        }
  
        ut_ad(!ibuf_inside(mtr) || mode == BUF_KEEP_OLD);
-@@ -2926,18 +3080,21 @@
+@@ -2930,18 +3084,21 @@
        ut_ad(mtr);
        ut_ad(mtr->state == MTR_ACTIVE);
  
  
  #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
        ut_a(buf_block_get_state(block) == BUF_BLOCK_FILE_PAGE);
-@@ -3026,7 +3183,10 @@
+@@ -3031,7 +3188,10 @@
        buf_page_t*     hash_page;
-       buf_pool_t*     buf_pool = buf_pool_get(space, offset);
  
+       ut_ad(buf_pool == buf_pool_get(space, offset));
 -      ut_ad(buf_pool_mutex_own(buf_pool));
 +      //ut_ad(buf_pool_mutex_own(buf_pool));
 +#ifdef UNIV_SYNC_DEBUG
        ut_ad(mutex_own(&(block->mutex)));
        ut_a(buf_block_get_state(block) != BUF_BLOCK_FILE_PAGE);
  
-@@ -3055,11 +3215,14 @@
+@@ -3060,11 +3220,14 @@
        if (UNIV_LIKELY(!hash_page)) {
        } else if (buf_pool_watch_is_sentinel(buf_pool, hash_page)) {
                /* Preserve the reference count. */
        } else {
                fprintf(stderr,
                        "InnoDB: Error: page %lu %lu already found"
-@@ -3069,7 +3232,8 @@
+@@ -3074,7 +3237,8 @@
                        (const void*) hash_page, (const void*) block);
  #if defined UNIV_DEBUG || defined UNIV_BUF_DEBUG
                mutex_exit(&block->mutex);
                buf_print();
                buf_LRU_print();
                buf_validate();
-@@ -3152,7 +3316,9 @@
+@@ -3157,7 +3321,9 @@
  
        fold = buf_page_address_fold(space, offset);
  
  
        watch_page = buf_page_hash_get_low(buf_pool, space, offset, fold);
        if (watch_page && !buf_pool_watch_is_sentinel(buf_pool, watch_page)) {
-@@ -3161,9 +3327,15 @@
+@@ -3166,9 +3332,15 @@
  err_exit:
                if (block) {
                        mutex_enter(&block->mutex);
  
                bpage = NULL;
                goto func_exit;
-@@ -3186,6 +3358,8 @@
+@@ -3191,6 +3363,8 @@
  
-               buf_page_init(space, offset, fold, block);
+               buf_page_init(buf_pool, space, offset, fold, block);
  
 +              rw_lock_x_unlock(&buf_pool->page_hash_latch);
 +
                /* The block must be put to the LRU list, to the old blocks */
                buf_LRU_add_block(bpage, TRUE/* to old blocks */);
  
-@@ -3213,7 +3387,7 @@
+@@ -3218,7 +3392,7 @@
                        been added to buf_pool->LRU and
                        buf_pool->page_hash. */
                        mutex_exit(&block->mutex);
                        mutex_enter(&block->mutex);
                        block->page.zip.data = data;
  
-@@ -3226,13 +3400,14 @@
+@@ -3231,13 +3405,14 @@
                        buf_unzip_LRU_add_block(block, TRUE);
                }
  
  
                /* If buf_buddy_alloc() allocated storage from the LRU list,
                it released and reacquired buf_pool->mutex.  Thus, we must
-@@ -3248,7 +3423,10 @@
+@@ -3253,7 +3428,10 @@
  
                                /* The block was added by some other thread. */
                                watch_page = NULL;
  
                                bpage = NULL;
                                goto func_exit;
-@@ -3296,20 +3474,26 @@
+@@ -3301,20 +3479,26 @@
                HASH_INSERT(buf_page_t, hash, buf_pool->page_hash, fold,
                            bpage);
  
  
        if (mode == BUF_READ_IBUF_PAGES_ONLY) {
  
-@@ -3351,7 +3535,9 @@
+@@ -3356,7 +3540,9 @@
  
        fold = buf_page_address_fold(space, offset);
  
  
        block = (buf_block_t*) buf_page_hash_get_low(
                buf_pool, space, offset, fold);
-@@ -3367,7 +3553,9 @@
+@@ -3372,7 +3558,9 @@
  #endif /* UNIV_DEBUG_FILE_ACCESSES || UNIV_DEBUG */
  
                /* Page can be found in buf_pool */
  
                buf_block_free(free_block);
  
-@@ -3389,6 +3577,7 @@
+@@ -3394,6 +3582,7 @@
        mutex_enter(&block->mutex);
  
-       buf_page_init(space, offset, fold, block);
+       buf_page_init(buf_pool, space, offset, fold, block);
 +      rw_lock_x_unlock(&buf_pool->page_hash_latch);
  
        /* The block must be put to the LRU list */
        buf_LRU_add_block(&block->page, FALSE);
-@@ -3415,7 +3604,7 @@
+@@ -3420,7 +3609,7 @@
                the reacquisition of buf_pool->mutex.  We also must
                defer this operation until after the block descriptor
                has been added to buf_pool->LRU and buf_pool->page_hash. */
                mutex_enter(&block->mutex);
                block->page.zip.data = data;
  
-@@ -3433,7 +3622,8 @@
+@@ -3438,7 +3627,8 @@
  
        buf_page_set_accessed(&block->page, time_ms);
  
  
        mtr_memo_push(mtr, block, MTR_MEMO_BUF_FIX);
  
-@@ -3484,6 +3674,8 @@
+@@ -3493,7 +3683,9 @@
+       ibool           ret = TRUE;
+       /* First unfix and release lock on the bpage */
+-      buf_pool_mutex_enter(buf_pool);
++      //buf_pool_mutex_enter(buf_pool);
++      mutex_enter(&buf_pool->LRU_list_mutex);
++      rw_lock_x_lock(&buf_pool->page_hash_latch);
+       mutex_enter(buf_page_get_mutex(bpage));
+       ut_ad(buf_page_get_io_fix(bpage) == BUF_IO_READ);
+       ut_ad(bpage->buf_fix_count == 0);
+@@ -3514,11 +3706,15 @@
+               ret = FALSE;
+       }
++      buf_pool_mutex_enter(buf_pool);
+       ut_ad(buf_pool->n_pend_reads > 0);
+       buf_pool->n_pend_reads--;
++      buf_pool_mutex_exit(buf_pool);
+       mutex_exit(buf_page_get_mutex(bpage));
+-      buf_pool_mutex_exit(buf_pool);
++      //buf_pool_mutex_exit(buf_pool);
++      mutex_exit(&buf_pool->LRU_list_mutex);
++      rw_lock_x_unlock(&buf_pool->page_hash_latch);
+       return(ret);
+ }
+@@ -3536,6 +3732,8 @@
        buf_pool_t*     buf_pool = buf_pool_from_bpage(bpage);
        const ibool     uncompressed = (buf_page_get_state(bpage)
                                        == BUF_BLOCK_FILE_PAGE);
  
        ut_a(buf_page_in_file(bpage));
  
-@@ -3617,8 +3809,26 @@
+@@ -3678,8 +3876,26 @@
                }
        }
  
  
  #ifdef UNIV_IBUF_COUNT_DEBUG
        if (io_type == BUF_IO_WRITE || uncompressed) {
-@@ -3641,6 +3851,7 @@
+@@ -3702,6 +3918,7 @@
                the x-latch to this OS thread: do not let this confuse you in
                debugging! */
  
                ut_ad(buf_pool->n_pend_reads > 0);
                buf_pool->n_pend_reads--;
                buf_pool->stat.n_pages_read++;
-@@ -3658,6 +3869,9 @@
+@@ -3719,6 +3936,9 @@
  
                buf_flush_write_complete(bpage);
  
                if (uncompressed) {
                        rw_lock_s_unlock_gen(&((buf_block_t*) bpage)->lock,
                                             BUF_IO_WRITE);
-@@ -3680,8 +3894,8 @@
+@@ -3741,8 +3961,8 @@
        }
  #endif /* UNIV_DEBUG */
  
  }
  
  /*********************************************************************//**
-@@ -3698,7 +3912,9 @@
+@@ -3759,7 +3979,9 @@
  
        ut_ad(buf_pool);
  
  
        chunk = buf_pool->chunks;
  
-@@ -3715,7 +3931,9 @@
+@@ -3776,7 +3998,9 @@
                }
        }
  
  
        return(TRUE);
  }
-@@ -3763,7 +3981,8 @@
+@@ -3824,7 +4048,8 @@
                freed = buf_LRU_search_and_free_block(buf_pool, 100);
        }
  
  
        ut_ad(UT_LIST_GET_LEN(buf_pool->LRU) == 0);
        ut_ad(UT_LIST_GET_LEN(buf_pool->unzip_LRU) == 0);
-@@ -3776,7 +3995,8 @@
+@@ -3837,7 +4062,8 @@
        memset(&buf_pool->stat, 0x00, sizeof(buf_pool->stat));
        buf_refresh_io_stats(buf_pool);
  
  }
  
  /*********************************************************************//**
-@@ -3818,7 +4038,10 @@
+@@ -3879,7 +4105,10 @@
  
        ut_ad(buf_pool);
  
  
        chunk = buf_pool->chunks;
  
-@@ -3913,7 +4136,7 @@
+@@ -3974,7 +4203,7 @@
        /* Check clean compressed-only blocks. */
  
        for (b = UT_LIST_GET_FIRST(buf_pool->zip_clean); b;
                ut_a(buf_page_get_state(b) == BUF_BLOCK_ZIP_PAGE);
                switch (buf_page_get_io_fix(b)) {
                case BUF_IO_NONE:
-@@ -3944,7 +4167,7 @@
+@@ -4005,7 +4234,7 @@
  
        buf_flush_list_mutex_enter(buf_pool);
        for (b = UT_LIST_GET_FIRST(buf_pool->flush_list); b;
                ut_ad(b->in_flush_list);
                ut_a(b->oldest_modification);
                n_flush++;
-@@ -4003,6 +4226,8 @@
+@@ -4064,6 +4293,8 @@
        }
  
        ut_a(UT_LIST_GET_LEN(buf_pool->LRU) == n_lru);
        if (UT_LIST_GET_LEN(buf_pool->free) != n_free) {
                fprintf(stderr, "Free list len %lu, free blocks %lu\n",
                        (ulong) UT_LIST_GET_LEN(buf_pool->free),
-@@ -4013,8 +4238,11 @@
+@@ -4074,8 +4305,11 @@
        ut_a(buf_pool->n_flush[BUF_FLUSH_SINGLE_PAGE] == n_single_flush);
        ut_a(buf_pool->n_flush[BUF_FLUSH_LIST] == n_list_flush);
        ut_a(buf_pool->n_flush[BUF_FLUSH_LRU] == n_lru_flush);
  
        ut_a(buf_LRU_validate());
        ut_a(buf_flush_validate(buf_pool));
-@@ -4070,7 +4298,9 @@
+@@ -4131,7 +4365,9 @@
        index_ids = mem_alloc(size * sizeof *index_ids);
        counts = mem_alloc(sizeof(ulint) * size);
  
        buf_flush_list_mutex_enter(buf_pool);
  
        fprintf(stderr,
-@@ -4139,7 +4369,9 @@
+@@ -4200,7 +4436,9 @@
                }
        }
  
  
        for (i = 0; i < n_found; i++) {
                index = dict_index_get_if_in_cache(index_ids[i]);
-@@ -4196,7 +4428,7 @@
+@@ -4257,7 +4495,7 @@
        buf_chunk_t*    chunk;
        ulint           fixed_pages_number = 0;
  
  
        chunk = buf_pool->chunks;
  
-@@ -4230,7 +4462,7 @@
+@@ -4291,7 +4529,7 @@
        /* Traverse the lists of clean and dirty compressed-only blocks. */
  
        for (b = UT_LIST_GET_FIRST(buf_pool->zip_clean); b;
                ut_a(buf_page_get_state(b) == BUF_BLOCK_ZIP_PAGE);
                ut_a(buf_page_get_io_fix(b) != BUF_IO_WRITE);
  
-@@ -4242,7 +4474,7 @@
+@@ -4303,7 +4541,7 @@
  
        buf_flush_list_mutex_enter(buf_pool);
        for (b = UT_LIST_GET_FIRST(buf_pool->flush_list); b;
                ut_ad(b->in_flush_list);
  
                switch (buf_page_get_state(b)) {
-@@ -4268,7 +4500,7 @@
+@@ -4329,7 +4567,7 @@
  
        buf_flush_list_mutex_exit(buf_pool);
        mutex_exit(&buf_pool->zip_mutex);
  
        return(fixed_pages_number);
  }
-@@ -4424,6 +4656,8 @@
+@@ -4487,6 +4725,8 @@
        /* Find appropriate pool_info to store stats for this buffer pool */
        pool_info = &all_pool_info[pool_id];
  
        buf_pool_mutex_enter(buf_pool);
        buf_flush_list_mutex_enter(buf_pool);
  
-@@ -4534,6 +4768,8 @@
+@@ -4602,6 +4842,8 @@
        pool_info->unzip_cur = buf_LRU_stat_cur.unzip;
  
        buf_refresh_io_stats(buf_pool);
        buf_pool_mutex_exit(buf_pool);
  }
  
-@@ -4775,11 +5011,13 @@
+@@ -4846,11 +5088,13 @@
  {
        ulint   len;
  
 +      buf_LRU_block_free_non_file_page(block, have_page_hash_mutex);
  }
  
- /**********************************************************************//**
-@@ -1909,7 +2063,8 @@
+ /******************************************************************//**
+@@ -1897,7 +2051,7 @@
+ {
+       if (buf_LRU_block_remove_hashed_page(bpage, TRUE)
+           != BUF_BLOCK_ZIP_FREE) {
+-              buf_LRU_block_free_hashed_page((buf_block_t*) bpage);
++              buf_LRU_block_free_hashed_page((buf_block_t*) bpage, TRUE);
+       }
+ }
+@@ -1925,7 +2079,8 @@
        }
  
        if (adjust) {
  
                if (ratio != buf_pool->LRU_old_ratio) {
                        buf_pool->LRU_old_ratio = ratio;
-@@ -1921,7 +2076,8 @@
+@@ -1937,7 +2092,8 @@
                        }
                }
  
        } else {
                buf_pool->LRU_old_ratio = ratio;
        }
-@@ -2026,7 +2182,8 @@
+@@ -2042,7 +2198,8 @@
        ulint           new_len;
  
        ut_ad(buf_pool);
  
        if (UT_LIST_GET_LEN(buf_pool->LRU) >= BUF_LRU_OLD_MIN_LEN) {
  
-@@ -2087,16 +2244,22 @@
+@@ -2103,16 +2260,22 @@
  
        ut_a(buf_pool->LRU_old_len == old_len);
  
        UT_LIST_VALIDATE(unzip_LRU, buf_block_t, buf_pool->unzip_LRU,
                         ut_ad(ut_list_node_313->in_unzip_LRU_list
                               && ut_list_node_313->page.in_LRU_list));
-@@ -2110,7 +2273,8 @@
+@@ -2126,7 +2289,8 @@
                ut_a(buf_page_belongs_to_unzip_LRU(&block->page));
        }
  
  }
  
  /**********************************************************************//**
-@@ -2146,7 +2310,8 @@
+@@ -2162,7 +2326,8 @@
        const buf_page_t*       bpage;
  
        ut_ad(buf_pool);
  
        bpage = UT_LIST_GET_FIRST(buf_pool->LRU);
  
-@@ -2203,7 +2368,8 @@
+@@ -2219,7 +2384,8 @@
                bpage = UT_LIST_GET_NEXT(LRU, bpage);
        }
  
  /**********************************************************************//**
 --- a/storage/innobase/buf/buf0rea.c
 +++ b/storage/innobase/buf/buf0rea.c
-@@ -311,6 +311,7 @@
+@@ -478,6 +478,7 @@
  
                return(0);
        }
  
        /* Check that almost all pages in the area have been accessed; if
        offset == low, the accesses must be in a descending order, otherwise,
-@@ -329,6 +330,7 @@
+@@ -496,6 +497,7 @@
  
        fail_count = 0;
  
        for (i = low; i < high; i++) {
                bpage = buf_page_hash_get(buf_pool, space, i);
  
-@@ -356,7 +358,8 @@
+@@ -523,7 +525,8 @@
  
                if (fail_count > threshold) {
                        /* Too many failures: return */
                        return(0);
                }
  
-@@ -371,7 +374,8 @@
+@@ -538,7 +541,8 @@
        bpage = buf_page_hash_get(buf_pool, space, offset);
  
        if (bpage == NULL) {
  
                return(0);
        }
-@@ -397,7 +401,8 @@
+@@ -564,7 +568,8 @@
        pred_offset = fil_page_get_prev(frame);
        succ_offset = fil_page_get_next(frame);
  
  #  endif /* !PFS_SKIP_BUFFER_MUTEX_RWLOCK */
 --- a/storage/innobase/handler/i_s.cc
 +++ b/storage/innobase/handler/i_s.cc
-@@ -1563,7 +1563,8 @@
+@@ -1583,7 +1583,8 @@
  
                buf_pool = buf_pool_from_array(i);
  
  
                for (uint x = 0; x <= BUF_BUDDY_SIZES; x++) {
                        buf_buddy_stat_t*       buddy_stat;
-@@ -1593,7 +1594,8 @@
+@@ -1613,7 +1614,8 @@
                        }
                }
  
  #ifdef UNIV_MATERIALIZE
 --- a/storage/innobase/include/buf0buf.h
 +++ b/storage/innobase/include/buf0buf.h
-@@ -208,6 +208,20 @@
+@@ -212,6 +212,20 @@
  /*==========================*/
  
  /********************************************************************//**
  Creates the buffer pool.
  @return       own: buf_pool object, NULL if not enough memory or error */
  UNIV_INTERN
-@@ -873,6 +887,15 @@
+@@ -864,6 +878,15 @@
        const buf_page_t*       bpage)  /*!< in: pointer to control block */
        __attribute__((pure));
  
  /*********************************************************************//**
  Get the flush type of a page.
  @return       flush type */
-@@ -1354,7 +1377,7 @@
+@@ -1345,7 +1368,7 @@
        All these are protected by buf_pool->mutex. */
        /* @{ */
  
                                        /*!< based on state, this is a
                                        list node, protected either by
                                        buf_pool->mutex or by
-@@ -1382,6 +1405,10 @@
+@@ -1373,6 +1396,10 @@
                                        BUF_BLOCK_REMOVE_HASH or
                                        BUF_BLOCK_READY_IN_USE. */
  
  #ifdef UNIV_DEBUG
        ibool           in_flush_list;  /*!< TRUE if in buf_pool->flush_list;
                                        when buf_pool->flush_list_mutex is
-@@ -1474,11 +1501,11 @@
+@@ -1465,11 +1492,11 @@
                                        a block is in the unzip_LRU list
                                        if page.state == BUF_BLOCK_FILE_PAGE
                                        and page.zip.data != NULL */
        mutex_t         mutex;          /*!< mutex protecting this block:
                                        state (also protected by the buffer
                                        pool mutex), io_fix, buf_fix_count,
-@@ -1653,6 +1680,11 @@
+@@ -1646,6 +1673,11 @@
                                        pool instance, protects compressed
                                        only pages (of type buf_page_t, not
                                        buf_block_t */
        ulint           instance_no;    /*!< Array index of this buffer
                                        pool instance */
        ulint           old_pool_size;  /*!< Old pool size in bytes */
-@@ -1806,8 +1838,8 @@
+@@ -1799,8 +1831,8 @@
  /** Test if a buffer pool mutex is owned. */
  #define buf_pool_mutex_own(b) mutex_own(&b->mutex)
  /** Acquire a buffer pool mutex. */
  
 --- a/storage/innobase/include/buf0buf.ic
 +++ b/storage/innobase/include/buf0buf.ic
-@@ -274,7 +274,7 @@
+@@ -292,7 +292,7 @@
        case BUF_BLOCK_ZIP_FREE:
                /* This is a free page in buf_pool->zip_free[].
                Such pages should only be accessed by the buddy allocator. */
                break;
        case BUF_BLOCK_ZIP_PAGE:
        case BUF_BLOCK_ZIP_DIRTY:
-@@ -317,9 +317,16 @@
+@@ -335,9 +335,16 @@
  {
        buf_pool_t*     buf_pool = buf_pool_from_bpage(bpage);
  
                return(NULL);
        case BUF_BLOCK_ZIP_PAGE:
        case BUF_BLOCK_ZIP_DIRTY:
-@@ -329,6 +336,28 @@
+@@ -347,6 +354,28 @@
        }
  }
  
  /*********************************************************************//**
  Get the flush type of a page.
  @return       flush type */
-@@ -425,8 +454,8 @@
+@@ -443,8 +472,8 @@
        enum buf_io_fix io_fix) /*!< in: io_fix state */
  {
  #ifdef UNIV_DEBUG
  #endif
        ut_ad(mutex_own(buf_page_get_mutex(bpage)));
  
-@@ -456,14 +485,14 @@
+@@ -474,14 +503,14 @@
        const buf_page_t*       bpage)  /*!< control block being relocated */
  {
  #ifdef UNIV_DEBUG
               && bpage->buf_fix_count == 0);
  }
  
-@@ -477,8 +506,8 @@
+@@ -495,8 +524,8 @@
        const buf_page_t*       bpage)  /*!< in: control block */
  {
  #ifdef UNIV_DEBUG
  #endif
        ut_ad(buf_page_in_file(bpage));
  
-@@ -498,7 +527,8 @@
+@@ -516,7 +545,8 @@
        buf_pool_t*     buf_pool = buf_pool_from_bpage(bpage);
  #endif /* UNIV_DEBUG */
        ut_a(buf_page_in_file(bpage));
        ut_ad(bpage->in_LRU_list);
  
  #ifdef UNIV_LRU_DEBUG
-@@ -545,9 +575,10 @@
+@@ -563,9 +593,10 @@
        ulint           time_ms)        /*!< in: ut_time_ms() */
  {
  #ifdef UNIV_DEBUG
        ut_a(buf_page_in_file(bpage));
  
        if (!bpage->access_time) {
-@@ -790,19 +821,19 @@
+@@ -808,19 +839,19 @@
  /*===========*/
        buf_block_t*    block)  /*!< in, own: block to be freed */
  {
  }
  #endif /* !UNIV_HOTBACKUP */
  
-@@ -850,17 +881,17 @@
+@@ -868,17 +899,17 @@
                                        page frame */
  {
        ib_uint64_t     lsn;
  
        return(lsn);
  }
-@@ -878,7 +909,7 @@
+@@ -896,7 +927,7 @@
  #ifdef UNIV_SYNC_DEBUG
        buf_pool_t*     buf_pool = buf_pool_from_bpage((buf_page_t*)block);
  
               && (block->page.buf_fix_count == 0))
              || rw_lock_own(&(block->lock), RW_LOCK_EXCLUSIVE));
  #endif /* UNIV_SYNC_DEBUG */
-@@ -995,7 +1026,11 @@
+@@ -1026,7 +1057,11 @@
        buf_page_t*     bpage;
  
        ut_ad(buf_pool);
        ut_ad(fold == buf_page_address_fold(space, offset));
  
        /* Look for the page in the hash table */
-@@ -1080,11 +1115,13 @@
+@@ -1111,11 +1146,13 @@
        const buf_page_t*       bpage;
        buf_pool_t*             buf_pool = buf_pool_get(space, offset);
  
  
        return(bpage != NULL);
  }
-@@ -1212,4 +1249,38 @@
+@@ -1243,4 +1280,38 @@
                buf_pool_mutex_exit(buf_pool);
        }
  }
  extern mysql_pfs_key_t        cache_last_read_mutex_key;
  extern mysql_pfs_key_t        dict_foreign_err_mutex_key;
  extern mysql_pfs_key_t        dict_sys_mutex_key;
-@@ -670,7 +674,7 @@
+@@ -667,7 +671,7 @@
  #define SYNC_TRX_SYS_HEADER   290
  #define       SYNC_PURGE_QUEUE        200
  #define SYNC_LOG              170
  #define SYNC_RECV             168
  #define       SYNC_WORK_QUEUE         162
  #define       SYNC_SEARCH_SYS_CONF    161     /* for assigning btr_search_enabled */
-@@ -680,8 +684,13 @@
+@@ -677,8 +681,13 @@
                                        SYNC_SEARCH_SYS, as memory allocation
                                        can call routines there! Otherwise
                                        the level is SYNC_MEM_HASH. */
  #define       SYNC_BUF_FLUSH_LIST     145     /* Buffer flush list mutex */
  #define SYNC_DOUBLEWRITE      140
  #define       SYNC_ANY_LATCH          135
-@@ -713,7 +722,7 @@
+@@ -709,7 +718,7 @@
                os_fast_mutex;  /*!< We use this OS mutex in place of lock_word
                                when atomic operations are not enabled */
  #endif
                                Otherwise, this is 0. */
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -3098,7 +3098,7 @@
+@@ -3102,7 +3102,7 @@
                                                                level += log_sys->max_checkpoint_age
                                                                         - (lsn - oldest_modification);
                                                        }
                                                        n_blocks++;
                                                }
  
-@@ -3184,7 +3184,7 @@
+@@ -3188,7 +3188,7 @@
                                                        found = TRUE;
                                                        break;
                                                }
  }
  
  /******************************************************************//**
-@@ -1239,7 +1249,12 @@
+@@ -1234,7 +1244,12 @@
                        ut_error;
                }
                break;
        case SYNC_BUF_POOL:
                /* We can have multiple mutexes of this type therefore we
                can only check whether the greater than condition holds. */
-@@ -1257,7 +1272,8 @@
+@@ -1252,7 +1267,8 @@
                buffer block (block->mutex or buf_pool->zip_mutex). */
                if (!sync_thread_levels_g(array, level, FALSE)) {
                        ut_a(sync_thread_levels_g(array, level - 1, TRUE));
index 8d8d78317089bd6f45291431841b25fad362caa1..4f4ee62f83d6d2345b8d22859b213ecf84163a0f 100644 (file)
        }
  
        return(table);
-@@ -4343,6 +4343,295 @@
+@@ -4344,6 +4344,295 @@
  }
  
  /*********************************************************************//**
  Calculates new estimates for table and index statistics. The statistics
  are used in query optimization. */
  UNIV_INTERN
-@@ -4350,10 +4639,11 @@
+@@ -4351,10 +4640,11 @@
  dict_update_statistics(
  /*===================*/
        dict_table_t*   table,          /*!< in/out: table */
  {
        dict_index_t*   index;
        ulint           sum_of_index_sizes      = 0;
-@@ -4370,6 +4660,27 @@
+@@ -4371,6 +4661,27 @@
                return;
        }
  
        /* Find out the sizes of the indexes and how many different values
        for the key they approximately have */
  
-@@ -4434,6 +4745,11 @@
+@@ -4435,6 +4746,11 @@
                index = dict_table_get_next_index(index);
        } while (index);
  
        index = dict_table_get_first_index(table);
  
        table->stat_n_rows = index->stat_n_diff_key_vals[
-@@ -4451,6 +4767,78 @@
+@@ -4452,6 +4768,78 @@
        dict_table_stats_unlock(table, RW_X_LATCH);
  }
  
  /**********************************************************************//**
  Prints info of a foreign key constraint. */
  static
-@@ -4528,7 +4916,8 @@
+@@ -4529,7 +4917,8 @@
  
        ut_ad(mutex_own(&(dict_sys->mutex)));
  
 +      "SYS_FOREIGN_COLS",
 +      "SYS_STATS"
  };
- /****************************************************************//**
- Compare the name of an index column.
-@@ -343,12 +344,13 @@
+ /* If this flag is TRUE, then we will load the cluster index's (and tables')
+@@ -348,12 +349,13 @@
        }
  
        if ((status & DICT_TABLE_UPDATE_STATS)
        }
  
        return(NULL);
-@@ -582,6 +584,75 @@
+@@ -587,6 +589,75 @@
  //#endif  /* FOREIGN_NOT_USED */
  
  /********************************************************************//**
  
  
  static char*  internal_innobase_data_file_path        = NULL;
-@@ -2439,6 +2440,8 @@
+@@ -2468,6 +2469,8 @@
                goto error;
        }
  
        /* -------------- Log files ---------------------------*/
  
        /* The default dir for log files is the datadir of MySQL */
-@@ -5247,6 +5250,10 @@
+@@ -5257,6 +5260,10 @@
  
        error = row_insert_for_mysql((byte*) record, prebuilt);
  
        /* Handle duplicate key errors */
        if (auto_inc_used) {
                ulint           err;
-@@ -5583,6 +5590,10 @@
+@@ -5593,6 +5600,10 @@
                }
        }
  
        innodb_srv_conc_exit_innodb(trx);
  
        error = convert_error_code_to_mysql(error,
-@@ -5636,6 +5647,10 @@
+@@ -5646,6 +5657,10 @@
  
        error = row_update_for_mysql((byte*) record, prebuilt);
  
        innodb_srv_conc_exit_innodb(trx);
  
        error = convert_error_code_to_mysql(
-@@ -5954,6 +5969,11 @@
+@@ -5966,6 +5981,11 @@
        case DB_SUCCESS:
                error = 0;
                table->status = 0;
                break;
        case DB_RECORD_NOT_FOUND:
                error = HA_ERR_KEY_NOT_FOUND;
-@@ -6163,6 +6183,11 @@
+@@ -6198,6 +6218,11 @@
        case DB_SUCCESS:
                error = 0;
                table->status = 0;
                break;
        case DB_RECORD_NOT_FOUND:
                error = HA_ERR_END_OF_FILE;
-@@ -8105,11 +8130,35 @@
+@@ -8144,11 +8169,35 @@
                        /* In sql_show we call with this flag: update
                        then statistics so that they are up-to-date */
  
  
                        prebuilt->trx->op_info = "returning various info to MySQL";
                }
-@@ -8187,7 +8236,7 @@
+@@ -8233,7 +8282,7 @@
                are asked by MySQL to avoid locking. Another reason to
                avoid the call is that it uses quite a lot of CPU.
                See Bug#38185. */
                    || !(flag & HA_STATUS_VARIABLE_EXTRA)) {
                        /* We do not update delete_length if no
                        locking is requested so the "old" value can
-@@ -11401,6 +11450,26 @@
+@@ -11503,6 +11552,26 @@
    "The number of index pages to sample when calculating statistics (default 8)",
    NULL, NULL, 8, 1, ~0ULL, 0);
  
  static MYSQL_SYSVAR_BOOL(adaptive_hash_index, btr_search_enabled,
    PLUGIN_VAR_OPCMDARG,
    "Enable InnoDB adaptive hash index (enabled by default).  "
-@@ -11727,6 +11796,9 @@
+@@ -11835,6 +11904,9 @@
    MYSQL_SYSVAR(recovery_update_relay_log),
    MYSQL_SYSVAR(rollback_on_timeout),
    MYSQL_SYSVAR(stats_on_metadata),
    MYSQL_SYSVAR(stats_sample_pages),
    MYSQL_SYSVAR(adaptive_hash_index),
    MYSQL_SYSVAR(stats_method),
-@@ -11796,7 +11868,10 @@
+@@ -11906,7 +11978,10 @@
  i_s_innodb_sys_columns,
  i_s_innodb_sys_fields,
  i_s_innodb_sys_foreign,
  }
  
  #define OK(expr)              \
-@@ -3455,6 +3456,221 @@
+@@ -3483,6 +3484,221 @@
        STRUCT_FLD(__reserved1, NULL)
  };
  
  /***********************************************************************
  */
  static ST_FIELD_INFO  i_s_innodb_rseg_fields_info[] =
-@@ -3617,3 +3833,347 @@
+@@ -3645,3 +3861,347 @@
        /* void* */
        STRUCT_FLD(__reserved1, NULL)
  };
 +#define       DICT_HDR_XTRADB_MARK    256     /* Flag to distinguish expansion of XtraDB */
  /*-------------------------------------------------------------*/
  
- /* The field number of the page number field in the sys_indexes table
-@@ -144,11 +148,16 @@
+ /* The field numbers in the SYS_TABLES clustered index */
+@@ -146,11 +150,16 @@
  #define DICT_SYS_INDEXES_TYPE_FIELD    6
  #define DICT_SYS_INDEXES_NAME_FIELD    4
  
  #include "dict0crea.ic"
 --- a/storage/innobase/include/dict0dict.h
 +++ b/storage/innobase/include/dict0dict.h
-@@ -1109,10 +1109,18 @@
+@@ -1126,10 +1126,18 @@
  dict_update_statistics(
  /*===================*/
        dict_table_t*   table,          /*!< in/out: table */
  /********************************************************************//**
  Reserves the dictionary system mutex for MySQL. */
  UNIV_INTERN
-@@ -1227,6 +1235,7 @@
+@@ -1244,6 +1252,7 @@
        dict_table_t*   sys_columns;    /*!< SYS_COLUMNS table */
        dict_table_t*   sys_indexes;    /*!< SYS_INDEXES table */
        dict_table_t*   sys_fields;     /*!< SYS_FIELDS table */
  should be called after the indexes for a table have been created.
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -211,6 +211,9 @@
+@@ -216,6 +216,9 @@
  extern ibool  srv_innodb_status;
  
  extern unsigned long long     srv_stats_sample_pages;
        } else {
 --- a/storage/innobase/row/row0ins.c
 +++ b/storage/innobase/row/row0ins.c
-@@ -2013,6 +2013,8 @@
+@@ -2015,6 +2015,8 @@
        }
  
  #ifdef UNIV_DEBUG
                /* Drop the index definition and the B-tree. */
 --- a/storage/innobase/row/row0mysql.c
 +++ b/storage/innobase/row/row0mysql.c
-@@ -921,6 +921,9 @@
+@@ -922,6 +922,9 @@
  
        table->stat_modified_counter = counter + 1;
  
        /* Calculate new statistics if 1 / 16 of table has been modified
        since the last time a statistics batch was run, or if
        stat_modified_counter > 2 000 000 000 (to avoid wrap-around).
-@@ -931,7 +934,7 @@
+@@ -932,7 +935,7 @@
            || ((ib_int64_t)counter > 16 + table->stat_n_rows / 16)) {
  
                dict_update_statistics(table, FALSE /* update even if stats
        }
  }
  
-@@ -2076,6 +2079,71 @@
+@@ -2077,6 +2080,71 @@
  }
  
  /*********************************************************************//**
  Scans a table create SQL string and adds to the data dictionary
  the foreign key constraints declared in the string. This function
  should be called after the indexes for a table have been created.
-@@ -3000,7 +3068,7 @@
+@@ -3001,7 +3069,7 @@
        dict_table_autoinc_initialize(table, 1);
        dict_table_autoinc_unlock(table);
        dict_update_statistics(table, FALSE /* update even if stats are
  
        trx_commit_for_mysql(trx);
  
-@@ -3302,6 +3370,8 @@
+@@ -3312,6 +3380,8 @@
                           "       IF (SQL % NOTFOUND) THEN\n"
                           "               found := 0;\n"
                           "       ELSE\n"
                           "               DELETE FROM SYS_INDEXES\n"
 --- a/storage/innobase/row/row0row.c
 +++ b/storage/innobase/row/row0row.c
-@@ -373,6 +373,14 @@
+@@ -364,6 +364,14 @@
  
        rec_len = rec_offs_n_fields(offsets);
  
        entry = dtuple_create(heap, rec_len);
  
        dtuple_set_n_fields_cmp(entry,
-@@ -384,6 +392,14 @@
+@@ -375,6 +383,14 @@
        for (i = 0; i < rec_len; i++) {
  
                dfield = dtuple_get_nth_field(entry, i);
                dfield = dtuple_get_nth_field(entry, i);
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -398,6 +398,9 @@
+@@ -400,6 +400,9 @@
  /* When estimating number of different key values in an index, sample
  this many index pages */
  UNIV_INTERN unsigned long long        srv_stats_sample_pages = 8;
  UNIV_INTERN ibool     srv_use_checksums = TRUE;
 --- a/storage/innobase/trx/trx0rec.c
 +++ b/storage/innobase/trx/trx0rec.c
-@@ -669,15 +669,27 @@
+@@ -669,14 +669,27 @@
        /* Save to the undo log the old values of the columns to be updated. */
  
        if (update) {
 +              ulint   extended = 0;
++
                if (trx_undo_left(undo_page, ptr) < 5) {
  
                        return(0);
 +                  && index == UT_LIST_GET_FIRST(dict_sys->sys_stats->indexes)) {
 +                      for (i = 0; i < upd_get_n_fields(update); i++) {
 +                              ulint   pos = upd_get_nth_field(update, i)->field_no;
--              for (i = 0; i < upd_get_n_fields(update); i++) {
++
 +                              if (pos >= rec_offs_n_fields(offsets)) {
 +                                      extended++;
 +                              }
 +              }
 +
 +              ptr += mach_write_compressed(ptr, upd_get_n_fields(update) - extended);
-+
+-              for (i = 0; i < upd_get_n_fields(update); i++) {
 +              for (i = 0; i < upd_get_n_fields(update) - extended; i++) {
  
                        ulint   pos = upd_get_nth_field(update, i)->field_no;
index 767a038340e89e414ed01166636490add3e85fd9..322961d8e66e2d7c784c1b357f9320fdf2e0a2b2 100644 (file)
@@ -15,7 +15,7 @@
  static long long innobase_buffer_pool_size, innobase_log_file_size;
  
  /** Percentage of the buffer pool to reserve for 'old' blocks.
-@@ -2548,6 +2549,9 @@
+@@ -2577,6 +2578,9 @@
        srv_n_log_files = (ulint) innobase_log_files_in_group;
        srv_log_file_size = (ulint) innobase_log_file_size;
  
@@ -25,7 +25,7 @@
  #ifdef UNIV_LOG_ARCHIVE
        srv_log_archive_on = (ulint) innobase_log_archive;
  #endif /* UNIV_LOG_ARCHIVE */
-@@ -11491,6 +11495,12 @@
+@@ -11593,6 +11597,12 @@
    "Maximum delay between polling for a spin lock (6 by default)",
    NULL, NULL, 6L, 0L, ~0L, 0);
  
@@ -38,7 +38,7 @@
  static MYSQL_SYSVAR_ULONG(thread_concurrency, srv_thread_concurrency,
    PLUGIN_VAR_RQCMDARG,
    "Helps in performance tuning in heavily concurrent environments. Sets the maximum number of threads allowed inside InnoDB. Value 0 will disable the thread throttling.",
-@@ -11703,6 +11713,7 @@
+@@ -11811,6 +11821,7 @@
    MYSQL_SYSVAR(spin_wait_delay),
    MYSQL_SYSVAR(table_locks),
    MYSQL_SYSVAR(thread_concurrency),
    MYSQL_SYSVAR(show_verbose_locks),
 --- a/storage/innobase/include/srv0srv.h
 +++ b/storage/innobase/include/srv0srv.h
-@@ -161,6 +161,8 @@
+@@ -165,6 +165,8 @@
  extern ulint  srv_mem_pool_size;
  extern ulint  srv_lock_table_size;
  
 +extern ibool  srv_thread_concurrency_timer_based;
 +
  extern ulint  srv_n_file_io_threads;
+ extern my_bool        srv_random_read_ahead;
  extern ulong  srv_read_ahead_threshold;
- extern ulint  srv_n_read_io_threads;
 --- a/storage/innobase/srv/srv0srv.c
 +++ b/storage/innobase/srv/srv0srv.c
-@@ -347,6 +347,7 @@
+@@ -349,6 +349,7 @@
  computer. Bigger computers need bigger values. Value 0 will disable the
  concurrency check. */
  
@@ -67,7 +67,7 @@
  UNIV_INTERN ulong     srv_thread_concurrency  = 0;
  
  /* this mutex protects srv_conc data structures */
-@@ -1143,6 +1144,75 @@
+@@ -1145,6 +1146,75 @@
  /*********************************************************************//**
  Puts an OS thread to wait if there are too many concurrent threads
  (>= srv_thread_concurrency) inside InnoDB. The threads wait in a FIFO queue. */
  UNIV_INTERN
  void
  srv_conc_enter_innodb(
-@@ -1177,6 +1247,13 @@
+@@ -1179,6 +1249,13 @@
                return;
        }
  
        os_fast_mutex_lock(&srv_conc_mutex);
  retry:
        if (trx->declared_to_be_inside_innodb) {
-@@ -1330,6 +1407,14 @@
+@@ -1332,6 +1409,14 @@
        }
  
        ut_ad(srv_conc_n_threads >= 0);
  
        os_fast_mutex_lock(&srv_conc_mutex);
  
-@@ -1363,6 +1448,13 @@
+@@ -1365,6 +1450,13 @@
                return;
        }
  
index cf41b7fe09718990eefccee20bb351546eb9e048..821a9cb2811ca7bc62638efa7dc1204fbfa00ef8 100644 (file)
@@ -41,7 +41,7 @@
    using my_pthread_setspecific_ptr()/my_thread_getspecific_ptr().
 --- a/sql/sql_class.cc
 +++ b/sql/sql_class.cc
-@@ -4854,7 +4854,7 @@
+@@ -4874,7 +4874,7 @@
                            ER_BINLOG_UNSAFE_STATEMENT,
                            ER(ER_BINLOG_UNSAFE_STATEMENT),
                            ER(LEX::binlog_stmt_unsafe_errcode[unsafe_type]));
@@ -62,7 +62,7 @@
                              SLAVE_EXEC_MODE_LAST_BIT};
 --- a/sql/sys_vars.cc
 +++ b/sql/sys_vars.cc
-@@ -1470,6 +1470,15 @@
+@@ -1493,6 +1493,15 @@
         READ_ONLY GLOBAL_VAR(mysqld_port), CMD_LINE(REQUIRED_ARG, 'P'),
         VALID_RANGE(0, UINT_MAX32), DEFAULT(0), BLOCK_SIZE(1));
  
 +  print "Occurrences: $count\n";
 +  close(FILE);
 +EOF
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -281,6 +281,9 @@
+  --log-tc-size=#     Size of transaction coordinator log.
+  -W, --log-warnings[=#] 
+  Log some not critical warnings to the log file
++ --log-warnings-suppress=name 
++ disable logging of enumerated warnings: 1592: unsafe
++ statements for binary logging; possible values : [1592]
+  --long-query-time=# Log all queries that have taken more than long_query_time
+  seconds to execute to file. The argument will be treated
+  as a decimal value with microsecond precision
+@@ -863,6 +866,7 @@
+ log-tc tc.log
+ log-tc-size 24576
+ log-warnings 1
++log-warnings-suppress 
+ long-query-time 10
+ low-priority-updates FALSE
+ lower-case-table-names 1
index dbea06bc38eca052206d433775dbcd5e4dcd663d..5b6da12e77f622af5a17473f3ef78f6373af5731 100644 (file)
@@ -19,7 +19,7 @@
  
  #define HP_MAX_LEVELS 4               /* 128^5 records is enough */
  #define HP_PTRS_IN_NOD        128
-@@ -130,22 +140,58 @@
+@@ -131,22 +141,58 @@
    uint (*get_key_length)(struct st_hp_keydef *keydef, const uchar *key);
  } HP_KEYDEF;
  
@@ -83,9 +83,9 @@
    uint open_count;
 -  uchar *del_link;                    /* Link to next block with del. rec */
    char * name;                        /* Name of "memory-file" */
+   time_t create_time;
    THR_LOCK lock;
-   mysql_mutex_t intern_lock;            /* Locking for use with _locking */
-@@ -154,6 +200,7 @@
+@@ -156,6 +202,7 @@
    uint auto_key;
    uint auto_key_type;                 /* real type of the auto key segment */
    ulonglong auto_increment;
@@ -93,7 +93,7 @@
  } HP_SHARE;
  
  struct st_hp_hash_info;
-@@ -163,7 +210,7 @@
+@@ -165,7 +212,7 @@
    HP_SHARE *s;
    uchar *current_ptr;
    struct st_hp_hash_info *current_hash_ptr;
    int lastinx,errkey;
    int  mode;                          /* Mode of file (READONLY..) */
    uint opt_flag,update;
-@@ -176,6 +223,9 @@
+@@ -178,6 +225,9 @@
    my_bool implicit_emptied;
    THR_LOCK_DATA lock;
    LIST open_list;
  } HP_INFO;
  
  
-@@ -197,6 +247,14 @@
+@@ -199,6 +249,14 @@
      open_count to 1. Is only looked at if not internal_table.
    */
    my_bool pin_share;
  } HP_CREATE_INFO;
  
        /* Prototypes for heap-functions */
-@@ -213,9 +271,8 @@
+@@ -215,9 +273,8 @@
  extern int heap_scan(register HP_INFO *info, uchar *record);
  extern int heap_delete(HP_INFO *info,const uchar *buff);
  extern int heap_info(HP_INFO *info,HEAPINFO *x,int flag);
    }
  }
  
-@@ -428,6 +435,13 @@
+@@ -429,6 +436,13 @@
    return 0;
  }
  
  
  int ha_heap::extra(enum ha_extra_function operation)
  {
-@@ -645,23 +659,70 @@
+@@ -646,23 +660,70 @@
  heap_prepare_hp_create_info(TABLE *table_arg, bool internal_table,
                              HP_CREATE_INFO *hp_create_info)
  {
    seg= reinterpret_cast<HA_KEYSEG*>(keydef + keys);
    for (key= 0; key < keys; key++)
    {
-@@ -677,11 +738,11 @@
+@@ -678,11 +739,11 @@
      case HA_KEY_ALG_UNDEF:
      case HA_KEY_ALG_HASH:
        keydef[key].algorithm= HA_KEY_ALG_HASH;
        break;
      default:
        DBUG_ASSERT(0); // cannot happen
-@@ -706,6 +767,16 @@
+@@ -707,6 +768,16 @@
        seg->length=  (uint) key_part->length;
        seg->flag=    key_part->key_part_flag;
  
        if (field->flags & (ENUM_FLAG | SET_FLAG))
          seg->charset= &my_charset_bin;
        else
-@@ -731,9 +802,75 @@
+@@ -732,9 +803,75 @@
          auto_key= key+ 1;
        auto_key_type= field->key_type();
        }
    if (table_arg->found_next_number_field)
    {
      keydef[share->next_number_index].flag|= HA_AUTO_KEY;
-@@ -744,16 +881,19 @@
+@@ -745,16 +882,19 @@
    hp_create_info->max_table_size=current_thd->variables.max_heap_table_size;
    hp_create_info->with_auto_increment= found_real_auto_increment;
    hp_create_info->internal_table= internal_table;
    return 0;
  }
  
-@@ -773,6 +913,7 @@
+@@ -774,6 +914,7 @@
                                  create_info->auto_increment_value - 1 : 0);
    error= heap_create(name, &hp_create_info, &internal_share, &created);
    my_free(hp_create_info.keydef);
    DBUG_ASSERT(file == 0);
    return (error);
  }
-@@ -783,6 +924,13 @@
+@@ -784,6 +925,13 @@
    table->file->info(HA_STATUS_AUTO);
    if (!(create_info->used_fields & HA_CREATE_USED_AUTO))
      create_info->auto_increment_value= stats.auto_increment_value;
        /* Fix keys */
      memcpy(share->keydef, keydef, (size_t) (sizeof(keydef[0]) * keys));
      for (i= 0, keyinfo= share->keydef; i < keys; i++, keyinfo++)
-@@ -177,15 +310,35 @@
+@@ -177,16 +310,36 @@
      share->min_records= min_records;
      share->max_records= max_records;
      share->max_table_size= create_info->max_table_size;
      share->auto_key= create_info->auto_key;
      share->auto_key_type= create_info->auto_key_type;
      share->auto_increment= create_info->auto_increment;
+     share->create_time= (long) time((time_t*) 0);
 +
 +    share->fixed_data_length= fixed_data_length;
 +    share->fixed_column_count= fixed_column_count;
      /* Must be allocated separately for rename to work */
      if (!(share->name= my_strdup(name,MYF(0))))
      {
-@@ -227,7 +380,7 @@
+@@ -228,7 +381,7 @@
                    param->search_flag, not_used);
  }
  
                       ulong max_records)
  {
    uint i,recbuffer,records_in_block;
-@@ -235,7 +388,12 @@
+@@ -236,7 +389,12 @@
    max_records= max(min_records,max_records);
    if (!max_records)
      max_records= 1000;                        /* As good as quess as anything */
 +PRIMARY KEY (f1)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=33 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=34 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=34    
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=34    
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=123 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=123   
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=123   
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=1000 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=1000  
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=1000  
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=33 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=34 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=34    
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=34    
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=121 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=121   
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=121   
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=1000 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=1000  
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=1000  
 +DROP TABLE t1;
 --- /dev/null
 +++ b/mysql-test/r/percona_heap_bug784464_32bit.result
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=124 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=124   
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=124   
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=122 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=122   
++t1    MEMORY  10      Dynamic 0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=122   
 +DROP TABLE t1;
 --- /dev/null
 +++ b/mysql-test/r/percona_heap_bug784464_64bit.result
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=124 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=124   
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=124   
 +DROP TABLE t1;
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +PRIMARY KEY (f1)) KEY_BLOCK_SIZE=122 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=122   
++t1    MEMORY  10      Fixed   0       X       0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC KEY_BLOCK_SIZE=122   
 +DROP TABLE t1;
 --- /dev/null
 +++ b/mysql-test/r/percona_heap_bug784468.result
 +CREATE TABLE t1 ( f1 VARCHAR(30)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       32      0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
++t1    MEMORY  10      Fixed   0       32      0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
 +DROP TABLE t1;
 +CREATE TABLE t1 ( f1 VARCHAR(31)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       33      0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
++t1    MEMORY  10      Fixed   0       33      0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
 +DROP TABLE t1;
 +CREATE TABLE t1 ( f1 VARCHAR(32)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
 +SHOW TABLE STATUS LIKE 't1';
 +Name  Engine  Version Row_format      Rows    Avg_row_length  Data_length     Max_data_length Index_length    Data_free       Auto_increment  Create_time     Update_time     Check_time      Collation       Checksum        Create_options  Comment
-+t1    MEMORY  10      Fixed   0       34      0       X       0       0       NULL    NULL    NULL    NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
++t1    MEMORY  10      Fixed   0       34      0       X       0       0       NULL    X       X       NULL    latin1_swedish_ci       NULL    row_format=DYNAMIC      
 +DROP TABLE t1;
 --- /dev/null
 +++ b/mysql-test/r/percona_heap_bug788544.result
 +DROP TABLE local_1_1;
 --- /dev/null
 +++ b/mysql-test/t/percona_heap_bug784464.test
-@@ -0,0 +1,64 @@
+@@ -0,0 +1,66 @@
 +#
 +# Bug #784464: Silent conversion from Dynamic to Fixed row_format for certain
 +# values of key_block_size.
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +--error ER_CANT_USE_OPTION_HERE
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=33 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
++--replace_column 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=34 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=123 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=1000 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +--error ER_CANT_USE_OPTION_HERE
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=33 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
++--replace_column 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=34 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=121 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=1000 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=124 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=122 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 --- /dev/null
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(32), f3 VARCHAR(32), f4 VARCHAR(32),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=124 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 (f1 VARCHAR(32), f2 VARCHAR(96),
 +                      PRIMARY KEY (f1)) KEY_BLOCK_SIZE=122 ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 6 X 8 X
++--replace_column 6 X 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 --- /dev/null
 +#
 +
 +CREATE TABLE t1 ( f1 VARCHAR(30)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 8 X
++--replace_column 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 ( f1 VARCHAR(31)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 8 X
++--replace_column 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
 +CREATE TABLE t1 ( f1 VARCHAR(32)) ENGINE=HEAP ROW_FORMAT=DYNAMIC;
-+--replace_column 8 X
++--replace_column 8 X 12 X 13 X
 +SHOW TABLE STATUS LIKE 't1';
 +DROP TABLE t1;
 +
index 0f9842a8243705f34de037b50ca4bfb7c6aafb0f..4a17c29921e0ac3f9e4414673d13dad6e0ce401a 100644 (file)
@@ -5,8 +5,8 @@
 #!!! notice !!!
 # Any small change to this file in the main branch
 # should be done or reviewed by the maintainer!
---- /dev/null  1970-01-01 09:00:00.000000000 +0900
-+++ b/patch_info/microsec_process.info 2010-12-02 20:41:41.616069579 +0900
+--- /dev/null
++++ b/patch_info/microsec_process.info
 @@ -0,0 +1,8 @@
 +File=microsec_process.patch
 +Name=Adds INFOMATION_SCHEMA.PROCESSLIST with TIME_MS column
@@ -16,8 +16,8 @@
 +Comment=
 +2010-01
 +Ported to 5.1.42
---- a/sql/sql_show.cc  2010-12-02 19:22:40.054024541 +0900
-+++ b/sql/sql_show.cc  2010-12-02 20:41:41.622941425 +0900
+--- a/sql/sql_show.cc
++++ b/sql/sql_show.cc
 @@ -1890,7 +1890,8 @@
    TABLE *table= tables->table;
    CHARSET_INFO *cs= system_charset_info;
@@ -39,7 +39,7 @@
        if (schema_table_store_record(thd, table))
        {
          mysql_mutex_unlock(&LOCK_thread_count);
-@@ -7409,6 +7414,8 @@
+@@ -7464,6 +7469,8 @@
    {"STATE", 64, MYSQL_TYPE_STRING, 0, 1, "State", SKIP_OPEN_TABLE},
    {"INFO", PROCESS_LIST_INFO_WIDTH, MYSQL_TYPE_STRING, 0, 1, "Info",
     SKIP_OPEN_TABLE},
index 2887e47066717b8ac54ba5da668d2ba6069d93fa..75d3d135248d2b9612fe2ea0f0b958dde2fc68c3 100644 (file)
@@ -35,13 +35,13 @@ Summary(ru.UTF-8):  MySQL - быстрый SQL-сервер
 Summary(uk.UTF-8):     MySQL - швидкий SQL-сервер
 Summary(zh_CN.UTF-8):  MySQL数据库服务器
 Name:          mysql
-Version:       5.5.15
-Release:       3
+Version:       5.5.17
+Release:       1
 License:       GPL + MySQL FLOSS Exception
 Group:         Applications/Databases
 # Source0Download: http://dev.mysql.com/downloads/mysql/5.5.html#downloads
 Source0:       http://vesta.informatik.rwth-aachen.de/mysql/Downloads/MySQL-5.5/%{name}-%{version}.tar.gz
-# Source0-md5: 306b5549c7bd72e8e705a890db0da82b
+# Source0-md5: dcb6a06e68c5e8f30f57b15300730c9c
 Source100:     http://www.sphinxsearch.com/files/sphinx-2.0.1-beta.tar.gz
 # Source100-md5:       95c217d81d0b7a4ff73d5297318c3481
 Source1:       %{name}.init
@@ -108,31 +108,36 @@ Patch127: innodb_adaptive_hash_index_partitions.patch
 Patch128:      innodb_buffer_pool_pages_i_s.patch
 Patch129:      innodb_buffer_pool_shm.patch
 Patch130:      innodb_show_status_extend.patch
-Patch131:      slow_extended.patch
-Patch132:      percona_support.patch
-Patch133:      query_cache_enhance.patch
-Patch134:      log_connection_error.patch
-Patch135:      mysql_syslog.patch
-Patch136:      error_pad.patch
-Patch137:      response_time_distribution.patch
-Patch138:      remove_fcntl_excessive_calls.patch
-Patch139:      sql_no_fcache.patch
-Patch140:      show_slave_status_nolock.patch
-Patch141:      log_warnings_suppress.patch
-Patch142:      userstat.patch
-Patch143:      bug580324.patch
-Patch144:      mysql_remove_eol_carret.patch
-Patch145:      processlist_row_stats.patch
-Patch146:      innodb_expand_fast_index_creation.patch
-Patch147:      innodb_bug60788.patch
-Patch148:      start-stop-messages.patch
-Patch149:      file-contents.patch
-Patch150:      slave_timeout_fix.patch
-Patch151:      utf8_general50_ci.patch
-Patch152:      bug813587.patch
-Patch153:      valgrind_zlib_suppression.patch
-Patch154:      memory_dynamic_rows.patch
-Patch155:      xtradb_bug317074.patch
+Patch131:      innodb_kill_idle_transaction.patch
+Patch132:      innodb_fake_changes.patch
+Patch133:      slow_extended.patch
+Patch134:      percona_support.patch
+Patch135:      query_cache_enhance.patch
+Patch136:      log_connection_error.patch
+Patch137:      mysql_syslog.patch
+Patch138:      error_pad.patch
+Patch139:      response_time_distribution.patch
+Patch140:      remove_fcntl_excessive_calls.patch
+Patch141:      sql_no_fcache.patch
+Patch142:      show_slave_status_nolock.patch
+Patch143:      log_warnings_suppress.patch
+Patch144:      userstat.patch
+Patch145:      bug580324.patch
+Patch146:      mysql_remove_eol_carret.patch
+Patch147:      processlist_row_stats.patch
+Patch148:      innodb_expand_fast_index_creation.patch
+Patch149:      innodb_bug60788.patch
+Patch150:      start-stop-messages.patch
+Patch151:      file-contents.patch
+Patch152:      slave_timeout_fix.patch
+Patch153:      utf8_general50_ci.patch
+Patch154:      bug813587.patch
+Patch155:      valgrind_zlib_suppression.patch
+Patch156:      memory_dynamic_rows.patch
+Patch157:      xtradb_bug317074.patch
+Patch158:      subunit.patch
+Patch159:      bug860910.patch
+Patch160:      bug45702.patch
 # </percona>
 URL:           http://www.mysql.com/products/community/
 BuildRequires: bison
@@ -624,6 +629,11 @@ cd ../..
 %patch153 -p1
 %patch154 -p1
 %patch155 -p1
+%patch156 -p1
+%patch157 -p1
+%patch158 -p1
+%patch159 -p1
+%patch160 -p1
 # </percona>
 
 # to get these files rebuild
@@ -746,6 +756,7 @@ mv $RPM_BUILD_ROOT%{_mandir}/man1/{,mysql_}resolve_stack_dump.1
 %{?debug:nm -n $RPM_BUILD_ROOT%{_sbindir}/mysqld > $RPM_BUILD_ROOT%{_datadir}/%{name}/mysqld.sym}
 
 # do not clobber users $PATH
+mv $RPM_BUILD_ROOT{%{_bindir},%{_sbindir}}/mysql_plugin
 mv $RPM_BUILD_ROOT{%{_bindir},%{_sbindir}}/mysql_upgrade
 mv $RPM_BUILD_ROOT{%{_bindir},%{_sbindir}}/innochecksum
 mv $RPM_BUILD_ROOT{%{_bindir},%{_sbindir}}/myisamchk
@@ -992,6 +1003,7 @@ done
 %attr(755,root,root) %{_sbindir}/myisamlog
 %attr(755,root,root) %{_sbindir}/myisampack
 #%attr(755,root,root) %{_sbindir}/mysql_fix_privilege_tables
+%attr(755,root,root) %{_sbindir}/mysql_plugin
 %attr(755,root,root) %{_sbindir}/mysql_upgrade
 %attr(755,root,root) %{_sbindir}/mysqlcheck
 %attr(755,root,root) %{_sbindir}/mysqld
@@ -1021,6 +1033,7 @@ done
 %{_mandir}/man1/myisamlog.1*
 %{_mandir}/man1/myisampack.1*
 #%{_mandir}/man1/mysql_fix_privilege_tables.1*
+%{_mandir}/man1/mysql_plugin.1*
 %{_mandir}/man1/mysql_upgrade.1*
 %{_mandir}/man1/mysqlcheck.1*
 %{_mandir}/man8/mysqld.8*
index e3e718b6519bcd82429da1edb605cfc47c3dab21..63c951aa3c37cef8bc5b80b390945982b8c52a45 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/scripts/mysql_install_db.sh
 +++ b/scripts/mysql_install_db.sh
-@@ -476,6 +476,9 @@
+@@ -481,6 +481,9 @@
    echo
    echo "Please report any problems with the $scriptdir/mysqlbug script!"
    echo
index 855340641fbdc9bbf144147b08bfed4fca59f96a..f4dd3dfbbb1edf692f7155d74caabc6f7804d45b 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/sql/sql_class.cc
 +++ b/sql/sql_class.cc
-@@ -2288,6 +2288,7 @@
+@@ -2308,6 +2308,7 @@
  
    thd->sent_row_count++;
    thd->sent_row_count_2++;
@@ -87,7 +87,7 @@
        if (schema_table_store_record(thd, table))
        {
          mysql_mutex_unlock(&LOCK_thread_count);
-@@ -8117,6 +8143,12 @@
+@@ -8140,6 +8166,12 @@
     SKIP_OPEN_TABLE},
    {"TIME_MS", MY_INT64_NUM_DECIMAL_DIGITS, MYSQL_TYPE_LONGLONG,
     0, 0, "Time_ms", SKIP_OPEN_TABLE},
index 827e0b32d541412f0bcf8dc54330de77375bf201..e8680d94c0c571d13bf16ed921cf046717d40fbe 100644 (file)
  
  class Reprepare_observer;
  class Relay_log_info;
-@@ -760,6 +763,9 @@
+@@ -764,6 +767,9 @@
      statement lifetime. FIXME: must be const
    */
     ulong id;
      MARK_COLUMNS_NONE:  Means mark_used_colums is not set and no indicator to
 --- a/sql/sys_vars.cc
 +++ b/sql/sys_vars.cc
-@@ -1786,6 +1786,11 @@
+@@ -1809,6 +1809,11 @@
         NO_MUTEX_GUARD, NOT_IN_BINLOG, ON_CHECK(0),
         ON_UPDATE(fix_query_cache_size));
  
 +--disconnect conn
 +DROP TABLE t;
 +SET GLOBAL query_cache_size=0;
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -491,6 +491,10 @@
+  The minimum size for blocks allocated by the query cache
+  --query-cache-size=# 
+  The memory allocated to store results from old queries
++ --query-cache-strip-comments 
++ Enable and disable optimisation "strip comment for query
++ cache" - optimisation strip all comments from query while
++ search query result in query cache
+  --query-cache-type=name 
+  OFF = Don't cache or retrieve results. ON = Cache all
+  results except SELECT SQL_NO_CACHE ... queries. DEMAND =
+@@ -928,6 +932,7 @@
+ query-cache-limit 1048576
+ query-cache-min-res-unit 4096
+ query-cache-size 0
++query-cache-strip-comments FALSE
+ query-cache-type ON
+ query-cache-wlock-invalidate FALSE
+ query-prealloc-size 8192
index c1b646e950ae3f3a0e59733d3bcb5157eafef8c5..76e6c5677dcf272854a372b3e9e3e41ca1ee0ded 100644 (file)
 +enable_query_log;
 --- /dev/null
 +++ b/mysql-test/include/query_response_time.inc
-@@ -0,0 +1,39 @@
+@@ -0,0 +1,43 @@
 +SET SESSION query_exec_time=0.1;
 +
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +EVAL SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=$base;
 +FLUSH QUERY_RESPONSE_TIME;
++# Following two queries check works of FLUSH and 
++# respecting of "QUERY_RESPONSE_TIME_STATS" variable (see launchpad bug #855312)
++SHOW QUERY_RESPONSE_TIME;
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +
 +SET SESSION query_exec_time=0.31; SELECT 1;
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        3             0.300000
++      0.125000        1             0.100000
 +      0.250000        0             0.000000
 +      0.500000        30           10.650000
 +      1.000000        3             1.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        4             0.400000
++      0.125000        1             0.100000
 +      0.250000        0             0.000000
 +      0.500000        30           10.650000
 +      1.000000        3             1.500000
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        3             0.300000
++      0.125000        1             0.100000
 +      0.250000        0             0.000000
 +      0.500000        30           10.650000
 +      1.000000        3             1.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        4             0.400000
++      0.125000        1             0.100000
 +      0.250000        0             0.000000
 +      0.500000        30           10.650000
 +      1.000000        3             1.500000
 +query_response_time_range_base        10
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        36           12.450000
++      1.000000        34           12.250000
 +     10.000000        33           77.099997
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        37           12.550000
++      1.000000        34           12.250000
 +     10.000000        33           77.099997
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +query_response_time_range_base        7
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        3             0.300000
++      0.142857        1             0.100000
 +      1.000000        33           12.150000
 +      7.000000        33           77.099997
 +     49.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        4             0.400000
++      0.142857        1             0.100000
 +      1.000000        33           12.150000
 +      7.000000        33           77.099997
 +     49.000000        0             0.000000
 +query_response_time_range_base        156
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000041        2             0.000000
++      0.000041        1             0.000000
 +      0.006410        0             0.000000
-+      1.000000        36           12.450000
++      1.000000        34           12.250000
 +    156.000000        33           77.099997
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000041        2             0.000000
++      0.000041        1             0.000000
 +      0.006410        0             0.000000
-+      1.000000        37           12.550000
++      1.000000        34           12.250000
 +    156.000000        33           77.099997
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.001000        0             0.000000
-+      1.000000        36           12.450000
++      1.000000        34           12.250000
 +   1000.000000        33           77.099997
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.001000        0             0.000000
-+      1.000000        37           12.550000
++      1.000000        34           12.250000
 +   1000.000000        33           77.099997
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.001000        0             0.000000
-+      1.000000        36           12.450000
++      1.000000        34           12.250000
 +   1000.000000        33           77.099997
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        2             0.000000
++      0.000001        1             0.000000
 +      0.001000        0             0.000000
-+      1.000000        37           12.550000
++      1.000000        34           12.250000
 +   1000.000000        33           77.099997
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SET GLOBAL query_exec_time=default;
 --- /dev/null
 +++ b/mysql-test/r/percona_query_response_time.result
-@@ -0,0 +1,1003 @@
+@@ -0,0 +1,1307 @@
 +SET SESSION query_exec_time=0.1;
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=1;
 +Warnings:
 +Warning       1292    Truncated incorrect query_response_time_range_base value: '1'
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.000003        0             0.000000
++      0.000007        0             0.000000
++      0.000015        0             0.000000
++      0.000030        0             0.000000
++      0.000061        0             0.000000
++      0.000122        0             0.000000
++      0.000244        0             0.000000
++      0.000488        0             0.000000
++      0.000976        0             0.000000
++      0.001953        0             0.000000
++      0.003906        0             0.000000
++      0.007812        0             0.000000
++      0.015625        0             0.000000
++      0.031250        0             0.000000
++      0.062500        0             0.000000
++      0.125000        0             0.000000
++      0.250000        0             0.000000
++      0.500000        0             0.000000
++      1.000000        0             0.000000
++      2.000000        0             0.000000
++      4.000000        0             0.000000
++      8.000000        0             0.000000
++     16.000000        0             0.000000
++     32.000000        0             0.000000
++     64.000000        0             0.000000
++    128.000000        0             0.000000
++    256.000000        0             0.000000
++    512.000000        0             0.000000
++   1024.000000        0             0.000000
++   2048.000000        0             0.000000
++   4096.000000        0             0.000000
++   8192.000000        0             0.000000
++  16384.000000        0             0.000000
++  32768.000000        0             0.000000
++  65536.000000        0             0.000000
++ 131072.000000        0             0.000000
++ 262144.000000        0             0.000000
++ 524288.000000        0             0.000000
++ 1048576.00000        0             0.000000
++ 2097152.00000        0             0.000000
++ 4194304.00000        0             0.000000
++ 8388608.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.000003        0             0.000000
++      0.000007        0             0.000000
++      0.000015        0             0.000000
++      0.000030        0             0.000000
++      0.000061        0             0.000000
++      0.000122        0             0.000000
++      0.000244        0             0.000000
++      0.000488        0             0.000000
++      0.000976        0             0.000000
++      0.001953        0             0.000000
++      0.003906        0             0.000000
++      0.007812        0             0.000000
++      0.015625        0             0.000000
++      0.031250        0             0.000000
++      0.062500        0             0.000000
++      0.125000        0             0.000000
++      0.250000        0             0.000000
++      0.500000        0             0.000000
++      1.000000        0             0.000000
++      2.000000        0             0.000000
++      4.000000        0             0.000000
++      8.000000        0             0.000000
++     16.000000        0             0.000000
++     32.000000        0             0.000000
++     64.000000        0             0.000000
++    128.000000        0             0.000000
++    256.000000        0             0.000000
++    512.000000        0             0.000000
++   1024.000000        0             0.000000
++   2048.000000        0             0.000000
++   4096.000000        0             0.000000
++   8192.000000        0             0.000000
++  16384.000000        0             0.000000
++  32768.000000        0             0.000000
++  65536.000000        0             0.000000
++ 131072.000000        0             0.000000
++ 262144.000000        0             0.000000
++ 524288.000000        0             0.000000
++ 1048576.00000        0             0.000000
++ 2097152.00000        0             0.000000
++ 4194304.00000        0             0.000000
++ 8388608.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        2             0.200000
++      0.125000        0             0.000000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        3             0.300000
++      0.125000        0             0.000000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=2;
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.000003        0             0.000000
++      0.000007        0             0.000000
++      0.000015        0             0.000000
++      0.000030        0             0.000000
++      0.000061        0             0.000000
++      0.000122        0             0.000000
++      0.000244        0             0.000000
++      0.000488        0             0.000000
++      0.000976        0             0.000000
++      0.001953        0             0.000000
++      0.003906        0             0.000000
++      0.007812        0             0.000000
++      0.015625        0             0.000000
++      0.031250        0             0.000000
++      0.062500        0             0.000000
++      0.125000        0             0.000000
++      0.250000        0             0.000000
++      0.500000        0             0.000000
++      1.000000        0             0.000000
++      2.000000        0             0.000000
++      4.000000        0             0.000000
++      8.000000        0             0.000000
++     16.000000        0             0.000000
++     32.000000        0             0.000000
++     64.000000        0             0.000000
++    128.000000        0             0.000000
++    256.000000        0             0.000000
++    512.000000        0             0.000000
++   1024.000000        0             0.000000
++   2048.000000        0             0.000000
++   4096.000000        0             0.000000
++   8192.000000        0             0.000000
++  16384.000000        0             0.000000
++  32768.000000        0             0.000000
++  65536.000000        0             0.000000
++ 131072.000000        0             0.000000
++ 262144.000000        0             0.000000
++ 524288.000000        0             0.000000
++ 1048576.00000        0             0.000000
++ 2097152.00000        0             0.000000
++ 4194304.00000        0             0.000000
++ 8388608.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.000003        0             0.000000
++      0.000007        0             0.000000
++      0.000015        0             0.000000
++      0.000030        0             0.000000
++      0.000061        0             0.000000
++      0.000122        0             0.000000
++      0.000244        0             0.000000
++      0.000488        0             0.000000
++      0.000976        0             0.000000
++      0.001953        0             0.000000
++      0.003906        0             0.000000
++      0.007812        0             0.000000
++      0.015625        0             0.000000
++      0.031250        0             0.000000
++      0.062500        0             0.000000
++      0.125000        0             0.000000
++      0.250000        0             0.000000
++      0.500000        0             0.000000
++      1.000000        0             0.000000
++      2.000000        0             0.000000
++      4.000000        0             0.000000
++      8.000000        0             0.000000
++     16.000000        0             0.000000
++     32.000000        0             0.000000
++     64.000000        0             0.000000
++    128.000000        0             0.000000
++    256.000000        0             0.000000
++    512.000000        0             0.000000
++   1024.000000        0             0.000000
++   2048.000000        0             0.000000
++   4096.000000        0             0.000000
++   8192.000000        0             0.000000
++  16384.000000        0             0.000000
++  32768.000000        0             0.000000
++  65536.000000        0             0.000000
++ 131072.000000        0             0.000000
++ 262144.000000        0             0.000000
++ 524288.000000        0             0.000000
++ 1048576.00000        0             0.000000
++ 2097152.00000        0             0.000000
++ 4194304.00000        0             0.000000
++ 8388608.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        2             0.200000
++      0.125000        0             0.000000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        3             0.300000
++      0.125000        0             0.000000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=10;
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.000010        0             0.000000
++      0.000100        0             0.000000
++      0.001000        0             0.000000
++      0.010000        0             0.000000
++      0.100000        0             0.000000
++      1.000000        0             0.000000
++     10.000000        0             0.000000
++    100.000000        0             0.000000
++   1000.000000        0             0.000000
++  10000.000000        0             0.000000
++ 100000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.000010        0             0.000000
++      0.000100        0             0.000000
++      0.001000        0             0.000000
++      0.010000        0             0.000000
++      0.100000        0             0.000000
++      1.000000        0             0.000000
++     10.000000        0             0.000000
++    100.000000        0             0.000000
++   1000.000000        0             0.000000
++  10000.000000        0             0.000000
++ 100000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        10
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        13            4.250000
++      1.000000        11            4.050000
 +     10.000000        11           25.699999
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        14            4.350000
++      1.000000        11            4.050000
 +     10.000000        11           25.699999
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=7;
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.000008        0             0.000000
++      0.000059        0             0.000000
++      0.000416        0             0.000000
++      0.002915        0             0.000000
++      0.020408        0             0.000000
++      0.142857        0             0.000000
++      1.000000        0             0.000000
++      7.000000        0             0.000000
++     49.000000        0             0.000000
++    343.000000        0             0.000000
++   2401.000000        0             0.000000
++  16807.000000        0             0.000000
++ 117649.000000        0             0.000000
++ 823543.000000        0             0.000000
++ 5764801.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.000008        0             0.000000
++      0.000059        0             0.000000
++      0.000416        0             0.000000
++      0.002915        0             0.000000
++      0.020408        0             0.000000
++      0.142857        0             0.000000
++      1.000000        0             0.000000
++      7.000000        0             0.000000
++     49.000000        0             0.000000
++    343.000000        0             0.000000
++   2401.000000        0             0.000000
++  16807.000000        0             0.000000
++ 117649.000000        0             0.000000
++ 823543.000000        0             0.000000
++ 5764801.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        7
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        2             0.200000
++      0.142857        0             0.000000
 +      1.000000        11            4.050000
 +      7.000000        11           25.699999
 +     49.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        3             0.300000
++      0.142857        0             0.000000
 +      1.000000        11            4.050000
 +      7.000000        11           25.699999
 +     49.000000        0             0.000000
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=156;
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000041        0             0.000000
++      0.006410        0             0.000000
++      1.000000        0             0.000000
++    156.000000        0             0.000000
++  24336.000000        0             0.000000
++ 3796416.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000041        0             0.000000
++      0.006410        0             0.000000
++      1.000000        0             0.000000
++    156.000000        0             0.000000
++  24336.000000        0             0.000000
++ 3796416.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        156
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000041        25            0.000000
++      0.000041        24            0.000000
 +      0.006410        0             0.000000
-+      1.000000        13            4.250000
++      1.000000        11            4.050000
 +    156.000000        11           25.699999
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000041        25            0.000000
++      0.000041        24            0.000000
 +      0.006410        0             0.000000
-+      1.000000        14            4.350000
++      1.000000        11            4.050000
 +    156.000000        11           25.699999
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=0;
 +SET GLOBAL QUERY_RESPONSE_TIME_RANGE_BASE=1000;
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.001000        0             0.000000
++      1.000000        0             0.000000
++   1000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.001000        0             0.000000
++      1.000000        0             0.000000
++   1000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.001000        0             0.000000
-+      1.000000        13            4.250000
++      1.000000        11            4.050000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.001000        0             0.000000
-+      1.000000        14            4.350000
++      1.000000        11            4.050000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +Warnings:
 +Warning       1292    Truncated incorrect query_response_time_range_base value: '1001'
 +FLUSH QUERY_RESPONSE_TIME;
++SHOW QUERY_RESPONSE_TIME;
++              
++      0.000001        0             0.000000
++      0.001000        0             0.000000
++      1.000000        0             0.000000
++   1000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
++SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
++time  count   total
++      0.000001        0             0.000000
++      0.001000        0             0.000000
++      1.000000        0             0.000000
++   1000.000000        0             0.000000
++ 1000000.00000        0             0.000000
++TOO LONG      0       TOO LONG
 +SET GLOBAL QUERY_RESPONSE_TIME_STATS=1;
 +SET SESSION query_exec_time=0.31;
 +SELECT 1;
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.001000        0             0.000000
-+      1.000000        13            4.250000
++      1.000000        11            4.050000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        25            0.000000
++      0.000001        24            0.000000
 +      0.001000        0             0.000000
-+      1.000000        14            4.350000
++      1.000000        11            4.050000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        46            4.600000
++      0.125000        44            4.400000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        47            4.700000
++      0.125000        44            4.400000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +query_response_time_range_base        2
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        46            4.600000
++      0.125000        44            4.400000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000003        0             0.000000
 +      0.000007        0             0.000000
 +      0.000015        0             0.000000
 +      0.015625        0             0.000000
 +      0.031250        0             0.000000
 +      0.062500        0             0.000000
-+      0.125000        47            4.700000
++      0.125000        44            4.400000
 +      0.250000        0             0.000000
 +      0.500000        10            3.550000
 +      1.000000        1             0.500000
 +query_response_time_range_base        10
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        57            8.650000
++      1.000000        55            8.450000
 +     10.000000        11           25.699999
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000010        0             0.000000
 +      0.000100        0             0.000000
 +      0.001000        0             0.000000
 +      0.010000        0             0.000000
 +      0.100000        0             0.000000
-+      1.000000        58            8.750000
++      1.000000        55            8.450000
 +     10.000000        11           25.699999
 +    100.000000        0             0.000000
 +   1000.000000        0             0.000000
 +query_response_time_range_base        7
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        46            4.600000
++      0.142857        44            4.400000
 +      1.000000        11            4.050000
 +      7.000000        11           25.699999
 +     49.000000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.000008        0             0.000000
 +      0.000059        0             0.000000
 +      0.000416        0             0.000000
 +      0.002915        0             0.000000
 +      0.020408        0             0.000000
-+      0.142857        47            4.700000
++      0.142857        44            4.400000
 +      1.000000        11            4.050000
 +      7.000000        11           25.699999
 +     49.000000        0             0.000000
 +query_response_time_range_base        156
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000041        46            0.000000
++      0.000041        45            0.000000
 +      0.006410        0             0.000000
-+      1.000000        57            8.650000
++      1.000000        55            8.450000
 +    156.000000        11           25.699999
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000041        46            0.000000
++      0.000041        45            0.000000
 +      0.006410        0             0.000000
-+      1.000000        58            8.750000
++      1.000000        55            8.450000
 +    156.000000        11           25.699999
 +  24336.000000        0             0.000000
 + 3796416.00000        0             0.000000
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.001000        0             0.000000
-+      1.000000        57            8.650000
++      1.000000        55            8.450000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.001000        0             0.000000
-+      1.000000        58            8.750000
++      1.000000        55            8.450000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +query_response_time_range_base        1000
 +SHOW QUERY_RESPONSE_TIME;
 +              
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.001000        0             0.000000
-+      1.000000        57            8.650000
++      1.000000        55            8.450000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
 +SELECT * FROM INFORMATION_SCHEMA.QUERY_RESPONSE_TIME;
 +time  count   total
-+      0.000001        46            0.000000
++      0.000001        45            0.000000
 +      0.001000        0             0.000000
-+      1.000000        58            8.750000
++      1.000000        55            8.450000
 +   1000.000000        11           25.699999
 + 1000000.00000        0             0.000000
 +TOO LONG      0       TOO LONG
    /* We have to initialize the storage engines before CSV logging */
    if (ha_init())
    {
-@@ -6909,6 +6921,11 @@
+@@ -6905,6 +6917,11 @@
  #else
    have_query_cache=SHOW_OPTION_NO;
  #endif
  #include "transaction.h"
  #include "sql_audit.h"
  #include "sql_prepare.h"
-@@ -1507,6 +1508,7 @@
+@@ -1507,6 +1508,12 @@
  
    ulonglong end_utime_of_query= thd->current_utime();
    ulonglong query_exec_time= get_query_exec_time(thd, end_utime_of_query);
-+  query_response_time_collect(query_exec_time);
++#ifdef HAVE_RESPONSE_TIME_DISTRIBUTION
++  if (opt_query_response_time_stats)
++  {
++    query_response_time_collect(query_exec_time);
++  }
++#endif
  
    /*
      Low long_query_time value most likely means user is debugging stuff and even
-@@ -1671,6 +1673,7 @@
+@@ -1671,6 +1678,7 @@
    case SCH_CHARSETS:
    case SCH_ENGINES:
    case SCH_COLLATIONS:
  #include "lock.h"                           // MYSQL_OPEN_IGNORE_FLUSH
  #include "debug_sync.h"
  #include "datadict.h"   // dd_frm_type()
-@@ -7865,6 +7866,14 @@
+@@ -7888,6 +7889,14 @@
  
  */
  
  ST_SCHEMA_TABLE schema_tables[]=
  {
    {"CHARACTER_SETS", charsets_fields_info, create_schema_table, 
-@@ -7918,6 +7927,13 @@
+@@ -7941,6 +7950,13 @@
     1, 9, 0, OPTIMIZE_I_S_TABLE|OPEN_TABLE_ONLY},
    {"ROUTINES", proc_fields_info, create_schema_table, 
     fill_schema_proc, make_proc_old_format, 0, -1, -1, 0, 0},
  %token  QUICK
  %token  RANGE_SYM                     /* SQL-2003-R */
  %token  READS_SYM                     /* SQL-2003-R */
-@@ -11080,6 +11081,15 @@
+@@ -11099,6 +11100,15 @@
            {
              Lex->sql_command = SQLCOM_SHOW_SLAVE_STAT;
            }
          | CREATE PROCEDURE_SYM sp_name
            {
              LEX *lex= Lex;
-@@ -11316,6 +11326,12 @@
-           { Lex->type|= REFRESH_STATUS; }
-         | SLAVE
-           { Lex->type|= REFRESH_SLAVE; }
+@@ -11338,6 +11348,12 @@
+             Lex->type|= REFRESH_SLAVE;
+             Lex->reset_slave_info.all= false;
+           }
 +        | QUERY_RESPONSE_TIME_SYM
 +          { 
 +#ifdef HAVE_RESPONSE_TIME_DISTRIBUTION
          | MASTER_SYM
            { Lex->type|= REFRESH_MASTER; }
          | DES_KEY_FILE
-@@ -12617,6 +12633,7 @@
+@@ -12645,6 +12661,7 @@
          | PROXY_SYM                {}
          | QUARTER_SYM              {}
          | QUERY_SYM                {}
 @@ -0,0 +1,2 @@
 +Variable_name Value
 +have_response_time_distribution       YES
---- a/include/atomic/x86-gcc.h 2011-05-11 14:54:11.000000000 +0300
-+++ b/include/atomic/x86-gcc.h 2011-07-21 16:20:24.563057000 +0300
+--- a/include/atomic/x86-gcc.h
++++ b/include/atomic/x86-gcc.h
 @@ -108,27 +108,22 @@
    v=tmp;
  
  #endif
  
  /*
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -503,6 +503,12 @@
+  Invalidate queries in query cache on LOCK for write
+  --query-prealloc-size=# 
+  Persistent buffer for query parsing and execution
++ --query-response-time-range-base=# 
++ Select base of log for query_response_time ranges.
++ WARNING: variable change affect only after flush
++ --query-response-time-stats 
++ Enable or disable query response time statisics
++ collecting
+  --range-alloc-block-size=# 
+  Allocation block size for storing ranges during
+  optimization
+@@ -936,6 +942,8 @@
+ query-cache-type ON
+ query-cache-wlock-invalidate FALSE
+ query-prealloc-size 8192
++query-response-time-range-base 10
++query-response-time-stats FALSE
+ range-alloc-block-size 4096
+ read-buffer-size 131072
+ read-only FALSE
index 9ed13a967a89d9d7db62b734f5346615503b07bc..279611cbba6ded9be8e8878165652b61f60e2dcd 100644 (file)
@@ -47,7 +47,7 @@
      in "struct show_var_st status_vars[]= {" ...
 --- a/sql/sql_parse.cc
 +++ b/sql/sql_parse.cc
-@@ -335,6 +335,7 @@
+@@ -336,6 +336,7 @@
    sql_command_flags[SQLCOM_SHOW_CREATE]=  CF_STATUS_COMMAND;
    sql_command_flags[SQLCOM_SHOW_MASTER_STAT]= CF_STATUS_COMMAND;
    sql_command_flags[SQLCOM_SHOW_SLAVE_STAT]=  CF_STATUS_COMMAND;
@@ -55,7 +55,7 @@
    sql_command_flags[SQLCOM_SHOW_CREATE_PROC]= CF_STATUS_COMMAND;
    sql_command_flags[SQLCOM_SHOW_CREATE_FUNC]= CF_STATUS_COMMAND;
    sql_command_flags[SQLCOM_SHOW_CREATE_TRIGGER]=  CF_STATUS_COMMAND;
-@@ -2359,12 +2360,16 @@
+@@ -2368,12 +2369,17 @@
      mysql_mutex_unlock(&LOCK_active_mi);
      break;
    }
      if (check_global_access(thd, SUPER_ACL | REPL_CLIENT_ACL))
        goto error;
 -    mysql_mutex_lock(&LOCK_active_mi);
-+    if(SQLCOM_SHOW_SLAVE_NOLOCK_STAT != lex->sql_command)
++    bool do_lock=SQLCOM_SHOW_SLAVE_NOLOCK_STAT != lex->sql_command;
++    if(do_lock)
 +    {
 +      mysql_mutex_lock(&LOCK_active_mi);
 +    }
      if (active_mi != NULL)
      {
        res = show_master_info(thd, active_mi);
-@@ -2375,7 +2380,10 @@
+@@ -2384,7 +2390,19 @@
                     WARN_NO_MASTER_INFO, ER(WARN_NO_MASTER_INFO));
        my_ok(thd);
      }
 -    mysql_mutex_unlock(&LOCK_active_mi);
-+    if(SQLCOM_SHOW_SLAVE_NOLOCK_STAT != lex->sql_command)
++    if(do_lock)
 +    {
 +      mysql_mutex_unlock(&LOCK_active_mi);
 +    }
++    DBUG_EXECUTE_IF("after_show_slave_status",
++                    {
++                      const char act[]=
++                        "now "
++                        "signal signal.after_show_slave_status";
++                      DBUG_ASSERT(opt_debug_sync_timeout > 0);
++                      DBUG_ASSERT(!debug_sync_set_action(current_thd,
++                                                         STRING_WITH_LEN(act)));
++                    };);
      break;
    }
    case SQLCOM_SHOW_MASTER_STAT:
  %token  STDDEV_SAMP_SYM               /* SQL-2003-N */
  %token  STD_SYM
  %token  STOP_SYM
-@@ -11086,6 +11087,10 @@
+@@ -11105,6 +11106,11 @@
            {
              Lex->sql_command = SQLCOM_SHOW_SLAVE_STAT;
            }
++      /* SHOW SLAVE STATUS NOLOCK */
 +        | SLAVE STATUS_SYM NOLOCK_SYM
 +          {
 +          Lex->sql_command = SQLCOM_SHOW_SLAVE_NOLOCK_STAT; //SQLCOM_SHOW_SLAVE_NOLOCK_STAT;
           {
  #ifdef HAVE_RESPONSE_TIME_DISTRIBUTION
 --- /dev/null
++++ b/mysql-test/t/percona_show_slave_status_nolock.test
+@@ -0,0 +1,90 @@
++--source include/master-slave.inc
++--source include/have_debug_sync.inc
++--source include/have_binlog_format_statement.inc
++
++call mtr.add_suppression("Slave SQL: Request to stop slave SQL Thread received while applying a group that has non-transactional changes");
++
++--let $rpl_connection_name=slave_lock
++--let $rpl_server_number=2
++--source include/rpl_connect.inc
++
++--let $rpl_connection_name=slave_nolock
++--let $rpl_server_number=2
++--source include/rpl_connect.inc
++
++--let $show_statement= SHOW PROCESSLIST
++--let $field= Info
++
++connection master;
++--echo [master]
++--disable_warnings
++DROP TABLE IF EXISTS t;
++--enable_warnings
++CREATE TABLE t(id INT);
++sync_slave_with_master;
++
++connection slave;
++--echo [slave]
++SET DEBUG_SYNC='RESET';
++SET GLOBAL DEBUG="+d,after_mysql_insert,after_show_slave_status";
++
++connection master;
++--echo [master]
++INSERT INTO t VALUES(0);
++
++connection slave;
++--echo [slave]
++--let $condition= 'INSERT INTO t VALUES(0)'
++--source include/wait_show_condition.inc
++
++--echo check 'SHOW SLAVE STATUS' and 'SHOW SLAVE STATUS NOLOCK' - both should work fine
++--source include/percona_show_slave_status_nolock.inc
++
++connection master;
++--echo [master]
++INSERT INTO t VALUES(1);
++
++connection slave;
++--echo [slave]
++--let $condition= 'INSERT INTO t VALUES(1)'
++--source include/wait_show_condition.inc
++
++--let $rpl_connection_name=slave_stop
++--let $rpl_server_number=2
++--source include/rpl_connect.inc
++
++connection slave_stop;
++--echo [slave_stop]
++send STOP SLAVE;
++
++connection slave;
++--echo [slave]
++--let $condition= 'STOP SLAVE'
++--source include/wait_show_condition.inc
++
++--echo check 'SHOW SLAVE STATUS' and 'SHOW SLAVE STATUS NOLOCK' - just NOLOCK version should works fine
++--source include/percona_show_slave_status_nolock.inc
++
++
++connection slave_stop;
++--echo [slave_stop]
++reap;
++--source include/wait_for_slave_to_stop.inc
++START SLAVE;
++--source include/wait_for_slave_to_start.inc
++
++connection master;
++--echo [master]
++SET DEBUG_SYNC='RESET';
++
++connection slave;
++--echo [slave]
++SET GLOBAL DEBUG='';
++SET DEBUG_SYNC='RESET';
++
++connection master;
++--echo [master]
++DROP TABLE t;
++sync_slave_with_master;
++
++--source include/rpl_end.inc
+--- /dev/null
 +++ b/mysql-test/r/percona_show_slave_status_nolock.result
-@@ -0,0 +1,21 @@
+@@ -0,0 +1,69 @@
 +include/master-slave.inc
 +[connection master]
++call mtr.add_suppression("Slave SQL: Request to stop slave SQL Thread received while applying a group that has non-transactional changes");
++include/rpl_connect.inc [creating slave_lock]
++include/rpl_connect.inc [creating slave_nolock]
++[master]
 +DROP TABLE IF EXISTS t;
 +CREATE TABLE t(id INT);
-+INSERT INTO t SELECT SLEEP(10);
++[slave]
++SET DEBUG_SYNC='RESET';
++SET GLOBAL DEBUG="+d,after_mysql_insert,after_show_slave_status";
++[master]
++INSERT INTO t VALUES(0);
++[slave]
++check 'SHOW SLAVE STATUS' and 'SHOW SLAVE STATUS NOLOCK' - both should work fine
++
++[slave_lock]
++SHOW SLAVE STATUS;
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++SIGNAL after SHOW SLAVE STATUS is 'signal.after_show_slave_status'
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
++[slave_nolock]
++SHOW SLAVE STATUS NOLOCK;
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++# should be 'signal.after_show_slave_status'
++SIGNAL after SHOW SLAVE STATUS NOLOCK is 'signal.after_show_slave_status'
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.continue';
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
++
++[master]
++INSERT INTO t VALUES(1);
++[slave]
++include/rpl_connect.inc [creating slave_stop]
++[slave_stop]
 +STOP SLAVE;
-+Warnings:
-+Note  1592    Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave.
-+master        count(*)
-+master        1
-+slave count(*)
-+slave 0
++[slave]
++check 'SHOW SLAVE STATUS' and 'SHOW SLAVE STATUS NOLOCK' - just NOLOCK version should works fine
++
++[slave_lock]
++SHOW SLAVE STATUS;
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++SIGNAL after SHOW SLAVE STATUS is 'signal.empty'
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
++[slave_nolock]
 +SHOW SLAVE STATUS NOLOCK;
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++# should be 'signal.after_show_slave_status'
++SIGNAL after SHOW SLAVE STATUS NOLOCK is 'signal.after_show_slave_status'
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.continue';
++[slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
++
++[slave_stop]
 +include/wait_for_slave_to_stop.inc
 +START SLAVE;
 +include/wait_for_slave_to_start.inc
-+slave count(*)
-+slave 1
++[master]
++SET DEBUG_SYNC='RESET';
++[slave]
++SET GLOBAL DEBUG='';
++SET DEBUG_SYNC='RESET';
++[master]
 +DROP TABLE t;
-+STOP SLAVE;
-+include/wait_for_slave_to_stop.inc
++include/rpl_end.inc
 --- /dev/null
-+++ b/mysql-test/t/percona_show_slave_status_nolock.test
-@@ -0,0 +1,53 @@
-+--source include/master-slave.inc
-+--source include/have_binlog_format_statement.inc
-+--disable_query_log
-+call mtr.add_suppression("Unsafe statement written to the binary log using statement format since BINLOG_FORMAT = STATEMENT. Statement is unsafe because it uses a system function that may return a different value on the slave. Statement:");
-+call mtr.add_suppression("Slave SQL.*Request to stop slave SQL Thread received while applying a group that has non-transactional changes; waiting for completion of the group");
-+--enable_query_log
-+connection master;
-+  --disable_warnings
-+  DROP TABLE IF EXISTS t;
-+  --enable_warnings
-+  CREATE TABLE t(id INT);
-+  sync_slave_with_master;
++++ b/mysql-test/include/percona_show_slave_status_nolock.inc
+@@ -0,0 +1,56 @@
++--echo
++--disable_result_log
++connection slave_lock;
++--echo [slave_lock]
++send SHOW SLAVE STATUS;
 +
-+connection master;
-+  send INSERT INTO t SELECT SLEEP(10);
++connection slave;
++--let $condition= 'SHOW SLAVE STATUS'
++--source include/wait_show_condition.inc
++
++--disable_warnings
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++--enable_warnings
++
++--let current=`SELECT SUBSTR(Variable_value FROM 22) FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE Variable_name = 'DEBUG_SYNC'`
++--echo SIGNAL after SHOW SLAVE STATUS is $current
 +
 +connection slave;
-+  sleep 15;
-+  send STOP SLAVE;
++--echo [slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
 +
-+connection master;
-+  reap;
++connection slave_nolock;
++--echo [slave_nolock]
++send SHOW SLAVE STATUS NOLOCK;
 +
-+  --disable_query_log
-+  select "master",count(*) from t;
-+  --enable_query_log
++connection slave;
++--let $condition= 'SHOW SLAVE STATUS NOLOCK'
++--source include/wait_show_condition.inc
 +
-+connection slave1;
-+  --disable_query_log
-+  select "slave",count(*) from t;
-+  --enable_query_log
++--disable_warnings
++SET DEBUG_SYNC='now WAIT_FOR signal.after_show_slave_status TIMEOUT 1';
++--enable_warnings
 +
-+  --disable_result_log
-+  SHOW SLAVE STATUS NOLOCK;
-+  --enable_result_log
++--echo # should be 'signal.after_show_slave_status'
++--let current=`SELECT SUBSTR(Variable_value FROM 22) FROM INFORMATION_SCHEMA.SESSION_VARIABLES WHERE Variable_name = 'DEBUG_SYNC'`
++--echo SIGNAL after SHOW SLAVE STATUS NOLOCK is $current
 +
 +connection slave;
-+  reap;
++--echo [slave]
++SET DEBUG_SYNC='now SIGNAL signal.continue';
 +
-+  --source include/wait_for_slave_to_stop.inc
-+  START SLAVE;
-+  --source include/wait_for_slave_to_start.inc
++connection slave_lock;
++--disable_result_log
++reap;
++--enable_result_log
 +
-+  --disable_query_log
-+  select "slave",count(*) from t;
-+  --enable_query_log
++connection slave_nolock;
++--disable_result_log
++reap;
++--enable_result_log
 +
-+connection master;
-+  DROP TABLE t;
-+sync_slave_with_master;
-+STOP SLAVE;
-+--source include/wait_for_slave_to_stop.inc
-+ 
-\ No newline at end of file
++connection slave;
++--echo [slave]
++SET DEBUG_SYNC='now SIGNAL signal.empty';
++--enable_result_log
++--echo
+--- a/sql/slave.cc
++++ b/sql/slave.cc
+@@ -1816,6 +1816,7 @@
+   if (mi->host[0])
+   {
++    bool do_lock=SQLCOM_SHOW_SLAVE_NOLOCK_STAT != thd->lex->sql_command;
+     DBUG_PRINT("info",("host is set: '%s'", mi->host));
+     String *packet= &thd->packet;
+     protocol->prepare_for_resend();
+@@ -1824,9 +1825,15 @@
+       slave_running can be accessed without run_lock but not other
+       non-volotile members like mi->io_thd, which is guarded by the mutex.
+     */
+-    mysql_mutex_lock(&mi->run_lock);
++    if (do_lock)
++    {
++      mysql_mutex_lock(&mi->run_lock);
++    }
+     protocol->store(mi->io_thd ? mi->io_thd->proc_info : "", &my_charset_bin);
+-    mysql_mutex_unlock(&mi->run_lock);
++    if (do_lock)
++    {
++      mysql_mutex_unlock(&mi->run_lock);
++    }
+     mysql_mutex_lock(&mi->data_lock);
+     mysql_mutex_lock(&mi->rli.data_lock);
index 01189cfeb99540ba078600375bd8211d6134f36f..d67f05644535c2d60da9e85aa0244b51d3e1f685 100644 (file)
@@ -88,7 +88,7 @@
    case SQLCOM_SHOW_TRIGGERS:
    case SQLCOM_SHOW_TABLE_STATUS:
    case SQLCOM_SHOW_OPEN_TABLES:
-@@ -4846,6 +4852,8 @@
+@@ -4852,6 +4858,8 @@
  
    case SCH_TABLE_NAMES:
    case SCH_TABLES:
    case SQLCOM_SHOW_TRIGGERS:
    case SQLCOM_SHOW_EVENTS:
      thd->make_lex_string(&lookup_field_values->db_value, 
-@@ -3279,6 +3280,231 @@
+@@ -3283,6 +3284,231 @@
    return (uint) OPEN_FULL_TABLE;
  }
  
  
  /**
     Try acquire high priority share metadata lock on a table (with
-@@ -7023,6 +7249,25 @@
+@@ -7046,6 +7272,25 @@
    {0, 0, MYSQL_TYPE_STRING, 0, 0, 0, SKIP_OPEN_TABLE}
  };
  
  
  ST_FIELD_INFO columns_fields_info[]=
  {
-@@ -7637,6 +7882,9 @@
+@@ -7660,6 +7905,9 @@
     hton_fill_schema_table, 0, 0, -1, -1, 0, 0},
    {"GLOBAL_STATUS", variables_fields_info, create_schema_table,
     fill_status, make_old_format, 0, 0, -1, 0, 0},
    {"GLOBAL_VARIABLES", variables_fields_info, create_schema_table,
     fill_variables, make_old_format, 0, 0, -1, 0, 0},
    {"KEY_COLUMN_USAGE", key_column_usage_fields_info, create_schema_table,
-@@ -7686,6 +7934,9 @@
+@@ -7709,6 +7957,9 @@
     get_all_tables, make_table_names_old_format, 0, 1, 2, 1, 0},
    {"TABLE_PRIVILEGES", table_privileges_fields_info, create_schema_table,
     fill_schema_table_privileges, 0, 0, -1, -1, 0, 0},
     OPEN_TRIGGER_ONLY|OPTIMIZE_I_S_TABLE},
 --- a/sql/sql_yacc.yy
 +++ b/sql/sql_yacc.yy
-@@ -10873,6 +10873,15 @@
+@@ -10892,6 +10892,15 @@
               if (prepare_schema_table(YYTHD, lex, 0, SCH_TABLE_NAMES))
                 MYSQL_YYABORT;
             }
    key_LOCK_connection_count, key_LOCK_crypt, key_LOCK_delayed_create,
 --- a/sql/sql_base.cc
 +++ b/sql/sql_base.cc
-@@ -1588,12 +1588,16 @@
+@@ -1651,12 +1651,16 @@
    if (!mysql_bin_log.is_open())
    {
      TABLE *tmp_next;
      DBUG_RETURN(FALSE);
    }
  
-@@ -1606,6 +1610,8 @@
+@@ -1669,6 +1673,8 @@
  
    memcpy(buf, stub, stub_len);
  
    /*
      Insertion sort of temp tables by pseudo_thread_id to build ordered list
      of sublists of equal pseudo_thread_id
-@@ -1727,6 +1733,8 @@
+@@ -1790,6 +1796,8 @@
      thd->variables.option_bits&= ~OPTION_QUOTE_SHOW_CREATE; /* restore option */
    thd->temporary_tables=0;
  
    DBUG_RETURN(error);
  }
  
-@@ -2104,6 +2112,8 @@
+@@ -2167,6 +2175,8 @@
                            table->s->db.str, table->s->table_name.str,
                            (long) table, table->alias));
  
    if (table->prev)
    {
      table->prev->next= table->next;
-@@ -2130,6 +2140,9 @@
+@@ -2193,6 +2203,9 @@
      slave_open_temp_tables--;
    }
    close_temporary(table, free_share, delete_table);
    DBUG_VOID_RETURN;
  }
  
-@@ -5854,6 +5867,7 @@
+@@ -5931,6 +5944,7 @@
    if (add_to_temporary_tables_list)
    {
      /* growing temp list at the head */
      tmp_table->next= thd->temporary_tables;
      if (tmp_table->next)
        tmp_table->next->prev= tmp_table;
-@@ -5861,6 +5875,7 @@
+@@ -5938,6 +5952,7 @@
      thd->temporary_tables->prev= 0;
      if (thd->slave_thread)
        slave_open_temp_tables++;
    DBUG_PRINT("tmptable", ("opened table: '%s'.'%s' 0x%lx", tmp_table->s->db.str,
 --- a/sql/sql_class.cc
 +++ b/sql/sql_class.cc
-@@ -837,6 +837,8 @@
+@@ -836,6 +836,8 @@
    active_vio = 0;
  #endif
    mysql_mutex_init(key_LOCK_thd_data, &LOCK_thd_data, MY_MUTEX_INIT_FAST);
  
    /* Variables with default values */
    proc_info="login";
-@@ -1349,6 +1351,7 @@
+@@ -1348,6 +1350,7 @@
    db= NULL;
    free_root(&transaction.mem_root,MYF(0));
    mysql_mutex_destroy(&LOCK_thd_data);
index d0ab66d13a3e555f3fa0e0aa12f69e4c93e54af3..f1cbd37b2dd4aeaf2a3373ffa0542dba0ef5829b 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/include/mysql/plugin_audit.h.pp
 +++ b/include/mysql/plugin_audit.h.pp
-@@ -185,6 +185,16 @@
+@@ -186,6 +186,16 @@
  char *thd_security_context(void* thd, char *buffer, unsigned int length,
                             unsigned int max_query_len);
  void thd_inc_row_count(void* thd);
@@ -26,7 +26,7 @@
  unsigned long thd_get_thread_id(const void* thd);
 --- a/include/mysql/plugin_auth.h.pp
 +++ b/include/mysql/plugin_auth.h.pp
-@@ -185,6 +185,16 @@
+@@ -186,6 +186,16 @@
  char *thd_security_context(void* thd, char *buffer, unsigned int length,
                             unsigned int max_query_len);
  void thd_inc_row_count(void* thd);
@@ -45,7 +45,7 @@
  unsigned long thd_get_thread_id(const void* thd);
 --- a/include/mysql/plugin_ftparser.h.pp
 +++ b/include/mysql/plugin_ftparser.h.pp
-@@ -138,6 +138,16 @@
+@@ -139,6 +139,16 @@
  char *thd_security_context(void* thd, char *buffer, unsigned int length,
                             unsigned int max_query_len);
  void thd_inc_row_count(void* thd);
@@ -64,7 +64,7 @@
  unsigned long thd_get_thread_id(const void* thd);
 --- a/include/mysql/plugin.h
 +++ b/include/mysql/plugin.h
-@@ -536,6 +536,17 @@
+@@ -545,6 +545,17 @@
  /* Increments the row counter, see THD::row_count */
  void thd_inc_row_count(MYSQL_THD thd);
  
    /*
 --- a/sql/filesort.cc
 +++ b/sql/filesort.cc
-@@ -195,6 +195,7 @@
+@@ -193,6 +193,7 @@
    {
      status_var_increment(thd->status_var.filesort_scan_count);
    }
  #ifdef CAN_TRUST_RANGE
    if (select && select->quick && select->quick->records > 0L)
    {
-@@ -260,6 +261,7 @@
-   }
-   else
-   {
+@@ -261,6 +262,7 @@
+     /* filesort cannot handle zero-length records during merge. */
+     DBUG_ASSERT(param.sort_length != 0);
 +    thd->query_plan_flags|= QPLAN_FILESORT_DISK;
      if (table_sort.buffpek && table_sort.buffpek_len < maxbuffer)
      {
        my_free(table_sort.buffpek);
-@@ -1219,6 +1221,7 @@
+@@ -1209,6 +1211,7 @@
    DBUG_ENTER("merge_buffers");
  
    status_var_increment(current_thd->status_var.filesort_merge_passes);
  my_bool lower_case_file_system= 0;
  my_bool opt_large_pages= 0;
  my_bool opt_super_large_pages= 0;
-@@ -5896,10 +5900,10 @@
-    "Log slow OPTIMIZE, ANALYZE, ALTER and other administrative statements to "
-    "the slow log if it is open.", &opt_log_slow_admin_statements,
-    &opt_log_slow_admin_statements, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
+@@ -5892,14 +5896,10 @@
+    "Don't log extra information to update and slow-query logs.",
+    &opt_short_log_format, &opt_short_log_format,
+    0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
+-  {"log-slow-admin-statements", 0,
+-   "Log slow OPTIMIZE, ANALYZE, ALTER and other administrative statements to "
+-   "the slow log if it is open.", &opt_log_slow_admin_statements,
+-   &opt_log_slow_admin_statements, 0, GET_BOOL, NO_ARG, 0, 0, 0, 0, 0, 0},
 - {"log-slow-slave-statements", 0,
 + /*{"log-slow-slave-statements", 0,
    "Log slow statements executed by slave thread to the slow log if it is open.",
    {"log-slow-queries", OPT_SLOW_QUERY_LOG,
     "Log slow queries to a table or log file. Defaults logging to table "
     "mysql.slow_log or hostname-slow.log if --log-output=file is used. "
-@@ -7288,6 +7292,10 @@
+@@ -7288,6 +7288,10 @@
  
  C_MODE_END
  
  /**
    Get server options from the command line,
    and perform related server initializations.
-@@ -7437,6 +7445,8 @@
+@@ -7437,6 +7441,8 @@
    global_system_variables.long_query_time= (ulonglong)
      (global_system_variables.long_query_time_double * 1e6);
  
  
  /**
    Dumps a text description of a thread, its security context
-@@ -912,6 +943,7 @@
-     *cond_hdl= NULL;
-     return FALSE;
-   }
+@@ -926,6 +957,8 @@
+                            const char* msg,
+                            MYSQL_ERROR ** cond_hdl)
+ {
 +  last_errno= sql_errno;
-   for (Internal_error_handler *error_handler= m_internal_handler;
-        error_handler;
-@@ -3656,6 +3688,12 @@
++
+   if (!m_internal_handler)
+   {
+     *cond_hdl= NULL;
+@@ -3675,6 +3708,12 @@
      first_successful_insert_id_in_prev_stmt;
    backup->first_successful_insert_id_in_cur_stmt= 
      first_successful_insert_id_in_cur_stmt;
  
    if ((!lex->requires_prelocking() || is_update_query(lex->sql_command)) &&
        !is_current_stmt_binlog_format_row())
-@@ -3676,6 +3714,14 @@
+@@ -3695,6 +3734,14 @@
    cuted_fields= 0;
    transaction.savepoints= 0;
    first_successful_insert_id_in_cur_stmt= 0;
  }
  
  
-@@ -3738,6 +3784,12 @@
+@@ -3757,6 +3804,12 @@
    */
    examined_row_count+= backup->examined_row_count;
    cuted_fields+=       backup->cuted_fields;
    /*
      Reset warning count for each query that uses tables
      A better approach would be to reset this for any commands
-@@ -5297,6 +5390,21 @@
+@@ -5303,6 +5396,21 @@
    thd->rand_used= 0;
    thd->sent_row_count= thd->examined_row_count= 0;
  
  static bool fix_low_prio_updates(sys_var *self, THD *thd, enum_var_type type)
  {
    if (type == OPT_SESSION)
-@@ -2898,6 +2921,117 @@
+@@ -2898,6 +2921,123 @@
         DEFAULT(FALSE), NO_MUTEX_GUARD, NOT_IN_BINLOG, ON_CHECK(0),
         ON_UPDATE(fix_log_state));
  
 +       "Log queries replayed be the slave SQL thread",
 +       GLOBAL_VAR(opt_log_slow_slave_statements), CMD_LINE(OPT_ARG),
 +       DEFAULT(FALSE));
++static Sys_var_mybool Sys_log_slow_admin_statements(
++       "log_slow_admin_statements",
++       "Log slow OPTIMIZE, ANALYZE, ALTER and other administrative statements"
++       " to the slow log if it is open.",
++       GLOBAL_VAR(opt_log_slow_admin_statements), CMD_LINE(OPT_ARG),
++       DEFAULT(FALSE));
 +static Sys_var_mybool Sys_log_slow_sp_statements(
 +       "log_slow_sp_statements",
 +       "Log slow statements executed by stored procedure to the slow log if it is open.",
 +DROP TABLE t;
 --- a/sql/log_event.cc
 +++ b/sql/log_event.cc
-@@ -2380,6 +2380,14 @@
+@@ -2385,6 +2385,14 @@
        start+= host.length;
      }
    }
    /*
      NOTE: When adding new status vars, please don't forget to update
      the MAX_SIZE_LOG_EVENT_STATUS in log_event.h and update the function
-@@ -2866,6 +2874,17 @@
+@@ -2871,6 +2879,17 @@
        data_written= master_data_written= uint4korr(pos);
        pos+= 4;
        break;
 +
 +SET GLOBAL query_exec_time=default;
 +SET SESSION query_exec_time=default;
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_global_control_default.result
+@@ -0,0 +1 @@
++SET GLOBAL slow_query_log_use_global_control=default;
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_global_control_default.test
+@@ -0,0 +1 @@
++SET GLOBAL slow_query_log_use_global_control=default;
+--- /dev/null
++++ b/mysql-test/r/percona_slow_extended_log_error.result
+@@ -0,0 +1,9 @@
++SET long_query_time=0;
++DROP TABLE IF EXISTS t1;
++CREATE TABLE t(a INT);
++[log_start.inc] percona.slow_extended.log_error
++CREATE TABLE t(a INT);
++ERROR 42S01: Table 't' already exists
++[log_stop.inc] percona.slow_extended.log_error
++[log_grep.inc] file: percona.slow_extended.log_error pattern: Last_errno: 1050
++[log_grep.inc] lines:   1
+--- /dev/null
++++ b/mysql-test/t/percona_slow_extended_log_error.test
+@@ -0,0 +1,15 @@
++--let log_file=percona.slow_extended.log_error
++SET long_query_time=0;
++--disable_warnings
++DROP TABLE IF EXISTS t1;
++--enable_warnings
++CREATE TABLE t(a INT);
++--source include/log_start.inc
++
++--error ER_TABLE_EXISTS_ERROR
++CREATE TABLE t(a INT);
++
++--source include/log_stop.inc
++--let grep_pattern = Last_errno: 1050
++--source include/log_grep.inc
++DROP TABLE t;
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/t/log_slow_admin_statements_basic.test
+@@ -0,0 +1 @@
++SELECT @@global.log_slow_admin_statements;
+--- /dev/null
++++ b/mysql-test/suite/sys_vars/r/log_slow_admin_statements_basic.result
+@@ -0,0 +1,3 @@
++SELECT @@global.log_slow_admin_statements;
++@@global.log_slow_admin_statements
++0
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_admin_statements.result
+@@ -0,0 +1,35 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
++SET GLOBAL log_slow_admin_statements=true;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     ON
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     ON
++SET GLOBAL log_slow_admin_statements=false;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
++SET GLOBAL log_slow_admin_statements=foo;
++ERROR 42000: Variable 'log_slow_admin_statements' can't be set to the value of 'foo'
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
++SET GLOBAL log_slow_admin_statements=default;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_admin_statements-config_false.result
+@@ -0,0 +1,6 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_admin_statements-config_foo.result
+@@ -0,0 +1,7 @@
++call mtr.add_suppression("option 'log_slow_admin_statements': boolean value 'foo' wasn't recognized. Set to OFF.");
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     OFF
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     OFF
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_admin_statements-config_true.result
+@@ -0,0 +1,6 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     ON
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     ON
+--- /dev/null
++++ b/mysql-test/r/percona_log_slow_admin_statements-config.result
+@@ -0,0 +1,6 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++Variable_name Value
++log_slow_admin_statements     ON
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++VARIABLE_NAME VARIABLE_VALUE
++LOG_SLOW_ADMIN_STATEMENTS     ON
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_false.cnf
+@@ -0,0 +1,2 @@
++[mysqld.1]
++log-slow-admin-statements=false
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_foo.cnf
+@@ -0,0 +1,2 @@
++[mysqld.1]
++log-slow-admin-statements=foo
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_true.cnf
+@@ -0,0 +1,2 @@
++[mysqld.1]
++log-slow-admin-statements=true
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config.cnf
+@@ -0,0 +1,2 @@
++[mysqld.1]
++log-slow-admin-statements
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements.test
+@@ -0,0 +1,20 @@
++# default value
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++# set value to 'true'
++SET GLOBAL log_slow_admin_statements=true;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++# set value to 'false'
++SET GLOBAL log_slow_admin_statements=false;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++# set value to 'foo'
++--error ER_WRONG_VALUE_FOR_VAR
++SET GLOBAL log_slow_admin_statements=foo;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
++# set value to default
++SET GLOBAL log_slow_admin_statements=default;
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_false.test
+@@ -0,0 +1,2 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_foo.test
+@@ -0,0 +1,3 @@
++call mtr.add_suppression("option 'log_slow_admin_statements': boolean value 'foo' wasn't recognized. Set to OFF.");
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config_true.test
+@@ -0,0 +1,2 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
+--- /dev/null
++++ b/mysql-test/t/percona_log_slow_admin_statements-config.test
+@@ -0,0 +1,2 @@
++SHOW GLOBAL VARIABLES like 'log_slow_admin_statements';
++SELECT * FROM INFORMATION_SCHEMA.GLOBAL_VARIABLES WHERE VARIABLE_NAME='log_slow_admin_statements';
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -250,15 +250,31 @@
+  --log-slow-admin-statements 
+  Log slow OPTIMIZE, ANALYZE, ALTER and other
+  administrative statements to the slow log if it is open.
++ --log-slow-filter=name 
++ Log only the queries that followed certain execution
++ plan. Multiple flags allowed in a comma-separated string.
++ [qc_miss, full_scan, full_join, tmp_table,
++ tmp_table_on_disk, filesort, filesort_on_disk]
+  --log-slow-queries[=name] 
+  Log slow queries to a table or log file. Defaults logging
+  to table mysql.slow_log or hostname-slow.log if
+  --log-output=file is used. Must be enabled to activate
+  other slow log options. Deprecated option, use
+  --slow-query-log/--slow-query-log-file instead.
++ --log-slow-rate-limit=# 
++ Rate limit statement writes to slow log to only those
++ from every (1/log_slow_rate_limit) session.
+  --log-slow-slave-statements 
+- Log slow statements executed by slave thread to the slow
+- log if it is open.
++ Log queries replayed be the slave SQL thread
++ --log-slow-sp-statements 
++ Log slow statements executed by stored procedure to the
++ slow log if it is open.
++ (Defaults to on; use --skip-log-slow-sp-statements to disable.)
++ --log-slow-verbosity=name 
++ Choose how verbose the messages to your slow log will be.
++ Multiple flags allowed in a comma-separated string.
++ [microtime, query_plan, innodb, profiling,
++ profiling_use_getrusage]
+  --log-tc=name       Path to transaction coordinator log (used for
+  transactions that affect more than one storage engine,
+  when binary log is disabled).
+@@ -660,6 +676,18 @@
+  Log slow queries to given log file. Defaults logging to
+  hostname-slow.log. Must be enabled to activate other slow
+  log options
++ --slow-query-log-timestamp-always 
++ Timestamp is printed for all records of the slow log even
++ if they are same time.
++ --slow-query-log-timestamp-precision=name 
++ Log slow statements executed by stored procedure to the
++ slow log if it is open. [second, microsecond]
++ --slow-query-log-use-global-control=name 
++ Choose flags, wich always use the global variables.
++ Multiple flags allowed in a comma-separated string.
++ [none, log_slow_filter, log_slow_rate_limit,
++ log_slow_verbosity, long_query_time,
++ min_examined_row_limit, all]
+  --socket=name       Socket file to use for connection
+  --sort-buffer-size=# 
+  Each thread that needs to do a sort allocates a buffer of
+@@ -817,7 +845,11 @@
+ log-short-format FALSE
+ log-slave-updates FALSE
+ log-slow-admin-statements FALSE
++log-slow-filter 
++log-slow-rate-limit 1
+ log-slow-slave-statements FALSE
++log-slow-sp-statements TRUE
++log-slow-verbosity 
+ log-tc tc.log
+ log-tc-size 24576
+ log-warnings 1
+@@ -933,6 +965,9 @@
+ slave-type-conversions 
+ slow-launch-time 2
+ slow-query-log FALSE
++slow-query-log-timestamp-always FALSE
++slow-query-log-timestamp-precision second
++slow-query-log-use-global-control 
+ sort-buffer-size 2097152
+ sporadic-binlog-dump-fail FALSE
+ sql-mode 
index 059ff867859fcc370010deef83af8a39f474695c..9756337a1775653cb11e75de898a0475cc90f347 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/client/mysqldump.c
 +++ b/client/mysqldump.c
-@@ -141,6 +141,8 @@
+@@ -143,6 +143,8 @@
  static uint opt_protocol= 0;
  static char *opt_plugin_dir= 0, *opt_default_auth= 0;
  
@@ -16,7 +16,7 @@
  /*
  Dynamic_string wrapper functions. In this file use these
  wrappers, they will terminate the process if there is
-@@ -1494,6 +1496,17 @@
+@@ -1496,6 +1498,17 @@
      /* Don't switch charsets for 4.1 and earlier.  (bug#34192). */
      server_supports_switching_charsets= FALSE;
    } 
@@ -34,7 +34,7 @@
    /*
      As we're going to set SQL_MODE, it would be lost on reconnect, so we
      cannot reconnect.
-@@ -3175,7 +3188,12 @@
+@@ -3177,7 +3190,12 @@
  
      /* now build the query string */
  
@@ -48,7 +48,7 @@
      dynstr_append_checked(&query_string, filename);
      dynstr_append_checked(&query_string, "'");
  
-@@ -3225,7 +3243,12 @@
+@@ -3227,7 +3245,12 @@
        check_io(md_result_file);
      }
      
    mysqld_exit(0);
  }
  
-@@ -6557,6 +6666,7 @@
+@@ -6553,6 +6662,7 @@
    {"Delayed_errors",           (char*) &delayed_insert_errors,  SHOW_LONG},
    {"Delayed_insert_threads",   (char*) &delayed_insert_threads, SHOW_LONG_NOFLUSH},
    {"Delayed_writes",           (char*) &delayed_insert_writes,  SHOW_LONG},
    lex->leaf_tables_insert= 0;
 --- a/sql/sql_lex.h
 +++ b/sql/sql_lex.h
-@@ -2298,6 +2298,7 @@
+@@ -2303,6 +2303,7 @@
  
    enum enum_yes_no_unknown tx_chain, tx_release;
    bool safe_to_cache_query;
  %token  SQL_SMALL_RESULT
  %token  SQL_SYM                       /* SQL-2003-R */
  %token  SQL_THREAD
-@@ -7353,6 +7354,10 @@
+@@ -7357,6 +7358,10 @@
                Lex->select_lex.sql_cache= SELECT_LEX::SQL_NO_CACHE;
              }
            }
diff --git a/subunit.patch b/subunit.patch
new file mode 100644 (file)
index 0000000..8d03b18
--- /dev/null
@@ -0,0 +1,199 @@
+=== added file 'mysql-test/lib/Subunit.pm'
+--- /dev/null
++++ b/mysql-test/lib/Subunit.pm
+@@ -0,0 +1,94 @@
++# Perl module for parsing and generating the Subunit protocol
++# Copyright (C) 2008-2009 Jelmer Vernooij <jelmer@samba.org>
++#
++#  Licensed under either the Apache License, Version 2.0 or the BSD 3-clause
++#  license at the users choice. A copy of both licenses are available in the
++#  project source as Apache-2.0 and BSD. You may not use this file except in
++#  compliance with one of these two licences.
++#
++#  Unless required by applicable law or agreed to in writing, software
++#  distributed under these licenses is distributed on an "AS IS" BASIS, WITHOUT
++#  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
++#  license you chose for the specific language governing permissions and
++#  limitations under that license.
++
++package Subunit;
++use POSIX;
++
++use vars qw ( $VERSION );
++
++$VERSION = '0.0.2';
++
++use strict;
++my $SUBUNIT_OUT= 'test_results.subunit';
++# reset the file
++open(SUBUNITOUT, ">$SUBUNIT_OUT");
++close(SUBUNITOUT);
++
++sub subunit_start_test($)
++{
++      my ($testname) = @_;
++        open(SUBUNITOUT, ">>$SUBUNIT_OUT");
++      print SUBUNITOUT "test: $testname\n";
++        close(SUBUNITOUT);
++        return;
++}
++
++sub subunit_end_test($$;$)
++{
++      my $name = shift;
++      my $result = shift;
++      my $reason = shift;
++        open(SUBUNITOUT, ">>$SUBUNIT_OUT");
++      if ($reason) {
++              print SUBUNITOUT "$result: $name [\n";
++              print SUBUNITOUT "$reason\n";
++              print SUBUNITOUT "]\n";
++      } else {
++              print SUBUNITOUT "$result: $name\n";
++      }
++        close(SUBUNITOUT);
++        return;
++}
++
++sub subunit_skip_test($;$)
++{
++      my $name = shift;
++      my $reason = shift;
++      subunit_end_test($name, "skip", $reason);
++}
++
++sub subunit_fail_test($;$)
++{
++      my $name = shift;
++      my $reason = shift;
++      subunit_end_test($name, "failure", $reason);
++}
++
++sub subunit_pass_test($;$)
++{
++      my $name = shift;
++      my $reason = shift;
++      subunit_end_test($name, "success", $reason);
++}
++
++sub subunit_xfail_test($;$)
++{
++      my $name = shift;
++      my $reason = shift;
++      subunit_end_test($name, "xfail", $reason);
++}
++
++sub report_time($)
++{
++      my ($time) = @_;
++      my ($sec, $min, $hour, $mday, $mon, $year, $wday, $yday, $isdst) = localtime($time);
++        open(SUBUNITOUT, ">>$SUBUNIT_OUT");
++      printf SUBUNITOUT "time: %04d-%02d-%02d %02d:%02d:%02dZ\n", $year+1900, $mon, $mday, $hour, $min, $sec;
++        close(SUBUNITOUT);
++        return;
++}
++
++
++
++1;
+--- a/mysql-test/lib/mtr_report.pm
++++ b/mysql-test/lib/mtr_report.pm
+@@ -27,9 +27,11 @@
+               mtr_warning mtr_error mtr_debug mtr_verbose
+               mtr_verbose_restart mtr_report_test_passed
+               mtr_report_test_skipped mtr_print
++              mtr_report_test_subunit
+               mtr_report_test);
+ use mtr_match;
++use Subunit;
+ use My::Platform;
+ use POSIX qw[ _exit ];
+ use IO::Handle qw[ flush ];
+@@ -225,6 +227,68 @@
+   }
+ }
++sub mtr_report_test_subunit ($) {
++  my ($tinfo)= @_;
++  my $subunit_testname= $tinfo->{name};
++  $subunit_testname.= " '$tinfo->{combination}'"
++    if defined $tinfo->{combination};
++
++
++  my $comment=  $tinfo->{'comment'};
++  my $logfile=  $tinfo->{'logfile'};
++  my $warnings= $tinfo->{'warnings'};
++  my $result=   $tinfo->{'result'};
++  my $retry=    $tinfo->{'retries'} ? "retry-" : "";
++
++  my $test_name_sub = $tinfo->{name};
++
++  if ($result eq 'MTR_RES_FAILED'){
++
++    my $timest = format_time();
++    my $fail = "fail";
++
++    if ( $warnings )
++    {
++      Subunit::subunit_start_test($subunit_testname);
++      Subunit::subunit_fail_test($subunit_testname, "Found warnings/errors in server log file!");
++      return;
++    }
++    my $timeout= $tinfo->{'timeout'};
++    if ( $timeout )
++    {
++      Subunit::subunit_start_test($subunit_testname);
++      Subunit::subunit_fail_test($subunit_testname, "Timeout after $timeout seconds\n\n$tinfo->{'comment'}");
++      return;
++    }
++    Subunit::subunit_start_test($subunit_testname);
++    Subunit::subunit_fail_test($subunit_testname, "Comment: $comment\n\nLogfile:\n$logfile");
++  }
++  elsif ($result eq 'MTR_RES_SKIPPED')
++  {
++    if ( $tinfo->{'disable'} )
++    {
++      $comment="DISABLED: $comment";
++    }
++    # report into to subunit for Jenkins reporting
++    Subunit::subunit_start_test($subunit_testname);
++    Subunit::subunit_skip_test($subunit_testname, $comment);
++  }
++  elsif ($result eq 'MTR_RES_PASSED')
++  {
++    # Show any problems check-testcase found
++    if ( defined $tinfo->{'check'} )
++    {
++      mtr_report($tinfo->{'check'});
++    }
++    # report info to subunit for Jenkins reporting
++    # TODO:  catch 'check-testcase' output??
++    Subunit::report_time(time() - $tinfo->{timer}/1000);
++    Subunit::subunit_start_test($subunit_testname);
++    Subunit::report_time(time());
++    Subunit::subunit_pass_test($subunit_testname);
++  }
++}
++
+ sub mtr_report_stats ($$;$) {
+   my ($prefix, $tests, $dont_error)= @_;
+--- a/mysql-test/mysql-test-run.pl
++++ b/mysql-test/mysql-test-run.pl
+@@ -99,6 +99,7 @@
+ use mtr_results;
+ use IO::Socket::INET;
+ use IO::Select;
++use Subunit;
+ require "lib/mtr_process.pl";
+ require "lib/mtr_io.pl";
+@@ -629,6 +630,7 @@
+         # Report test status
+         mtr_report_test($result);
++        mtr_report_test_subunit($result);
+         if ( $result->is_failed() ) {
index 3cf82113592dd1ad82782f9418b935e362f34ce7..9567dea19c127aaa3d8b65f128bbe76bb9d26abe 100644 (file)
@@ -7,7 +7,7 @@
 # should be done or reviewed by the maintainer!
 --- a/include/mysql/plugin.h
 +++ b/include/mysql/plugin.h
-@@ -547,6 +547,9 @@
+@@ -556,6 +556,9 @@
  unsigned long thd_log_slow_verbosity(const MYSQL_THD thd);
  int thd_opt_slow_log();
  #define EXTENDED_SLOWLOG
@@ -61,7 +61,7 @@
 +Rename variable USERSTAT_RUNNING => USERSTAT
 --- a/sql/handler.cc
 +++ b/sql/handler.cc
-@@ -1244,6 +1244,8 @@
+@@ -1245,6 +1245,8 @@
          goto end;
        }
      DBUG_EXECUTE_IF("crash_commit_after", DBUG_SUICIDE(););
@@ -70,7 +70,7 @@
      RUN_HOOK(transaction, after_commit, (thd, FALSE));
  end:
      if (rw_trans && mdl_request.ticket)
-@@ -1398,6 +1400,8 @@
+@@ -1399,6 +1401,8 @@
    /* Always cleanup. Even if nht==0. There may be savepoints. */
    if (is_real_trans)
      thd->transaction.cleanup();
@@ -79,7 +79,7 @@
    if (all)
      thd->transaction_rollback_request= FALSE;
  
-@@ -1802,6 +1806,7 @@
+@@ -1803,6 +1807,7 @@
      ha_info->reset(); /* keep it conveniently zero-filled */
    }
    trans->ha_list= sv->ha_list;
@@ -87,7 +87,7 @@
    DBUG_RETURN(error);
  }
  
-@@ -2178,6 +2183,8 @@
+@@ -2179,6 +2184,8 @@
        dup_ref=ref+ALIGN_SIZE(ref_length);
      cached_table_flags= table_flags();
    }
@@ -96,7 +96,7 @@
    DBUG_RETURN(error);
  }
  
-@@ -3631,6 +3638,127 @@
+@@ -3638,6 +3645,127 @@
    return;
  }
  
      delete thd;
      DBUG_VOID_RETURN;
    }
-@@ -7961,6 +7993,8 @@
+@@ -7957,6 +7989,8 @@
    key_delayed_insert_mutex, key_hash_filo_lock, key_LOCK_active_mi,
    key_LOCK_connection_count, key_LOCK_crypt, key_LOCK_delayed_create,
    key_LOCK_delayed_insert, key_LOCK_delayed_status, key_LOCK_error_log,
    key_LOCK_gdl, key_LOCK_global_system_variables,
    key_LOCK_manager,
    key_LOCK_prepared_stmt_count,
-@@ -8000,6 +8034,13 @@
+@@ -7996,6 +8030,13 @@
    { &key_LOCK_delayed_insert, "LOCK_delayed_insert", PSI_FLAG_GLOBAL},
    { &key_LOCK_delayed_status, "LOCK_delayed_status", PSI_FLAG_GLOBAL},
    { &key_LOCK_error_log, "LOCK_error_log", PSI_FLAG_GLOBAL},
    TODO: Replace this with an inline function.
 --- a/sql/sql_base.cc
 +++ b/sql/sql_base.cc
-@@ -1524,6 +1524,11 @@
+@@ -1587,6 +1587,11 @@
    table->mdl_ticket= NULL;
  
    mysql_mutex_lock(&thd->LOCK_thd_data);
    *table_ptr=table->next;
    mysql_mutex_unlock(&thd->LOCK_thd_data);
  
-@@ -2162,6 +2167,8 @@
+@@ -2225,6 +2230,8 @@
    DBUG_PRINT("tmptable", ("closing table: '%s'.'%s'",
                            table->s->db.str, table->s->table_name.str));
  
    if (delete_table)
 --- a/sql/sql_class.cc
 +++ b/sql/sql_class.cc
-@@ -850,6 +850,13 @@
+@@ -869,6 +869,13 @@
    mysys_var=0;
    binlog_evt_union.do_union= FALSE;
    enable_slow_log= 0;
  #ifndef DBUG_OFF
    dbug_sentry=THD_SENTRY_MAGIC;
  #endif
-@@ -1228,6 +1235,7 @@
+@@ -1248,6 +1255,7 @@
      variables.option_bits|= OPTION_BIN_LOG;
    else
      variables.option_bits&= ~OPTION_BIN_LOG;
  
  #if defined(ENABLED_DEBUG_SYNC)
    /* Initialize the Debug Sync Facility. See debug_sync.cc. */
-@@ -1235,6 +1243,94 @@
+@@ -1255,6 +1263,94 @@
  #endif /* defined(ENABLED_DEBUG_SYNC) */
  }
  
  
  /*
    Init THD for query processing.
-@@ -1989,6 +2085,32 @@
+@@ -2009,6 +2105,32 @@
  }
  #endif
  
  
  struct Item_change_record: public ilink
  {
-@@ -2165,6 +2287,7 @@
+@@ -2185,6 +2307,7 @@
    }
  
    thd->sent_row_count++;
  
    if (thd->vio_ok())
      DBUG_RETURN(protocol->write());
-@@ -2257,6 +2380,7 @@
+@@ -2277,6 +2400,7 @@
  select_export::~select_export()
  {
    thd->sent_row_count=row_count;
  }
  
  
-@@ -3280,6 +3404,7 @@
+@@ -3300,6 +3424,7 @@
    if (likely(thd != 0))
    { /* current_thd==0 when close_connection() calls net_send_error() */
      thd->status_var.bytes_sent+= length;
    }
  }
  
-@@ -3287,6 +3412,7 @@
+@@ -3307,6 +3432,7 @@
  void thd_increment_bytes_received(ulong length)
  {
    current_thd->status_var.bytes_received+= length;
    uint32     file_id;                 // for LOAD DATA INFILE
    /* remote (peer) port */
    uint16 peer_port;
-@@ -2105,6 +2107,8 @@
+@@ -2098,6 +2100,8 @@
    */
    enum_tx_isolation tx_isolation;
    enum_check_fields count_cuted_fields;
  
    DYNAMIC_ARRAY user_var_events;        /* For user variables replication */
    MEM_ROOT      *user_var_events_alloc; /* Allocate above array elements here */
-@@ -2199,6 +2203,49 @@
+@@ -2192,6 +2196,49 @@
    */
    LOG_INFO*  current_linfo;
    NET*       slave_net;                       // network connection from slave -> m.
    /* Used by the sys_var class to store temporary values */
    union
    {
-@@ -2279,6 +2326,11 @@
+@@ -2272,6 +2319,11 @@
      alloc_root. 
    */
    void init_for_queries();
    void change_user(void);
    void cleanup(void);
    void cleanup_after_query();
-@@ -2751,6 +2803,15 @@
+@@ -2744,6 +2796,15 @@
    }
    thd_scheduler scheduler;
  
  public:
    inline Internal_error_handler *get_internal_handler()
    { return m_internal_handler; }
-@@ -2951,6 +3012,10 @@
+@@ -2944,6 +3005,10 @@
    LEX_STRING invoker_host;
  };
  
    thd->abort_on_warning= 0;
    DBUG_RETURN(FALSE);
  
-@@ -3540,6 +3543,7 @@
+@@ -3535,6 +3538,7 @@
       thd->first_successful_insert_id_in_prev_stmt :
       (info.copied ? autoinc_value_of_last_inserted_row : 0));
    ::my_ok(thd, row_count, id, buff);
    /*
      Commands which always take a long time are logged into
      the slow log only if opt_log_slow_admin_statements is set.
-@@ -1667,6 +1680,13 @@
+@@ -1672,6 +1685,13 @@
      thd->profiling.discard_current_query();
  #endif
      break;
    case SCH_OPEN_TABLES:
    case SCH_VARIABLES:
    case SCH_STATUS:
-@@ -1824,6 +1844,7 @@
+@@ -1829,6 +1849,7 @@
                         thd->security_ctx->priv_host)) &&
          check_global_access(thd, SUPER_ACL))
      {
        my_error(ER_SPECIFIC_ACCESS_DENIED_ERROR, MYF(0), "SUPER");
        DBUG_RETURN(TRUE);
      }
-@@ -4806,6 +4827,7 @@
+@@ -4827,6 +4848,7 @@
        case ACL_INTERNAL_ACCESS_DENIED:
          if (! no_errors)
          {
            my_error(ER_DBACCESS_DENIED_ERROR, MYF(0),
                     sctx->priv_user, sctx->priv_host, db);
          }
-@@ -4856,6 +4878,7 @@
+@@ -4877,6 +4899,7 @@
      DBUG_PRINT("error",("No possible access"));
      if (!no_errors)
      {
        if (thd->password == 2)
          my_error(ER_ACCESS_DENIED_NO_PASSWORD_ERROR, MYF(0),
                   sctx->priv_user,
-@@ -4972,6 +4995,7 @@
+@@ -4993,6 +5016,7 @@
  
      if (!thd->col_access && check_grant_db(thd, dst_db_name))
      {
        my_error(ER_DBACCESS_DENIED_ERROR, MYF(0),
                 thd->security_ctx->priv_user,
                 thd->security_ctx->priv_host,
-@@ -5242,6 +5266,7 @@
+@@ -5263,6 +5287,7 @@
    if ((thd->security_ctx->master_access & want_access))
      return 0;
    get_privilege_desc(command, sizeof(command), want_access);
    my_error(ER_SPECIFIC_ACCESS_DENIED_ERROR, MYF(0), command);
    return 1;
  #else
-@@ -5623,6 +5648,32 @@
+@@ -5644,6 +5669,32 @@
    lex_start(thd);
    mysql_reset_thd_for_next_command(thd);
  
    if (query_cache_send_result_to_client(thd, rawbuf, length) <= 0)
    {
      LEX *lex= thd->lex;
-@@ -5691,6 +5742,52 @@
+@@ -5712,6 +5763,52 @@
      DBUG_ASSERT(thd->change_list.is_empty());
    }
  
  
  /* collect status for all running threads */
  
-@@ -7689,6 +8005,104 @@
+@@ -7712,6 +8028,104 @@
  };
  
  
  ST_FIELD_INFO processlist_fields_info[]=
  {
    {"ID", 4, MYSQL_TYPE_LONGLONG, 0, 0, "Id", SKIP_OPEN_TABLE},
-@@ -7878,6 +8292,8 @@
+@@ -7901,6 +8315,8 @@
  {
    {"CHARACTER_SETS", charsets_fields_info, create_schema_table, 
     fill_schema_charsets, make_character_sets_old_format, 0, -1, -1, 0, 0},
    {"COLLATIONS", collation_fields_info, create_schema_table, 
     fill_schema_collation, make_old_format, 0, -1, -1, 0, 0},
    {"COLLATION_CHARACTER_SET_APPLICABILITY", coll_charset_app_fields_info,
-@@ -7887,6 +8303,8 @@
+@@ -7910,6 +8326,8 @@
     OPTIMIZE_I_S_TABLE|OPEN_VIEW_FULL},
    {"COLUMN_PRIVILEGES", column_privileges_fields_info, create_schema_table,
     fill_schema_column_privileges, 0, 0, -1, -1, 0, 0},
    {"ENGINES", engines_fields_info, create_schema_table,
     fill_schema_engines, make_old_format, 0, -1, -1, 0, 0},
  #ifdef HAVE_EVENT_SCHEDULER
-@@ -7959,14 +8377,20 @@
+@@ -7982,14 +8400,20 @@
     get_all_tables, make_table_names_old_format, 0, 1, 2, 1, 0},
    {"TABLE_PRIVILEGES", table_privileges_fields_info, create_schema_table,
     fill_schema_table_privileges, 0, 0, -1, -1, 0, 0},
  %token  USE_FRM
  %token  USE_SYM
  %token  USING                         /* SQL-2003-R */
-@@ -11100,6 +11105,41 @@
+@@ -11120,6 +11125,41 @@
               MYSQL_YYABORT;
  #endif // HAVE_RESPONSE_TIME_DISTRIBUTION
           }
          | CREATE PROCEDURE_SYM sp_name
            {
              LEX *lex= Lex;
-@@ -11342,6 +11382,16 @@
+@@ -11365,6 +11405,16 @@
              Lex->type|= REFRESH_QUERY_RESPONSE_TIME;
  #endif // HAVE_RESPONSE_TIME_DISTRIBUTION
            }
          | MASTER_SYM
            { Lex->type|= REFRESH_MASTER; }
          | DES_KEY_FILE
-@@ -12480,6 +12530,7 @@
+@@ -12509,6 +12559,7 @@
          | CHAIN_SYM                {}
          | CHANGED                  {}
          | CIPHER_SYM               {}
          | CLIENT_SYM               {}
          | CLASS_ORIGIN_SYM         {}
          | COALESCE                 {}
-@@ -12548,6 +12599,7 @@
+@@ -12577,6 +12628,7 @@
          | HOSTS_SYM                {}
          | HOUR_SYM                 {}
          | IDENTIFIED_SYM           {}
          | IGNORE_SERVER_IDS_SYM    {}
          | INVOKER_SYM              {}
          | IMPORT                   {}
-@@ -12699,6 +12751,7 @@
+@@ -12728,6 +12780,7 @@
          | SUSPEND_SYM              {}
          | SWAPS_SYM                {}
          | SWITCHES_SYM             {}
          | TABLE_NAME_SYM           {}
          | TABLES                   {}
          | TABLE_CHECKSUM_SYM       {}
-@@ -12724,6 +12777,7 @@
+@@ -12753,6 +12806,7 @@
          | UNKNOWN_SYM              {}
          | UNTIL_SYM                {}
          | USER                     {}
 +SET GLOBAL userstat=OFF;
 +DROP TABLE t1;
 \ No newline at end of file
+--- a/mysql-test/r/mysqld--help-notwin.result
++++ b/mysql-test/r/mysqld--help-notwin.result
+@@ -743,6 +743,8 @@
+  Define threads usage for handling queries, one of
+  one-thread-per-connection, no-threads, loaded-dynamically
+  --thread-stack=#    The stack size for each thread
++ --thread-statistics Control TABLE_STATISTICS running, when userstat is
++ enabled
+  --time-format=name  The TIME format (ignored)
+  --timed-mutexes     Specify whether to time mutexes (only InnoDB mutexes are
+  currently supported)
+@@ -768,6 +770,9 @@
+  of the underlying table and the query uses a LIMIT clause
+  (usually get from GUI tools)
+  -u, --user=name     Run mysqld daemon as user.
++ --userstat          Control USER_STATISTICS, CLIENT_STATISTICS,
++ THREAD_STATISTICS, INDEX_STATISTICS and TABLE_STATISTICS
++ running
+  -v, --verbose       Used with --help option for detailed help.
+  -V, --version       Output version information and exit.
+  --wait-timeout=#    The number of seconds the server waits for activity on a
+@@ -1002,6 +1007,7 @@
+ thread-cache-size 0
+ thread-handling one-thread-per-connection
+ thread-stack 262144
++thread-statistics FALSE
+ time-format %H:%i:%s
+ timed-mutexes FALSE
+ tmp-table-size 16777216
+@@ -1009,6 +1015,7 @@
+ transaction-isolation REPEATABLE-READ
+ transaction-prealloc-size 4096
+ updatable-views-with-limit YES
++userstat FALSE
+ verbose TRUE
+ wait-timeout 28800
+ xtradb-admin-command ON
index bdbb5ba1e609c1617000488df0e3f553e6d5a04b..1504176c57707050b85b99f39a3fb8df50374ca3 100644 (file)
@@ -2,7 +2,7 @@
 #  https://bugs.launchpad.net/percona-server/+bug/794837
 --- a/mysql-test/valgrind.supp
 +++ b/mysql-test/valgrind.supp
-@@ -876,3 +876,12 @@
+@@ -876,6 +876,15 @@
     fun:buf_buddy_free_low
     fun:buf_buddy_free
  }
@@ -15,3 +15,6 @@
 +   fun:compress
 +   fun:my_compress_alloc
 +}
+ # Note the wildcard in the (mangled) function signatures of
+ # write_keys() and find_all_keys().
This page took 0.896124 seconds and 4 git commands to generate.