List:Commits« Previous MessageNext Message »
From:Pekka Nousiainen Date:May 19 2011 9:16am
Subject:bzr commit into mysql-5.1-telco-7.0-wl4163 branch (pekka:4374) WL#4124
View as plain text  
#At file:///export/space/pekka/ms/ms-wl4124-70/ based on revid:pekka@stripped

 4374 Pekka Nousiainen	2011-05-19
      wl#4124 b01_sys.diff
      configs, pseudo-cols, sys tables, signals

    added:
      storage/ndb/include/kernel/signaldata/IndexStatSignal.hpp
      storage/ndb/src/common/debugger/signaldata/IndexStatSignal.cpp
    modified:
      mysql-test/suite/ndb/r/ndb_restore_misc.result
      mysql-test/suite/ndb/t/ndb_restore_misc.test
      storage/ndb/include/kernel/AttributeHeader.hpp
      storage/ndb/include/kernel/GlobalSignalNumbers.h
      storage/ndb/include/kernel/ndb_limits.h
      storage/ndb/include/kernel/signaldata/AccScan.hpp
      storage/ndb/include/kernel/signaldata/ScanFrag.hpp
      storage/ndb/include/kernel/signaldata/ScanTab.hpp
      storage/ndb/include/kernel/signaldata/SignalData.hpp
      storage/ndb/include/mgmapi/mgmapi_config_parameters.h
      storage/ndb/include/ndbapi/NdbDictionary.hpp
      storage/ndb/include/ndbapi/NdbScanOperation.hpp
      storage/ndb/src/common/debugger/signaldata/Makefile.am
      storage/ndb/src/common/debugger/signaldata/ScanFrag.cpp
      storage/ndb/src/common/debugger/signaldata/ScanTab.cpp
      storage/ndb/src/common/debugger/signaldata/SchemaTransImpl.cpp
      storage/ndb/src/common/debugger/signaldata/SignalDataPrint.cpp
      storage/ndb/src/common/debugger/signaldata/SignalNames.cpp
      storage/ndb/src/kernel/blocks/ERROR_codes.txt
      storage/ndb/src/kernel/blocks/cmvmi/Cmvmi.cpp
      storage/ndb/src/kernel/blocks/dblqh/Dblqh.hpp
      storage/ndb/src/kernel/blocks/dblqh/DblqhMain.cpp
      storage/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp
      storage/ndb/src/kernel/blocks/dbtup/DbtupRoutines.cpp
      storage/ndb/src/kernel/blocks/ndbcntr/Ndbcntr.hpp
      storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrInit.cpp
      storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrMain.cpp
      storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrSysTable.cpp
      storage/ndb/src/mgmsrv/ConfigInfo.cpp
      storage/ndb/src/ndbapi/NdbDictionaryImpl.cpp
      storage/ndb/src/ndbapi/ndberror.c
      storage/ndb/tools/restore/Restore.cpp
      storage/ndb/tools/restore/consumer_restore.cpp
=== modified file 'mysql-test/suite/ndb/r/ndb_restore_misc.result'
--- a/mysql-test/suite/ndb/r/ndb_restore_misc.result	2011-04-11 13:36:12 +0000
+++ b/mysql-test/suite/ndb/r/ndb_restore_misc.result	2011-05-19 09:16:32 +0000
@@ -623,8 +623,12 @@ name VARCHAR(255)
 
 ndb_show_tables completed.....
 
+select id into @tmp1 from ndb_show_tables_results
+where name like '%NDB$IS_SAMPLE_X1%';
 select * from ndb_show_tables_results
 where type like '%Index%'
+and name not like '%NDB$IS_SAMPLE_X1%'
+and name not like concat('%NDB$INDEX_',@tmp1,'_CUSTOM%')
 order by 1,2,3,4,5,6,7;
 id	type	state	logging	_database	_schema	name
 drop table ndb_show_tables_results;

=== modified file 'mysql-test/suite/ndb/t/ndb_restore_misc.test'
--- a/mysql-test/suite/ndb/t/ndb_restore_misc.test	2011-05-06 14:11:46 +0000
+++ b/mysql-test/suite/ndb/t/ndb_restore_misc.test	2011-05-19 09:16:32 +0000
@@ -546,8 +546,15 @@ CREATE TEMPORARY TABLE IF NOT EXISTS ndb
   name VARCHAR(255)
 );
 --source ndb_show_tables_result.inc
+# the db fields include single quotes...
+--disable_warnings
+select id into @tmp1 from ndb_show_tables_results
+where name like '%NDB$IS_SAMPLE_X1%';
+--enable_warnings
 select * from ndb_show_tables_results
 where type like '%Index%'
+and name not like '%NDB$IS_SAMPLE_X1%'
+and name not like concat('%NDB$INDEX_',@tmp1,'_CUSTOM%')
 order by 1,2,3,4,5,6,7;
 drop table ndb_show_tables_results;
 

=== modified file 'storage/ndb/include/kernel/AttributeHeader.hpp'
--- a/storage/ndb/include/kernel/AttributeHeader.hpp	2011-02-01 23:27:25 +0000
+++ b/storage/ndb/include/kernel/AttributeHeader.hpp	2011-05-19 09:16:32 +0000
@@ -73,6 +73,10 @@ public:
   STATIC_CONST( OPTIMIZE_MOVE_VARPART = 0x0001 ); //option to move varpart
   STATIC_CONST( OPTIMIZE_MOVE_FIXPART = 0x0002 ); //option to move fixpart
 
+  // index stats pseudo columns
+  STATIC_CONST( INDEX_STAT_KEY   = 0xFFD0 );
+  STATIC_CONST( INDEX_STAT_VALUE = 0xFFD1 );
+
   // NOTE: in 5.1 ctors and init take size in bytes
 
   /** Initialize AttributeHeader at location aHeaderPtr */

=== modified file 'storage/ndb/include/kernel/GlobalSignalNumbers.h'
--- a/storage/ndb/include/kernel/GlobalSignalNumbers.h	2011-04-28 07:47:53 +0000
+++ b/storage/ndb/include/kernel/GlobalSignalNumbers.h	2011-05-19 09:16:32 +0000
@@ -866,15 +866,6 @@ extern const GlobalSignalNumber NO_OF_SI
 #define GSN_648
 #define GSN_649
 
-#define GSN_650
-#define GSN_651
-#define GSN_652
-#define GSN_653
-#define GSN_654
-#define GSN_655
-
-#define GSN_656
-
 #define GSN_UTIL_CREATE_LOCK_REQ        132
 #define GSN_UTIL_CREATE_LOCK_REF        133
 #define GSN_UTIL_CREATE_LOCK_CONF       188
@@ -1079,4 +1070,12 @@ extern const GlobalSignalNumber NO_OF_SI
 #define GSN_RELEASE_PAGES_REQ           680
 #define GSN_RELEASE_PAGES_CONF          681
 
+#define GSN_INDEX_STAT_REQ              650
+#define GSN_INDEX_STAT_CONF             651
+#define GSN_INDEX_STAT_REF              652
+#define GSN_INDEX_STAT_IMPL_REQ         653
+#define GSN_INDEX_STAT_IMPL_CONF        654
+#define GSN_INDEX_STAT_IMPL_REF         655
+#define GSN_INDEX_STAT_REP              656
+
 #endif

=== modified file 'storage/ndb/include/kernel/ndb_limits.h'
--- a/storage/ndb/include/kernel/ndb_limits.h	2011-04-13 08:51:04 +0000
+++ b/storage/ndb/include/kernel/ndb_limits.h	2011-05-19 09:16:32 +0000
@@ -218,4 +218,19 @@
  */
 #define NDB_SPJ_MAX_TREE_NODES 32
 
+/*
+ * Stored ordered index stats uses 2 Longvarbinary pseudo-columns: the
+ * packed index keys and the packed values.  Key size is limited by
+ * SAMPLES table which has 3 other PK attributes.  Also length bytes is
+ * counted as 1 word.  Values currently contain RIR (one word) and RPK
+ * (one word for each key level).  The SAMPLEs table STAT_VALUE column
+ * is longer to allow future changes.
+ */
+#define MAX_INDEX_STAT_KEY_COUNT    MAX_ATTRIBUTES_IN_INDEX
+#define MAX_INDEX_STAT_KEY_SIZE     (MAX_KEY_SIZE_IN_WORDS - 3 - 1)
+#define MAX_INDEX_STAT_VALUE_COUNT  (1 + MAX_INDEX_STAT_KEY_COUNT)
+#define MAX_INDEX_STAT_VALUE_SIZE   MAX_INDEX_STAT_VALUE_COUNT
+#define MAX_INDEX_STAT_VALUE_CSIZE  512 /* Longvarbinary(2048) */
+#define MAX_INDEX_STAT_VALUE_FORMAT 1
+
 #endif

=== modified file 'storage/ndb/include/kernel/signaldata/AccScan.hpp'
--- a/storage/ndb/include/kernel/signaldata/AccScan.hpp	2011-02-01 21:05:11 +0000
+++ b/storage/ndb/include/kernel/signaldata/AccScan.hpp	2011-05-19 09:16:32 +0000
@@ -72,6 +72,9 @@ private:
 
   static Uint32 getLcpScanFlag(const Uint32 & requestInfo);
   static void setLcpScanFlag(Uint32 & requestInfo, Uint32 nr);
+
+  static Uint32 getStatScanFlag(const Uint32 & requestInfo);
+  static void setStatScanFlag(Uint32 & requestInfo, Uint32 nr);
 };
 
 /**
@@ -83,10 +86,11 @@ private:
  * d = No disk scan          - 1  Bit 7
  * n = Node recovery scan    - 1  Bit 8
  * c = LCP scan              - 1  Bit 9
+ * s = Statistics scan       - 1  Bit 4
  *
  *           1111111111222222222233
  * 01234567890123456789012345678901
- *   l  hzdn   
+ *   l shzdn   
  */
 #define AS_LOCK_MODE_SHIFT       (2)
 #define AS_LOCK_MODE_MASK        (1)
@@ -95,6 +99,7 @@ private:
 #define AS_NO_DISK_SCAN          (7)
 #define AS_NR_SCAN               (8)
 #define AS_LCP_SCAN              (9)
+#define AS_STAT_SCAN             (4)
 
 inline 
 Uint32
@@ -174,6 +179,19 @@ AccScanReq::setLcpScanFlag(UintR & reque
   requestInfo |= (val << AS_LCP_SCAN);
 }
 
+inline
+Uint32
+AccScanReq::getStatScanFlag(const Uint32 & requestInfo){
+  return (requestInfo >> AS_STAT_SCAN) & 1;
+}
+
+inline
+void
+AccScanReq::setStatScanFlag(UintR & requestInfo, UintR val){
+  ASSERT_BOOL(val, "AccScanReq::setStatScanScanFlag");
+  requestInfo |= (val << AS_STAT_SCAN);
+}
+
 class AccScanConf {
   /**
    * Sender(s)
@@ -212,7 +230,9 @@ class AccScanRef {
 
   enum ErrorCode {
     TuxNoFreeScanOp = 909,
-    TuxIndexNotOnline = 910
+    TuxIndexNotOnline = 910,
+    TuxNoFreeStatOp = 911,
+    TuxInvalidLockMode = 912
   };
 
 public:

=== added file 'storage/ndb/include/kernel/signaldata/IndexStatSignal.hpp'
--- a/storage/ndb/include/kernel/signaldata/IndexStatSignal.hpp	1970-01-01 00:00:00 +0000
+++ b/storage/ndb/include/kernel/signaldata/IndexStatSignal.hpp	2011-05-19 09:16:32 +0000
@@ -0,0 +1,121 @@
+/* Copyright (C) 2003 MySQL AB
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; version 2 of the License.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
+
+#ifndef INDEX_STAT_SIGNAL_DATA_HPP
+#define INDEX_STAT_SIGNAL_DATA_HPP
+
+#include "SignalData.hpp"
+
+struct IndexStatReq {
+  enum RequestType {
+    // update
+    RT_UPDATE_STAT = 1,
+    RT_CLEAN_NEW = 2,
+    RT_SCAN_FRAG = 3,
+    RT_CLEAN_OLD = 4,
+    RT_START_MON = 5,
+    // delete
+    RT_DELETE_STAT = 6,
+    RT_STOP_MON = 7,
+    RT_DROP_HEAD = 8,
+    RT_CLEAN_ALL = 9
+  };
+  STATIC_CONST( SignalLength = 9 );
+  Uint32 clientRef;
+  Uint32 clientData;
+  Uint32 transId;
+  Uint32 transKey;
+  Uint32 requestInfo;
+  Uint32 requestFlag;
+  Uint32 indexId;
+  Uint32 indexVersion;
+  Uint32 tableId;
+};
+
+struct IndexStatImplReq {
+  STATIC_CONST( SignalLength = 10 );
+  Uint32 senderRef;
+  Uint32 senderData;
+  Uint32 transId;
+  Uint32 requestType;
+  Uint32 requestFlag;
+  Uint32 indexId;
+  Uint32 indexVersion;
+  Uint32 tableId;
+  Uint32 fragId;
+  Uint32 fragCount;
+};
+
+struct IndexStatConf {
+  STATIC_CONST( SignalLength = 3 );
+  Uint32 senderRef;
+  union { Uint32 senderData; Uint32 clientData; };
+  Uint32 transId;
+};
+
+struct IndexStatImplConf {
+  STATIC_CONST( SignalLength = 2 );
+  Uint32 senderRef;
+  Uint32 senderData;
+};
+
+struct IndexStatRef {
+  enum ErrorCode {
+    Busy = 701,
+    NotMaster = 702,
+    InvalidIndex = 913,
+    InvalidRequest = 914,
+    NoFreeStatOp = 915,
+    InvalidSysTable = 916,
+    InvalidSysTableData = 917,
+    BusyUtilPrepare = 918,
+    BusyUtilExecute = 919
+  };
+  STATIC_CONST( SignalLength = 7 );
+  Uint32 senderRef;
+  union { Uint32 senderData; Uint32 clientData; };
+  Uint32 transId;
+  Uint32 errorCode;
+  Uint32 errorLine;
+  Uint32 errorNodeId;
+  Uint32 masterNodeId;
+};
+
+struct IndexStatImplRef {
+  STATIC_CONST( SignalLength = 4 );
+  Uint32 senderRef;
+  Uint32 senderData;
+  Uint32 errorCode;
+  Uint32 errorLine;
+};
+
+struct IndexStatRep {
+  enum RequestType {
+    RT_UPDATE_REQ = 1,  // TUX->DICT request stats update
+    RT_UPDATE_CONF = 2  // TRIX->TUX report stats update
+  };
+  STATIC_CONST( SignalLength = 9 );
+  Uint32 senderRef;
+  Uint32 senderData;
+  Uint32 requestType;
+  Uint32 requestFlag;
+  Uint32 indexId;
+  Uint32 indexVersion;
+  Uint32 tableId;
+  Uint32 fragId;
+  Uint32 loadTime;
+};
+
+#endif

=== modified file 'storage/ndb/include/kernel/signaldata/ScanFrag.hpp'
--- a/storage/ndb/include/kernel/signaldata/ScanFrag.hpp	2011-02-23 19:28:26 +0000
+++ b/storage/ndb/include/kernel/signaldata/ScanFrag.hpp	2011-05-19 09:16:32 +0000
@@ -79,6 +79,7 @@ public:
   static Uint32 getScanPrio(const Uint32 & requestInfo);
   static Uint32 getNoDiskFlag(const Uint32 & requestInfo);
   static Uint32 getLcpScanFlag(const Uint32 & requestInfo);
+  static Uint32 getStatScanFlag(const Uint32 & requestInfo);
 
   static void setLockMode(Uint32 & requestInfo, Uint32 lockMode);
   static void setHoldLockFlag(Uint32 & requestInfo, Uint32 holdLock);
@@ -91,6 +92,7 @@ public:
   static void setScanPrio(Uint32& requestInfo, Uint32 prio);
   static void setNoDiskFlag(Uint32& requestInfo, Uint32 val);
   static void setLcpScanFlag(Uint32 & requestInfo, Uint32 val);
+  static void setStatScanFlag(Uint32 & requestInfo, Uint32 val);
 
   static void setReorgFlag(Uint32 & requestInfo, Uint32 val);
   static Uint32 getReorgFlag(const Uint32 & requestInfo);
@@ -270,11 +272,12 @@ public:
  * p = Scan prio             - 4  Bits (12-15) -> max 15
  * r = Reorg flag            - 2  Bits (1-2)
  * C = corr value flag       - 1  Bit  (16)
+ * s = Stat scan             - 1  Bit 17
  *
  *           1111111111222222222233
  * 01234567890123456789012345678901
  *  rrcdlxhkrztppppaaaaaaaaaaaaaaaa   Short variant ( < 6.4.0)
- *  rrcdlxhkrztppppA                  Long variant (6.4.0 +)
+ *  rrcdlxhkrztppppAs                 Long variant (6.4.0 +)
  */
 #define SF_LOCK_MODE_SHIFT   (5)
 #define SF_LOCK_MODE_MASK    (1)
@@ -299,6 +302,8 @@ public:
 
 #define SF_CORR_FACTOR_SHIFT  (16)
 
+#define SF_STAT_SCAN_SHIFT  (17)
+
 inline 
 Uint32
 ScanFragReq::getLockMode(const Uint32 & requestInfo){
@@ -488,6 +493,19 @@ ScanFragReq::setCorrFactorFlag(UintR & r
   requestInfo |= (val << SF_CORR_FACTOR_SHIFT);
 }
 
+inline
+Uint32
+ScanFragReq::getStatScanFlag(const Uint32 & requestInfo){
+  return (requestInfo >> SF_STAT_SCAN_SHIFT) & 1;
+}
+
+inline
+void
+ScanFragReq::setStatScanFlag(UintR & requestInfo, UintR val){
+  ASSERT_BOOL(val, "ScanFragReq::setStatScanFlag");
+  requestInfo |= (val << SF_STAT_SCAN_SHIFT);
+}
+
 /**
  * Request Info (SCAN_NEXTREQ)
  *

=== modified file 'storage/ndb/include/kernel/signaldata/ScanTab.hpp'
--- a/storage/ndb/include/kernel/signaldata/ScanTab.hpp	2011-02-08 13:55:54 +0000
+++ b/storage/ndb/include/kernel/signaldata/ScanTab.hpp	2011-05-19 09:16:32 +0000
@@ -108,6 +108,7 @@ private:
   static Uint32 getViaSPJFlag(const Uint32 & requestInfo);
   static Uint32 getPassAllConfsFlag(const Uint32 & requestInfo);
   static Uint32 get4WordConf(const Uint32&);
+  static UintR getStatScanFlag(const UintR & requestInfo);
 
   /**
    * Set:ers for requestInfo
@@ -127,6 +128,7 @@ private:
   static void setViaSPJFlag(Uint32 & requestInfo, Uint32 val);
   static void setPassAllConfsFlag(Uint32 & requestInfo, Uint32 val);
   static void set4WordConf(Uint32 & requestInfo, Uint32 val);
+  static void setStatScanFlag(UintR & requestInfo, UintR val);
 };
 
 /**
@@ -150,10 +152,11 @@ private:
  j = Via SPJ flag          - 1  Bit 27
  a = Pass all confs flag   - 1  Bit 28
  f = 4 word conf           - 1  Bit 29
+ s = Stat scan             - 1  Bit 30  index stats
 
            1111111111222222222233
  01234567890123456789012345678901
- pppppppplnhcktzxbbbbbbbbbbdjaf
+ pppppppplnhcktzxbbbbbbbbbbdjafs
 */
 
 #define PARALLEL_SHIFT     (0)
@@ -193,6 +196,8 @@ private:
 #define SCAN_PASS_CONF_SHIFT (28)
 #define SCAN_4WORD_CONF_SHIFT (29)
 
+#define STAT_SCAN_SHIFT (30)
+
 inline
 Uint8
 ScanTabReq::getParallelism(const UintR & requestInfo){
@@ -392,6 +397,19 @@ ScanTabReq::set4WordConf(UintR & request
   requestInfo |= (flag << SCAN_4WORD_CONF_SHIFT);
 }
 
+inline
+UintR 
+ScanTabReq::getStatScanFlag(const UintR & requestInfo){
+  return (requestInfo >> STAT_SCAN_SHIFT) & 1;
+}
+
+inline
+void 
+ScanTabReq::setStatScanFlag(UintR & requestInfo, Uint32 flag){
+  ASSERT_BOOL(flag, "ScanTabReq::setStatScanFlag");
+  requestInfo |= (flag << STAT_SCAN_SHIFT);
+}
+
 /**
  * 
  * SENDER:  Dbtc

=== modified file 'storage/ndb/include/kernel/signaldata/SignalData.hpp'
--- a/storage/ndb/include/kernel/signaldata/SignalData.hpp	2011-04-09 15:48:21 +0000
+++ b/storage/ndb/include/kernel/signaldata/SignalData.hpp	2011-05-19 09:16:32 +0000
@@ -309,4 +309,12 @@ GSN_PRINT_SIGNATURE(printDBINFO_SCAN_REF
 GSN_PRINT_SIGNATURE(printNODE_PING_REQ);
 GSN_PRINT_SIGNATURE(printNODE_PING_CONF);
 
+GSN_PRINT_SIGNATURE(printINDEX_STAT_REQ);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_CONF);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_REF);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_IMPL_REQ);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_IMPL_CONF);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_IMPL_REF);
+GSN_PRINT_SIGNATURE(printINDEX_STAT_REP);
+
 #endif

=== modified file 'storage/ndb/include/mgmapi/mgmapi_config_parameters.h'
--- a/storage/ndb/include/mgmapi/mgmapi_config_parameters.h	2011-04-15 13:52:53 +0000
+++ b/storage/ndb/include/mgmapi/mgmapi_config_parameters.h	2011-05-19 09:16:32 +0000
@@ -190,6 +190,14 @@
 #define CFG_NODE_ARBIT_DELAY          201
 #define CFG_RESERVED_SEND_BUFFER_MEMORY 202
 
+#define CFG_DB_INDEX_STAT_AUTO_CREATE    203
+#define CFG_DB_INDEX_STAT_AUTO_UPDATE    204
+#define CFG_DB_INDEX_STAT_SAVE_SIZE      205
+#define CFG_DB_INDEX_STAT_SAVE_SCALE     206
+#define CFG_DB_INDEX_STAT_TRIGGER_PCT    207
+#define CFG_DB_INDEX_STAT_TRIGGER_SCALE  208
+#define CFG_DB_INDEX_STAT_UPDATE_DELAY   209
+
 #define CFG_MIN_LOGLEVEL          250
 #define CFG_LOGLEVEL_STARTUP      250
 #define CFG_LOGLEVEL_SHUTDOWN     251

=== modified file 'storage/ndb/include/ndbapi/NdbDictionary.hpp'
--- a/storage/ndb/include/ndbapi/NdbDictionary.hpp	2011-02-16 14:53:53 +0000
+++ b/storage/ndb/include/ndbapi/NdbDictionary.hpp	2011-05-19 09:16:32 +0000
@@ -610,6 +610,8 @@ public:
     static const Column * OPTIMIZE;
     static const Column * FRAGMENT_EXTENT_SPACE;
     static const Column * FRAGMENT_FREE_EXTENT_SPACE;
+    static const Column * INDEX_STAT_KEY;
+    static const Column * INDEX_STAT_VALUE;
 
     int getSizeInBytes() const;
 

=== modified file 'storage/ndb/include/ndbapi/NdbScanOperation.hpp'
--- a/storage/ndb/include/ndbapi/NdbScanOperation.hpp	2011-02-09 14:18:53 +0000
+++ b/storage/ndb/include/ndbapi/NdbScanOperation.hpp	2011-05-19 09:16:32 +0000
@@ -82,7 +82,9 @@ public:
       It is enabled by default for scans using LM_Exclusive, but must be
       explicitly specified to enable the taking-over of LM_Read locks.
     */
-    SF_KeyInfo = 1
+    SF_KeyInfo = 1,
+    /* Statistics scan (INDEX_STAT) */
+    SF_StatScan = 2
   };
 
 

=== added file 'storage/ndb/src/common/debugger/signaldata/IndexStatSignal.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/IndexStatSignal.cpp	1970-01-01 00:00:00 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/IndexStatSignal.cpp	2011-05-19 09:16:32 +0000
@@ -0,0 +1,152 @@
+/* Copyright (C) 2003 MySQL AB
+
+   This program is free software; you can redistribute it and/or modify
+   it under the terms of the GNU General Public License as published by
+   the Free Software Foundation; version 2 of the License.
+
+   This program is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+   GNU General Public License for more details.
+
+   You should have received a copy of the GNU General Public License
+   along with this program; if not, write to the Free Software
+   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
+
+#include <signaldata/IndexStatSignal.hpp>
+
+static void
+get_req_rt_name(Uint32 rt, char* rt_name)
+{
+  strcpy(rt_name, "Unknown");
+#define set_req_rt_name(x) if (rt == IndexStatReq::x) strcpy(rt_name, #x)
+  set_req_rt_name(RT_UPDATE_STAT);
+  set_req_rt_name(RT_CLEAN_NEW);
+  set_req_rt_name(RT_SCAN_FRAG);
+  set_req_rt_name(RT_CLEAN_OLD);
+  set_req_rt_name(RT_START_MON);
+  set_req_rt_name(RT_DELETE_STAT);
+  set_req_rt_name(RT_STOP_MON);
+  set_req_rt_name(RT_DROP_HEAD);
+  set_req_rt_name(RT_CLEAN_ALL);
+#undef set_req_rt_name
+}
+
+static void
+get_rep_rt_name(Uint32 rt, char* rt_name)
+{
+  strcpy(rt_name, "Unknown");
+#define set_rep_rt_name(x) if (rt == IndexStatRep::x) strcpy(rt_name, #x)
+  set_rep_rt_name(RT_UPDATE_REQ);
+  set_rep_rt_name(RT_UPDATE_CONF);
+#undef set_rep_rt_name
+}
+
+bool
+printINDEX_STAT_REQ(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatReq* sig = (const IndexStatReq*)theData;
+  fprintf(output, " clientRef: 0x%x", sig->clientRef);
+  fprintf(output, " clientData: %u", sig->clientData);
+  fprintf(output, "\n");
+  Uint32 rt = sig->requestInfo & 0xFF;
+  char rt_name[40];
+  get_req_rt_name(rt, rt_name);
+  fprintf(output, " requestType: %s[%u]", rt_name, rt);
+  fprintf(output, " requestFlag: 0x%x", sig->requestFlag);
+  fprintf(output, "\n");
+  fprintf(output, " indexId: %u", sig->indexId);
+  fprintf(output, " indexVersion: %u", sig->indexVersion);
+  fprintf(output, " tableId: %u", sig->tableId);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_IMPL_REQ(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatImplReq* sig = (const IndexStatImplReq*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, "\n");
+  Uint32 rt = sig->requestType;
+  char rt_name[40];
+  get_req_rt_name(rt, rt_name);
+  fprintf(output, " requestType: %s[%u]", rt_name, rt);
+  fprintf(output, " requestFlag: 0x%x", sig->requestFlag);
+  fprintf(output, "\n");
+  fprintf(output, " indexId: %u", sig->indexId);
+  fprintf(output, " indexVersion: %u", sig->indexVersion);
+  fprintf(output, " tableId: %u", sig->tableId);
+  fprintf(output, " fragId: %u", sig->fragId);
+  fprintf(output, " fragCount: %u", sig->fragCount);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_CONF(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatConf* sig = (const IndexStatConf*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_IMPL_CONF(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatImplConf* sig = (const IndexStatImplConf*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_REF(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatRef* sig = (const IndexStatRef*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, " errorCode: %u", sig->errorCode);
+  fprintf(output, " errorLine: %u", sig->errorLine);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_IMPL_REF(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatImplRef* sig = (const IndexStatImplRef*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, " errorCode: %u", sig->errorCode);
+  fprintf(output, " errorLine: %u", sig->errorLine);
+  fprintf(output, "\n");
+  return true;
+}
+
+bool
+printINDEX_STAT_REP(FILE* output, const Uint32* theData, Uint32 len, Uint16)
+{
+  const IndexStatRep* sig = (const IndexStatRep*)theData;
+  fprintf(output, " senderRef: 0x%x", sig->senderRef);
+  fprintf(output, " senderData: %u", sig->senderData);
+  fprintf(output, "\n");
+  Uint32 rt = sig->requestType;
+  char rt_name[40];
+  get_rep_rt_name(rt, rt_name);
+  fprintf(output, " requestType: %s[%u]", rt_name, rt);
+  fprintf(output, " requestFlag: 0x%x", sig->requestFlag);
+  fprintf(output, "\n");
+  fprintf(output, " indexId: %u", sig->indexId);
+  fprintf(output, " indexVersion: %u", sig->indexVersion);
+  fprintf(output, " tableId: %u", sig->tableId);
+  fprintf(output, "\n");
+  fprintf(output, " fragId: %u", sig->fragId);
+  fprintf(output, " loadTime: %u", sig->loadTime);
+  fprintf(output, "\n");
+  return true;
+}

=== modified file 'storage/ndb/src/common/debugger/signaldata/Makefile.am'
--- a/storage/ndb/src/common/debugger/signaldata/Makefile.am	2011-04-09 15:48:21 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/Makefile.am	2011-05-19 09:16:32 +0000
@@ -46,7 +46,8 @@ libsignaldataprint_la_SOURCES = \
   	  CreateTrigImpl.cpp DropTrigImpl.cpp \
  	  CreateIndxImpl.cpp DropIndxImpl.cpp AlterIndxImpl.cpp \
  	  BuildIndx.cpp BuildIndxImpl.cpp ApiVersion.cpp \
-          LocalRouteOrd.cpp DbinfoScan.cpp NodePing.cpp
+          LocalRouteOrd.cpp DbinfoScan.cpp NodePing.cpp \
+	  IndexStatSignal.cpp
 
 include $(top_srcdir)/storage/ndb/config/common.mk.am
 include $(top_srcdir)/storage/ndb/config/type_ndbapi.mk.am

=== modified file 'storage/ndb/src/common/debugger/signaldata/ScanFrag.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/ScanFrag.cpp	2011-02-08 13:55:54 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/ScanFrag.cpp	2011-05-19 09:16:32 +0000
@@ -51,8 +51,11 @@ printSCAN_FRAGREQ(FILE * output, const U
           ScanFragReq::getAttrLen(sig->requestInfo));
   fprintf(output, " reorg: %u",
           ScanFragReq::getReorgFlag(sig->requestInfo));
-  fprintf(output, " corr: %u\n",
+  fprintf(output, " corr: %u",
           ScanFragReq::getCorrFactorFlag(sig->requestInfo));
+  fprintf(output, " stat: %u",
+          ScanFragReq::getStatScanFlag(sig->requestInfo));
+  fprintf(output, "\n");
 
   fprintf(output, " tableId: %u\n", sig->tableId);
   fprintf(output, " fragmentNo: %u\n", sig->fragmentNoKeyLen & 0xFFFF);

=== modified file 'storage/ndb/src/common/debugger/signaldata/ScanTab.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/ScanTab.cpp	2011-02-08 13:55:54 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/ScanTab.cpp	2011-05-19 09:16:32 +0000
@@ -31,7 +31,7 @@ printSCANTABREQ(FILE * output, const Uin
   fprintf(output, " apiConnectPtr: H\'%.8x", 
 	  sig->apiConnectPtr);
   fprintf(output, " requestInfo: H\'%.8x:\n",  requestInfo);
-  fprintf(output, "  Parallellism: %u Batch: %u LockMode: %u Keyinfo: %u Holdlock: %u RangeScan: %u Descending: %u TupScan: %u\n ReadCommitted: %u DistributionKeyFlag: %u NoDisk: %u spj: %u",
+  fprintf(output, "  Parallellism: %u Batch: %u LockMode: %u Keyinfo: %u Holdlock: %u RangeScan: %u Descending: %u TupScan: %u\n ReadCommitted: %u DistributionKeyFlag: %u NoDisk: %u spj: %u StatScan: %u",
 	  sig->getParallelism(requestInfo), 
 	  sig->getScanBatch(requestInfo), 
 	  sig->getLockMode(requestInfo), 
@@ -43,7 +43,8 @@ printSCANTABREQ(FILE * output, const Uin
 	  sig->getReadCommittedFlag(requestInfo),
 	  sig->getDistributionKeyFlag(requestInfo),
 	  sig->getNoDiskFlag(requestInfo),
-          sig->getViaSPJFlag(requestInfo));
+          sig->getViaSPJFlag(requestInfo),
+          sig->getStatScanFlag(requestInfo));
   
   if(sig->getDistributionKeyFlag(requestInfo))
     fprintf(output, " DKey: %x", sig->distributionKey);

=== modified file 'storage/ndb/src/common/debugger/signaldata/SchemaTransImpl.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/SchemaTransImpl.cpp	2011-02-02 00:40:07 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/SchemaTransImpl.cpp	2011-05-19 09:16:32 +0000
@@ -137,6 +137,9 @@ printSCHEMA_TRANS_IMPL_REQ(FILE* output,
     case GSN_BUILD_INDX_IMPL_REQ:
       printBUILD_INDX_IMPL_REQ(output, pb_data, pb_len, rbn);
       break;
+    case GSN_INDEX_STAT_IMPL_REQ:
+      printINDEX_STAT_IMPL_REQ(output, pb_data, pb_len, rbn);
+      break;
     default:
     {
       Uint32 i;

=== modified file 'storage/ndb/src/common/debugger/signaldata/SignalDataPrint.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/SignalDataPrint.cpp	2011-04-09 15:48:21 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/SignalDataPrint.cpp	2011-05-19 09:16:32 +0000
@@ -260,6 +260,14 @@ SignalDataPrintFunctions[] = {
   ,{ GSN_NODE_PING_REQ, printNODE_PING_REQ }
   ,{ GSN_NODE_PING_CONF, printNODE_PING_CONF }
 
+  ,{ GSN_INDEX_STAT_REQ, printINDEX_STAT_REQ }
+  ,{ GSN_INDEX_STAT_CONF, printINDEX_STAT_CONF }
+  ,{ GSN_INDEX_STAT_REF, printINDEX_STAT_REF }
+  ,{ GSN_INDEX_STAT_IMPL_REQ, printINDEX_STAT_IMPL_REQ }
+  ,{ GSN_INDEX_STAT_IMPL_CONF, printINDEX_STAT_IMPL_CONF }
+  ,{ GSN_INDEX_STAT_IMPL_REF, printINDEX_STAT_IMPL_REF }
+  ,{ GSN_INDEX_STAT_REP, printINDEX_STAT_REP }
+
   ,{ 0, 0 }
 };
 

=== modified file 'storage/ndb/src/common/debugger/signaldata/SignalNames.cpp'
--- a/storage/ndb/src/common/debugger/signaldata/SignalNames.cpp	2011-04-09 15:48:21 +0000
+++ b/storage/ndb/src/common/debugger/signaldata/SignalNames.cpp	2011-05-19 09:16:32 +0000
@@ -763,5 +763,13 @@ const GsnName SignalNames [] = {
 
   ,{ GSN_NODE_PING_REQ, "NODE_PING_REQ" }
   ,{ GSN_NODE_PING_CONF, "NODE_PING_CONF" }
+
+  ,{ GSN_INDEX_STAT_REQ, "INDEX_STAT_REQ" }
+  ,{ GSN_INDEX_STAT_CONF, "INDEX_STAT_CONF" }
+  ,{ GSN_INDEX_STAT_REF, "INDEX_STAT_REF" }
+  ,{ GSN_INDEX_STAT_IMPL_REQ, "INDEX_STAT_IMPL_REQ" }
+  ,{ GSN_INDEX_STAT_IMPL_CONF, "INDEX_STAT_IMPL_CONF" }
+  ,{ GSN_INDEX_STAT_IMPL_REF, "INDEX_STAT_IMPL_REF" }
+  ,{ GSN_INDEX_STAT_REP, "INDEX_STAT_REP" }
 };
 const unsigned short NO_OF_SIGNAL_NAMES = sizeof(SignalNames)/sizeof(GsnName);

=== modified file 'storage/ndb/src/kernel/blocks/ERROR_codes.txt'
--- a/storage/ndb/src/kernel/blocks/ERROR_codes.txt	2011-04-28 07:47:53 +0000
+++ b/storage/ndb/src/kernel/blocks/ERROR_codes.txt	2011-05-19 09:16:32 +0000
@@ -29,6 +29,7 @@ Next DBTUX 12010
 Next SUMA 13047
 Next LGMAN 15001
 Next TSMAN 16001
+Next TRIX 17xxx
 
 TESTING NODE FAILURE, ARBITRATION
 ---------------------------------
@@ -720,3 +721,15 @@ ACC bug#34348
 3002: limit frags to 2 directory pages (instead of 256)
       print (if VM_TRACE) LH variables at expand and shrink
       apply before mass data load, reset with error insert 0
+
+TRIX
+----
+Index stats:
+17001: fail to seize statOp
+17002: fail to seize associated subRec
+17011: fail HEAD read - simulate UtilExecuteRef::AllocationError
+17012: fail HEAD insert/update/delete - as in 17011
+17021: fail RT_CLEAN_NEW - simulate TC error 626
+17022: fail RT_CLEAN_OLD (non-fatal) - as in 17021
+17023: fail RT_CLEAN_ALL (non-fatal) - as in 17021
+17024: fail RT_SCAN_FRAG - simulate TC error 630

=== modified file 'storage/ndb/src/kernel/blocks/cmvmi/Cmvmi.cpp'
--- a/storage/ndb/src/kernel/blocks/cmvmi/Cmvmi.cpp	2011-05-02 13:36:19 +0000
+++ b/storage/ndb/src/kernel/blocks/cmvmi/Cmvmi.cpp	2011-05-19 09:16:32 +0000
@@ -1431,6 +1431,11 @@ void Cmvmi::execTAMPER_ORD(Signal* signa
     jam();
     tuserblockref = TSMAN_REF;
   }
+  else if (errNo < 18000)
+  {
+    jam();
+    tuserblockref = TRIX_REF;
+  }
   else if (errNo < 30000)
   {
     /*--------------------------------------------------------------------*/

=== modified file 'storage/ndb/src/kernel/blocks/dblqh/Dblqh.hpp'
--- a/storage/ndb/src/kernel/blocks/dblqh/Dblqh.hpp	2011-04-28 07:47:53 +0000
+++ b/storage/ndb/src/kernel/blocks/dblqh/Dblqh.hpp	2011-05-19 09:16:32 +0000
@@ -563,6 +563,8 @@ public:
     Uint8 scanKeyinfoFlag;
     Uint8 m_last_row;
     Uint8 m_reserved;
+    Uint8 statScan;
+    Uint8 dummy[3]; // align?
   }; // Size 272 bytes
   typedef Ptr<ScanRecord> ScanRecordPtr;
 

=== modified file 'storage/ndb/src/kernel/blocks/dblqh/DblqhMain.cpp'
--- a/storage/ndb/src/kernel/blocks/dblqh/DblqhMain.cpp	2011-04-28 12:04:11 +0000
+++ b/storage/ndb/src/kernel/blocks/dblqh/DblqhMain.cpp	2011-05-19 09:16:32 +0000
@@ -3396,6 +3396,8 @@ Dblqh::execREAD_PSEUDO_REQ(Signal* signa
     break;
   }
   case AttributeHeader::RECORDS_IN_RANGE:
+  case AttributeHeader::INDEX_STAT_KEY:
+  case AttributeHeader::INDEX_STAT_VALUE:
   {
     jam();
     // scanptr gets reset somewhere within the timeslice
@@ -10445,6 +10447,7 @@ void Dblqh::continueAfterReceivingAllAiL
   AccScanReq::setLockMode(req->requestInfo, scanptr.p->scanLockMode);
   AccScanReq::setReadCommittedFlag(req->requestInfo, scanptr.p->readCommitted);
   AccScanReq::setDescendingFlag(req->requestInfo, scanptr.p->descending);
+  AccScanReq::setStatScanFlag(req->requestInfo, scanptr.p->statScan);
 
   if (refToMain(tcConnectptr.p->clientBlockref) == BACKUP)
   {
@@ -11516,6 +11519,7 @@ Uint32 Dblqh::initScanrec(const ScanFrag
   scanptr.p->descending = descending;
   scanptr.p->tupScan = tupScan;
   scanptr.p->lcpScan = ScanFragReq::getLcpScanFlag(reqinfo);
+  scanptr.p->statScan = ScanFragReq::getStatScanFlag(reqinfo);
   scanptr.p->scanState = ScanRecord::SCAN_FREE;
   scanptr.p->scanFlag = ZFALSE;
   scanptr.p->m_row_id.setNull();

=== modified file 'storage/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp'
--- a/storage/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp	2011-05-03 13:48:54 +0000
+++ b/storage/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp	2011-05-19 09:16:32 +0000
@@ -10614,6 +10614,7 @@ Dbtc::initScanrec(ScanRecordPtr scanptr,
   ScanFragReq::setDescendingFlag(tmp, ScanTabReq::getDescendingFlag(ri));
   ScanFragReq::setTupScanFlag(tmp, ScanTabReq::getTupScanFlag(ri));
   ScanFragReq::setNoDiskFlag(tmp, ScanTabReq::getNoDiskFlag(ri));
+  ScanFragReq::setStatScanFlag(tmp, ScanTabReq::getStatScanFlag(ri));
   if (ScanTabReq::getViaSPJFlag(ri))
   {
     jam();

=== modified file 'storage/ndb/src/kernel/blocks/dbtup/DbtupRoutines.cpp'
--- a/storage/ndb/src/kernel/blocks/dbtup/DbtupRoutines.cpp	2011-04-13 08:51:04 +0000
+++ b/storage/ndb/src/kernel/blocks/dbtup/DbtupRoutines.cpp	2011-05-19 09:16:32 +0000
@@ -2418,7 +2418,8 @@ Dbtup::read_pseudo(const Uint32 * inBuff
   Uint32* outBuffer = outBuf + ((outPos - 1) >> 2);
   
   Uint32 sz;
-  SignalT<4> signalT;
+  const Uint32 DataSz = MAX_INDEX_STAT_KEY_SIZE;
+  SignalT<DataSz> signalT;
   Signal * signal = new (&signalT) Signal(0);
   bzero(signal, sizeof(signalT));
   switch(attrId){
@@ -2488,6 +2489,23 @@ Dbtup::read_pseudo(const Uint32 * inBuff
     outBuffer[4] = signal->theData[3];
     sz = 4;
     break;
+  case AttributeHeader::INDEX_STAT_KEY:
+  case AttributeHeader::INDEX_STAT_VALUE:
+  {
+    signal->theData[0] = req_struct->operPtrP->userpointer;
+    signal->theData[1] = attrId;
+
+    EXECUTE_DIRECT(DBLQH, GSN_READ_PSEUDO_REQ, signal, 2);
+
+    const Uint8* src = (Uint8*)&signal->theData[0];
+    Uint32 byte_sz = 2 + src[0] + (src[1] << 8);
+    Uint8* dst = (Uint8*)&outBuffer[1];
+    memcpy(dst, src, byte_sz);
+    while (byte_sz % 4 != 0)
+      dst[byte_sz++] = 0;
+    sz = byte_sz / 4;
+    break;
+  }
   case AttributeHeader::ROWID:
     outBuffer[1] = req_struct->frag_page_id;
     outBuffer[2] = req_struct->operPtrP->m_tuple_location.m_page_idx;

=== modified file 'storage/ndb/src/kernel/blocks/ndbcntr/Ndbcntr.hpp'
--- a/storage/ndb/src/kernel/blocks/ndbcntr/Ndbcntr.hpp	2011-02-03 14:20:36 +0000
+++ b/storage/ndb/src/kernel/blocks/ndbcntr/Ndbcntr.hpp	2011-05-19 09:16:32 +0000
@@ -117,6 +117,18 @@ public:
     bool keyFlag;
     bool nullable;
   };
+  struct SysIndex {
+    const char* name;
+    Uint32 columnCount;
+    Uint32 columnList[4];
+    // DictTabInfo
+    DictTabInfo::TableType indexType;
+    bool indexLoggedFlag;
+    // saved id (initially set only at creating node)
+    mutable Uint32 tableId;
+    mutable Uint32 indexId;
+    mutable Uint32 indexVersion;
+  };
   struct SysTable {
     const char* name;
     unsigned columnCount;
@@ -125,27 +137,21 @@ public:
     DictTabInfo::TableType tableType;
     DictTabInfo::FragmentType fragmentType;
     bool tableLoggedFlag;
-    // saved table id
+    // indexes
+    Uint32 indexCount;
+    const SysIndex** indexList;
+    // saved id (initially set only at creating node)
     mutable Uint32 tableId;
     mutable Uint32 tableVersion;
   };
-  struct SysIndex {
-    const char* name;
-    const SysTable* primaryTable;
-    Uint32 columnCount;
-    Uint32 columnList[4];
-    // DictTabInfo
-    DictTabInfo::TableType indexType;
-    DictTabInfo::FragmentType fragmentType;
-    bool indexLoggedFlag;
-    // saved index table id
-    mutable Uint32 indexId;
-  };
   static const SysTable* g_sysTableList[];
   static const unsigned g_sysTableCount;
   // the system tables
   static const SysTable g_sysTable_SYSTAB_0;
   static SysTable g_sysTable_NDBEVENTS_0;
+  static const SysTable g_sysTable_NDBIS_HEAD;
+  static const SysTable g_sysTable_NDBIS_SAMPLE;
+  static const SysIndex g_sysIndex_NDBIS_SAMPLE_X1;
   // schema trans
   Uint32 c_schemaTransId;
   Uint32 c_schemaTransKey;
@@ -195,6 +201,8 @@ private:
   void execSCHEMA_TRANS_END_REF(Signal* signal);
   void execCREATE_TABLE_REF(Signal* signal);
   void execCREATE_TABLE_CONF(Signal* signal);
+  void execCREATE_INDX_REF(Signal* signal);
+  void execCREATE_INDX_CONF(Signal* signal);
   void execCREATE_HASH_MAP_REF(Signal* signal);
   void execCREATE_HASH_MAP_CONF(Signal* signal);
   void execCREATE_FILEGROUP_REF(Signal* signal);
@@ -244,7 +252,8 @@ private:
   void systemErrorLab(Signal* signal, int line);
 
   void createHashMap(Signal*, Uint32 index);
-  void createSystableLab(Signal* signal, unsigned index);
+  void createSystableLab(Signal* signal, Uint32 ti);
+  void createSysindexLab(Signal* signal, Uint32 ti, Uint32 xi);
   void createDDObjects(Signal*, unsigned index);
   void crSystab7Lab(Signal* signal);
   void crSystab8Lab(Signal* signal);

=== modified file 'storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrInit.cpp'
--- a/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrInit.cpp	2011-02-01 23:27:25 +0000
+++ b/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrInit.cpp	2011-05-19 09:16:32 +0000
@@ -87,6 +87,8 @@ Ndbcntr::Ndbcntr(Block_context& ctx):
   addRecSignal(GSN_SCHEMA_TRANS_END_REF, &Ndbcntr::execSCHEMA_TRANS_END_REF);
   addRecSignal(GSN_CREATE_TABLE_REF, &Ndbcntr::execCREATE_TABLE_REF);
   addRecSignal(GSN_CREATE_TABLE_CONF, &Ndbcntr::execCREATE_TABLE_CONF);
+  addRecSignal(GSN_CREATE_INDX_REF, &Ndbcntr::execCREATE_INDX_REF);
+  addRecSignal(GSN_CREATE_INDX_CONF, &Ndbcntr::execCREATE_INDX_CONF);
   addRecSignal(GSN_CREATE_HASH_MAP_REF, &Ndbcntr::execCREATE_HASH_MAP_REF);
   addRecSignal(GSN_CREATE_HASH_MAP_CONF, &Ndbcntr::execCREATE_HASH_MAP_CONF);
   addRecSignal(GSN_CREATE_FILEGROUP_REF, &Ndbcntr::execCREATE_FILEGROUP_REF);

=== modified file 'storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrMain.cpp'
--- a/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrMain.cpp	2011-04-15 13:52:53 +0000
+++ b/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrMain.cpp	2011-05-19 09:16:32 +0000
@@ -24,6 +24,7 @@
 #include <signaldata/DictTabInfo.hpp>
 #include <signaldata/SchemaTrans.hpp>
 #include <signaldata/CreateTable.hpp>
+#include <signaldata/CreateIndx.hpp>
 #include <signaldata/CreateHashMap.hpp>
 #include <signaldata/ReadNodesConf.hpp>
 #include <signaldata/NodeFailRep.hpp>
@@ -2406,16 +2407,16 @@ Ndbcntr::execCREATE_FILE_CONF(Signal* si
   createDDObjects(signal, conf->senderData + 1);
 }
 
-void Ndbcntr::createSystableLab(Signal* signal, unsigned index)
+void Ndbcntr::createSystableLab(Signal* signal, Uint32 ti)
 {
-  if (index >= g_sysTableCount) {
-    ndbassert(index == g_sysTableCount);
+  if (ti >= g_sysTableCount) {
+    ndbassert(ti == g_sysTableCount);
     createDDObjects(signal, 0);
     return;
   }
-  const SysTable& table = *g_sysTableList[index];
-  Uint32 propPage[256];
-  LinearWriter w(propPage, 256);
+  const SysTable& table = *g_sysTableList[ti];
+  Uint32 propPage[1024];
+  LinearWriter w(propPage, 1024);
 
   // XXX remove commented-out lines later
 
@@ -2436,7 +2437,8 @@ void Ndbcntr::createSystableLab(Signal*
   w.add(DictTabInfo::HashMapObjectId, c_hashMapId);
   w.add(DictTabInfo::HashMapVersion, c_hashMapVersion);
 
-  for (unsigned i = 0; i < table.columnCount; i++) {
+  Uint32 i;
+  for (i = 0; i < table.columnCount; i++) {
     const SysColumn& column = table.columnList[i];
     ndbassert(column.pos == i);
     w.add(DictTabInfo::AttributeName, column.name);
@@ -2445,11 +2447,13 @@ void Ndbcntr::createSystableLab(Signal*
     w.add(DictTabInfo::AttributeStorageType, 
 	  (Uint32)NDB_STORAGETYPE_MEMORY);
     switch(column.type){
+    case DictTabInfo::ExtVarchar:
     case DictTabInfo::ExtVarbinary:
       jam();
       w.add(DictTabInfo::AttributeArrayType,
             (Uint32)NDB_ARRAYTYPE_SHORT_VAR);
       break;
+    case DictTabInfo::ExtLongvarchar:
     case DictTabInfo::ExtLongvarbinary:
       jam();
       w.add(DictTabInfo::AttributeArrayType,
@@ -2475,10 +2479,12 @@ void Ndbcntr::createSystableLab(Signal*
 
   CreateTableReq* const req = (CreateTableReq*)signal->getDataPtrSend();
   req->clientRef = reference();
-  req->clientData = index;
+  req->clientData = ti;
   req->requestInfo = 0;
   req->transId = c_schemaTransId;
   req->transKey = c_schemaTransKey;
+
+  D("create table" << V(ti) << V(table.name));
   sendSignal(DBDICT_REF, GSN_CREATE_TABLE_REQ, signal,
 	     CreateTableReq::SignalLength, JBB, ptr, 1);
   return;
@@ -2487,6 +2493,9 @@ void Ndbcntr::createSystableLab(Signal*
 void Ndbcntr::execCREATE_TABLE_REF(Signal* signal) 
 {
   jamEntry();
+  const CreateTableRef* ref = (const CreateTableRef*)signal->getDataPtr();
+  ndbout << "CreateTableRef" << " errorCode=" << ref->errorCode
+         << " errorLine=" << ref->errorLine << endl;
   progError(__LINE__,NDBD_EXIT_NDBREQUIRE, "CREATE_TABLE_REF");
   return;
 }//Ndbcntr::execDICTTABREF()
@@ -2495,14 +2504,92 @@ void Ndbcntr::execCREATE_TABLE_CONF(Sign
 {
   jamEntry();
   const CreateTableConf* conf = (const CreateTableConf*)signal->getDataPtr();
-  //csystabId = conf->tableId;
   ndbrequire(conf->transId == c_schemaTransId);
-  ndbrequire(conf->senderData < g_sysTableCount);
-  const SysTable& table = *g_sysTableList[conf->senderData];
+  const Uint32 ti = conf->clientData;
+  ndbrequire(ti < g_sysTableCount);
+  const SysTable& table = *g_sysTableList[ti];
   table.tableId = conf->tableId;
   table.tableVersion = conf->tableVersion;
-  createSystableLab(signal, conf->senderData + 1);
-  //startInsertTransactions(signal);
+  createSysindexLab(signal, ti, 0);
+  return;
+}//Ndbcntr::execDICTTABCONF()
+
+void Ndbcntr::createSysindexLab(Signal* signal, Uint32 ti, Uint32 xi)
+{
+  ndbrequire(ti < g_sysTableCount);
+  const SysTable& table = *g_sysTableList[ti];
+  if (xi >= table.indexCount) {
+    ndbassert(xi == table.indexCount);
+    createSystableLab(signal, ti + 1);
+    return;
+  }
+
+  ndbrequire(table.indexList[xi] != 0);
+  const SysIndex& index = *table.indexList[xi];
+  CreateIndxReq* const req = (CreateIndxReq*)signal->getDataPtrSend();
+  req->clientRef = reference();
+  req->clientData = ti | (xi << 8);
+  req->transId = c_schemaTransId;
+  req->transKey = c_schemaTransKey;
+  req->requestInfo = 0;
+  req->tableId = table.tableId;
+  req->tableVersion = table.tableVersion;
+  req->indexType = index.indexType;
+  req->online = 1;
+
+  LinearSectionPtr ptr[3];
+
+  Uint32 attr[1 + 32];
+  attr[0] = index.columnCount;
+  memcpy(&attr[1], index.columnList, index.columnCount * 4);
+  ptr[0].p = attr;
+  ptr[0].sz = 1 + index.columnCount;
+
+  Uint32 propPage[256];
+  LinearWriter w(propPage, 256);
+  w.first();
+  char name[MAX_TAB_NAME_SIZE];
+  sprintf(name, index.name, table.tableId);
+  w.add(DictTabInfo::TableName, name);
+  w.add(DictTabInfo::TableLoggedFlag, index.indexLoggedFlag);
+  w.add(DictTabInfo::TableEnd, (Uint32)true);
+  Uint32 length = w.getWordsUsed();
+  ptr[1].p = &propPage[0];
+  ptr[1].sz = length;
+
+  D("create index" << V(ti) << V(xi) << V(name));
+  sendSignal(DBDICT_REF, GSN_CREATE_INDX_REQ, signal,
+             CreateIndxReq::SignalLength, JBB, ptr, 2);
+}
+
+void Ndbcntr::execCREATE_INDX_REF(Signal* signal)
+{
+  jamEntry();
+  const CreateIndxRef* ref = (const CreateIndxRef*)signal->getDataPtr();
+  ndbout << "CreateIndxRef" << " errorCode=" << ref->errorCode
+         << " errorLine=" << ref->errorLine << endl;
+  progError(__LINE__,NDBD_EXIT_NDBREQUIRE, "CREATE_INDX_REF");
+  return;
+}//Ndbcntr::execDICTTABREF()
+
+void Ndbcntr::execCREATE_INDX_CONF(Signal* signal)
+{
+  jamEntry();
+  const CreateIndxConf* conf = (const CreateIndxConf*)signal->getDataPtr();
+  ndbrequire(conf->transId == c_schemaTransId);
+
+  const Uint32 ti = conf->clientData & 0xFF;
+  const Uint32 xi = conf->clientData >> 8;
+  ndbrequire(ti < g_sysTableCount);
+  const SysTable& table = *g_sysTableList[ti];
+  ndbrequire(xi < table.indexCount);
+  ndbrequire(table.indexList[xi] != 0);
+  const SysIndex& index = *table.indexList[xi];
+
+  index.tableId = table.tableId;
+  index.indexId = conf->indexId;
+  index.indexVersion = conf->indexVersion;
+  createSysindexLab(signal, ti, xi + 1);
   return;
 }//Ndbcntr::execDICTTABCONF()
 

=== modified file 'storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrSysTable.cpp'
--- a/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrSysTable.cpp	2011-02-01 23:27:25 +0000
+++ b/storage/ndb/src/kernel/blocks/ndbcntr/NdbcntrSysTable.cpp	2011-05-19 09:16:32 +0000
@@ -39,7 +39,7 @@ Ndbcntr::g_sysTable_SYSTAB_0 = {
   arrayLength(column_SYSTAB_0), column_SYSTAB_0,
   DictTabInfo::SystemTable,
   DictTabInfo::HashMapPartition,
-  true, ~0, ~0
+  true, 0, 0, ~0, ~0
 };
 
 // NDB$EVENTS_0
@@ -90,7 +90,113 @@ Ndbcntr::g_sysTable_NDBEVENTS_0 = {
   arrayLength(column_NDBEVENTS_0), column_NDBEVENTS_0,
   DictTabInfo::SystemTable,
   DictTabInfo::HashMapPartition,
-  true, ~0, ~0
+  true, 0, 0, ~0, ~0
+};
+
+// NDB$IS_HEAD
+
+static const Ndbcntr::SysColumn
+column_NDBIS_HEAD[] = {
+  // key must be first
+  { 0, "INDEX_ID",
+    DictTabInfo::ExtUnsigned, 1,
+    true, false
+  },
+  { 1, "INDEX_VERSION",
+    DictTabInfo::ExtUnsigned, 1,
+    true, false
+  },
+  // table
+  { 2, "TABLE_ID",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  { 3, "FRAG_COUNT",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  { 4, "VALUE_FORMAT",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  // current sample
+  { 5, "SAMPLE_VERSION",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  { 6, "LOAD_TIME",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  { 7, "SAMPLE_COUNT",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  },
+  { 8, "KEY_BYTES",
+    DictTabInfo::ExtUnsigned, 1,
+    false, false
+  }
+};
+
+const Ndbcntr::SysTable
+Ndbcntr::g_sysTable_NDBIS_HEAD = {
+  "sys/def/NDB$IS_HEAD",
+  arrayLength(column_NDBIS_HEAD), column_NDBIS_HEAD,
+  DictTabInfo::SystemTable,
+  DictTabInfo::HashMapPartition,
+  true, 0, 0, ~0, ~0
+};
+
+// NDB$IS_SAMPLE
+
+static const Ndbcntr::SysColumn
+column_NDBIS_SAMPLE[] = {
+  // key must be first
+  { 0, "INDEX_ID",
+    DictTabInfo::ExtUnsigned, 1,
+    true, false
+  },
+  { 1, "INDEX_VERSION",
+    DictTabInfo::ExtUnsigned, 1,
+    true, false
+  },
+  { 2, "SAMPLE_VERSION",
+    DictTabInfo::ExtUnsigned, 1,
+    true, false
+  },
+  { 3, "STAT_KEY",
+    DictTabInfo::ExtLongvarbinary, MAX_INDEX_STAT_KEY_SIZE * 4,
+    true, false
+  },
+  // value
+  { 4, "STAT_VALUE",
+    DictTabInfo::ExtLongvarbinary, MAX_INDEX_STAT_VALUE_CSIZE * 4,
+    false, false
+  }
+};
+
+const Ndbcntr::SysIndex
+Ndbcntr::g_sysIndex_NDBIS_SAMPLE_X1 = {
+    "sys/def/%u/NDB$IS_SAMPLE_X1",
+    3, { 0, 1, 2, ~0 },
+    DictTabInfo::OrderedIndex,
+    false, ~0, ~0, ~0
+};
+
+static const Ndbcntr::SysIndex*
+index_NDBIS_SAMPLE[] = {
+  &Ndbcntr::g_sysIndex_NDBIS_SAMPLE_X1
+};
+
+const Ndbcntr::SysTable
+Ndbcntr::g_sysTable_NDBIS_SAMPLE = {
+  "sys/def/NDB$IS_SAMPLE",
+  arrayLength(column_NDBIS_SAMPLE), column_NDBIS_SAMPLE,
+  DictTabInfo::SystemTable,
+  DictTabInfo::HashMapPartition,
+  true,
+  arrayLength(index_NDBIS_SAMPLE), index_NDBIS_SAMPLE,
+  ~0, ~0
 };
 
 // all
@@ -98,7 +204,9 @@ Ndbcntr::g_sysTable_NDBEVENTS_0 = {
 const Ndbcntr::SysTable*
 Ndbcntr::g_sysTableList[] = {
   &g_sysTable_SYSTAB_0,
-  &g_sysTable_NDBEVENTS_0
+  &g_sysTable_NDBEVENTS_0,
+  &g_sysTable_NDBIS_HEAD,
+  &g_sysTable_NDBIS_SAMPLE
 };
 
 //TODO Backup needs this info to allocate appropriate number of records

=== modified file 'storage/ndb/src/mgmsrv/ConfigInfo.cpp'
--- a/storage/ndb/src/mgmsrv/ConfigInfo.cpp	2011-04-19 13:47:33 +0000
+++ b/storage/ndb/src/mgmsrv/ConfigInfo.cpp	2011-05-19 09:16:32 +0000
@@ -1985,6 +1985,114 @@ const ConfigInfo::ParamInfo ConfigInfo::
     STR_VALUE(MAX_INT_RNIL)      /* Max */
   },
 
+  /* ordered index stats */
+
+  {
+    CFG_DB_INDEX_STAT_AUTO_CREATE,
+    "IndexStatAutoCreate",
+    DB_TOKEN,
+    "Make create index also create initial index stats",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "0",
+    "0",
+    "1"
+  },
+
+  {
+    CFG_DB_INDEX_STAT_AUTO_UPDATE,
+    "IndexStatAutoUpdate",
+    DB_TOKEN,
+    "Monitor each index for changes and trigger automatic stats updates."
+    " See IndexStatTrigger options",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "0",
+    "0",
+    "1"
+  },
+
+  {
+    CFG_DB_INDEX_STAT_SAVE_SIZE,
+    "IndexStatSaveSize",
+    DB_TOKEN,
+    "Maximum bytes allowed for the saved stats of one index."
+    " At least 1 sample is produced regardless of size limit."
+    " The size is scaled up by a factor from IndexStatSaveScale."
+    " The value affects size of stats saved in NDB system tables"
+    " and in mysqld memory cache",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "32768",
+    "0",
+    STR_VALUE(MAX_INT_RNIL)
+  },
+
+  {
+    CFG_DB_INDEX_STAT_SAVE_SCALE,
+    "IndexStatSaveScale",
+    DB_TOKEN,
+    "Factor to scale up IndexStatSaveSize for a large index."
+    " Given in units of 0.01."
+    " Multiplied by a logarithmic index size."
+    " Value 0 disables scaling",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "100",
+    "0",
+    STR_VALUE(MAX_INT_RNIL)
+  },
+
+  {
+    CFG_DB_INDEX_STAT_TRIGGER_PCT,
+    "IndexStatTriggerPct",
+    DB_TOKEN,
+    "Percent change (in DML ops) to schedule index stats update."
+    " The value is scaled down by a factor from IndexStatTriggerScale."
+    " Value 0 disables the trigger",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "100",
+    "0",
+    STR_VALUE(MAX_INT_RNIL)
+  },
+
+  {
+    CFG_DB_INDEX_STAT_TRIGGER_SCALE,
+    "IndexStatTriggerScale",
+    DB_TOKEN,
+    "Factor to scale down IndexStatTriggerPct for a large index."
+    " Given in units of 0.01."
+    " Multiplied by a logarithmic index size."
+    " Value 0 disables scaling",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "100",
+    "0",
+    STR_VALUE(MAX_INT_RNIL)
+  },
+
+  {
+    CFG_DB_INDEX_STAT_UPDATE_DELAY,
+    "IndexStatUpdateDelay",
+    DB_TOKEN,
+    "Minimum delay in seconds between automatic index stats updates"
+    " for a given index."
+    " Value 0 means no delay",
+    ConfigInfo::CI_USED,
+    0,
+    ConfigInfo::CI_INT,
+    "60",
+    "0",
+    STR_VALUE(MAX_INT_RNIL)
+  },
+
   /***************************************************************************
    * API
    ***************************************************************************/

=== modified file 'storage/ndb/src/ndbapi/NdbDictionaryImpl.cpp'
--- a/storage/ndb/src/ndbapi/NdbDictionaryImpl.cpp	2011-05-12 09:01:21 +0000
+++ b/storage/ndb/src/ndbapi/NdbDictionaryImpl.cpp	2011-05-19 09:16:32 +0000
@@ -392,6 +392,10 @@ NdbColumnImpl::create_pseudo_columns()
     NdbColumnImpl::create_pseudo("NDB$LOCK_REF");
   NdbDictionary::Column::OP_ID = 
     NdbColumnImpl::create_pseudo("NDB$OP_ID");
+  NdbDictionary::Column::INDEX_STAT_KEY =
+    NdbColumnImpl::create_pseudo("NDB$INDEX_STAT_KEY");
+  NdbDictionary::Column::INDEX_STAT_VALUE =
+    NdbColumnImpl::create_pseudo("NDB$INDEX_STAT_VALUE");
 }
 
 void
@@ -437,6 +441,11 @@ NdbColumnImpl::destory_pseudo_columns()
   delete NdbDictionary::Column::OP_ID;
   NdbDictionary::Column::LOCK_REF = 0;
   NdbDictionary::Column::OP_ID = 0;
+
+  delete NdbDictionary::Column::INDEX_STAT_KEY;
+  delete NdbDictionary::Column::INDEX_STAT_VALUE;
+  NdbDictionary::Column::INDEX_STAT_KEY = 0;
+  NdbDictionary::Column::INDEX_STAT_VALUE = 0;
 }
 
 NdbDictionary::Column *
@@ -534,6 +543,16 @@ NdbColumnImpl::create_pseudo(const char
     col->m_impl.m_attrId = AttributeHeader::OP_ID;
     col->m_impl.m_attrSize = 8;
     col->m_impl.m_arraySize = 1;
+  } else if (!strcmp(name, "NDB$INDEX_STAT_KEY")){
+    col->setType(NdbDictionary::Column::Longvarbinary);
+    col->m_impl.m_attrId = AttributeHeader::INDEX_STAT_KEY;
+    col->m_impl.m_attrSize = 1;
+    col->m_impl.m_arraySize = 2 + MAX_INDEX_STAT_KEY_SIZE * 4;;
+  } else if (!strcmp(name, "NDB$INDEX_STAT_VALUE")){
+    col->setType(NdbDictionary::Column::Longvarbinary);
+    col->m_impl.m_attrId = AttributeHeader::INDEX_STAT_VALUE;
+    col->m_impl.m_attrSize = 1;
+    col->m_impl.m_arraySize = 2 + MAX_INDEX_STAT_VALUE_SIZE * 4;
   }
   else {
     abort();
@@ -8433,4 +8452,7 @@ const NdbDictionary::Column * NdbDiction
 const NdbDictionary::Column * NdbDictionary::Column::LOCK_REF = 0;
 const NdbDictionary::Column * NdbDictionary::Column::OP_ID = 0;
 
+const NdbDictionary::Column * NdbDictionary::Column::INDEX_STAT_KEY = 0;
+const NdbDictionary::Column * NdbDictionary::Column::INDEX_STAT_VALUE = 0;
+
 template class Vector<NdbDictInterface::Tx::Op>;

=== modified file 'storage/ndb/src/ndbapi/ndberror.c'
--- a/storage/ndb/src/ndbapi/ndberror.c	2011-05-07 06:17:02 +0000
+++ b/storage/ndb/src/ndbapi/ndberror.c	2011-05-19 09:16:32 +0000
@@ -449,6 +449,13 @@ ErrorBundle ErrorCodes[] = {
   { 908,  DMEC, IS, "Invalid ordered index tree node size" },
   { 909,  DMEC, IE, "No free index scan op" },
   { 910, HA_ERR_NO_SUCH_TABLE, SE, "Index is being dropped" },
+  { 913,  DMEC, AE, "Invalid index for index state update" },
+  { 914,  DMEC, IE, "Invalid index stats request" },
+  { 915,  DMEC, TR, "No free index stats op" },
+  { 916,  DMEC, IE, "Invalid index stats sys tables" },
+  { 917,  DMEC, IE, "Invalid index stats sys tables data" },
+  { 918,  DMEC, TR, "Cannot prepare index stats update" },
+  { 919,  DMEC, TR, "Cannot execute index stats update" },
   { 1224, HA_WRONG_CREATE_OPTION, SE, "Too many fragments" },
   { 1225, DMEC, SE, "Table not defined in local query handler" },
   { 1226, DMEC, SE, "Table is being dropped" },
@@ -529,6 +536,16 @@ ErrorBundle ErrorCodes[] = {
   { 1702, DMEC, AE, "Node already connected" },
   { 1703, DMEC, IT, "Node failure handling not completed" },
   { 1704, DMEC, AE, "Node type mismatch" },
+
+  /*
+   * Index stats error codes
+   */
+  { 4714, DMEC, AE, "Index stats sys tables NDB$IS are invalid" },
+  { 4715, DMEC, AE, "Index stats for specified index do not exist" },
+  { 4716, DMEC, AE, "Index stats methods usage error" },
+  { 4717, DMEC, AE, "Index stats cannot allocate memory" },
+  { 4718, DMEC, IE, "Index stats memory cache is corrupted" },
+  { 4719, DMEC, IE, "Index stats internal error" },
   
   /**
    * Still uncategorized
@@ -554,6 +571,7 @@ ErrorBundle ErrorCodes[] = {
   { 1425, DMEC, SE, "Subscription being defined...while trying to stop subscriber" },
   { 1426, DMEC, SE, "No such subscriber" },
   { 1427, DMEC, NR, "Api node died, when SUB_START_REQ reached node "},
+  { 1428, DMEC, IE, "No replica to scan on this node (internal index stats error)" },
 
   { 4004, DMEC, AE, "Attribute name or id not found in the table" },
   

=== modified file 'storage/ndb/tools/restore/Restore.cpp'
--- a/storage/ndb/tools/restore/Restore.cpp	2011-04-04 09:41:30 +0000
+++ b/storage/ndb/tools/restore/Restore.cpp	2011-05-19 09:16:32 +0000
@@ -523,6 +523,9 @@ RestoreMetaData::markSysTables()
         strcmp(tableName, "NDB$EVENTS_0") == 0 ||
         strcmp(tableName, "sys/def/SYSTAB_0") == 0 ||
         strcmp(tableName, "sys/def/NDB$EVENTS_0") == 0 ||
+        // index stats tables and indexes
+        strncmp(tableName, "NDB$IS_", 7) == 0 ||
+        strstr(tableName, "/NDB$IS_") != 0 ||
         /*
           The following is for old MySQL versions,
            before we changed the database name of the tables from

=== modified file 'storage/ndb/tools/restore/consumer_restore.cpp'
--- a/storage/ndb/tools/restore/consumer_restore.cpp	2011-03-24 10:00:24 +0000
+++ b/storage/ndb/tools/restore/consumer_restore.cpp	2011-05-19 09:16:32 +0000
@@ -1794,7 +1794,8 @@ BackupRestore::table(const TableS & tabl
   
   const NdbTableImpl & tmptab = NdbTableImpl::getImpl(* table.m_dictTable);
   if ((int) tmptab.m_indexType != (int) NdbDictionary::Index::Undefined){
-    m_indexes.push_back(table.m_dictTable);
+    if (!table.getSysTable())
+      m_indexes.push_back(table.m_dictTable);
     return true;
   }
   


Attachment: [text/bzr-bundle] bzr/pekka@mysql.com-20110519091632-nn66goh3rsfee289.bundle
Thread
bzr commit into mysql-5.1-telco-7.0-wl4163 branch (pekka:4374) WL#4124Pekka Nousiainen19 May