From bd653371c5b3f2198f2d2cf7608b037c88014ca3 Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 7 Jan 2005 15:11:32 +0100 Subject: [PATCH 01/23] updated docs on event --- ndb/include/ndbapi/NdbEventOperation.hpp | 71 +++++++++++++----------- ndb/src/ndbapi/Ndb.cpp | 9 ++- ndb/src/ndbapi/NdbEventOperationImpl.cpp | 34 ++++++------ 3 files changed, 62 insertions(+), 52 deletions(-) diff --git a/ndb/include/ndbapi/NdbEventOperation.hpp b/ndb/include/ndbapi/NdbEventOperation.hpp index c695b5acd86..a0004558b39 100644 --- a/ndb/include/ndbapi/NdbEventOperation.hpp +++ b/ndb/include/ndbapi/NdbEventOperation.hpp @@ -24,73 +24,78 @@ class NdbEventOperationImpl; * @class NdbEventOperation * @brief Class of operations for getting change events from database. * - * An NdbEventOperation object is instantiated by - * Ndb::createEventOperation + * Brief description on how to work with events: * - * Prior to that an event must have been created in the Database through - * NdbDictionary::createEvent - * - * The instance is removed by Ndb::dropEventOperation + * - An event i created in the Database through + * NdbDictionary::Dictionary::createEvent() (note that this can be done + * by any application or thread and not necessarily by the "listener") + * - To listen to events, an NdbEventOperation object is instantiated by + * Ndb::createEventOperation() + * - execute() starts the event flow. Use Ndb::pollEvents() to wait + * for an event to occur. Use next() to iterate + * through the events that have occured. + * - The instance is removed by Ndb::dropEventOperation() * * For more info see: * @ref ndbapi_event.cpp * * Known limitations: * - * Maximum number of active NdbEventOperations are now set at compile time. + * - Maximum number of active NdbEventOperations are now set at compile time. * Today 100. This will become a configuration parameter later. - * - * Maximum number of NdbEventOperations tied to same event are maximum 16 + * - Maximum number of NdbEventOperations tied to same event are maximum 16 * per process. * * Known issues: * - * When several NdbEventOperation's are tied to the same event in the same + * - When several NdbEventOperation's are tied to the same event in the same * process they will share the circular buffer. The BufferLength will then * be the same for all and decided by the first NdbEventOperation * instantiation. Just make sure to instantiate the "largest" one first. - * - * Today all events INSERT/DELETE/UPDATE and all changed attributes are + * - Today all events INSERT/DELETE/UPDATE and all changed attributes are * sent to the API, even if only specific attributes have been specified. * These are however hidden from the user and only relevant data is shown * after next(). - * However false exits from Ndb::pollEvents() may occur and thus + * - "False" exits from Ndb::pollEvents() may occur and thus * the subsequent next() will return zero, * since there was no available data. Just do Ndb::pollEvents() again. - * - * Event code does not check table schema version. Make sure to drop events + * - Event code does not check table schema version. Make sure to drop events * after table is dropped. Will be fixed in later * versions. - * - * If a node failure has occured not all events will be recieved + * - If a node failure has occured not all events will be recieved * anymore. Drop NdbEventOperation and Create again after nodes are up * again. Will be fixed in later versions. * * Test status: - * Tests have been run on 1-node and 2-node systems * - * Known bugs: - * - * None, except if we can call some of the "issues" above bugs + * - Tests have been run on 1-node and 2-node systems * * Useful API programs: * - * ndb_select_all -d sys 'NDB$EVENTS_0' - * Will show contents in the system table containing created events. + * - ndb_select_all -d sys 'NDB$EVENTS_0' + * shows contents in the system table containing created events. * + * @note this is an inteface to viewing events that is subject to change */ class NdbEventOperation { public: + /** + * State of the NdbEventOperation object + */ + enum State { + EO_CREATED, ///< Created but execute() not called + EO_EXECUTING, ///< execute() called + EO_ERROR ///< An error has occurred. Object unusable. + }; /** * Retrieve current state of the NdbEventOperation object */ - enum State {CREATED,EXECUTING,ERROR}; State getState(); /** * Activates the NdbEventOperation to start receiving events. The * changed attribute values may be retrieved after next() has returned - * a value greater than zero. The getValue() methods below must be called + * a value greater than zero. The getValue() methods must be called * prior to execute(). * * @return 0 if successful otherwise -1. @@ -112,21 +117,21 @@ public: * aligned appropriately. The buffer is used directly * (avoiding a copy penalty) only if it is aligned on a * 4-byte boundary and the attribute size in bytes - * (i.e. NdbRecAttr::attrSize times NdbRecAttr::arraySize is + * (i.e. NdbRecAttr::attrSize() times NdbRecAttr::arraySize() is * a multiple of 4). * - * @note There are two versions, NdbOperation::getValue and - * NdbOperation::getPreValue for retrieving the current and + * @note There are two versions, getValue() and + * getPreValue() for retrieving the current and * previous value repectively. * * @note This method does not fetch the attribute value from * the database! The NdbRecAttr object returned by this method * is not readable/printable before the - * NdbEventConnection::execute has been made and - * NdbEventConnection::next has returned a value greater than + * execute() has been made and + * next() has returned a value greater than * zero. If a specific attribute has not changed the corresponding * NdbRecAttr will be in state UNDEFINED. This is checked by - * NdbRecAttr::isNull which then returns -1. + * NdbRecAttr::isNull() which then returns -1. * * @param anAttrName Attribute name * @param aValue If this is non-NULL, then the attribute value @@ -143,11 +148,11 @@ public: /** * Retrieves event resultset if available, inserted into the NdbRecAttrs * specified in getValue() and getPreValue(). To avoid polling for - * a resultset, one can use Ndb::pollEvents + * a resultset, one can use Ndb::pollEvents() * which will wait on a mutex until an event occurs or the specified * timeout occurs. * - * @return >=0 if successful otherwise -1. Return value inicates number + * @return >=0 if successful otherwise -1. Return value indicates number * of available events. By sending pOverRun one may query for buffer * overflow and *pOverRun will indicate the number of events that have * overwritten. diff --git a/ndb/src/ndbapi/Ndb.cpp b/ndb/src/ndbapi/Ndb.cpp index baa34b2006e..5ffb087cde7 100644 --- a/ndb/src/ndbapi/Ndb.cpp +++ b/ndb/src/ndbapi/Ndb.cpp @@ -1177,7 +1177,14 @@ NdbEventOperation* Ndb::createEventOperation(const char* eventName, tOp = new NdbEventOperation(this, eventName, bufferLength); - if (tOp->getState() != NdbEventOperation::CREATED) { + if (tOp == 0) + { + theError.code= 4000; + return NULL; + } + + if (tOp->getState() != NdbEventOperation::EO_CREATED) { + theError.code= tOp->getNdbError().code; delete tOp; tOp = NULL; } diff --git a/ndb/src/ndbapi/NdbEventOperationImpl.cpp b/ndb/src/ndbapi/NdbEventOperationImpl.cpp index 813a3a5f861..69c05dcb0b7 100644 --- a/ndb/src/ndbapi/NdbEventOperationImpl.cpp +++ b/ndb/src/ndbapi/NdbEventOperationImpl.cpp @@ -55,9 +55,8 @@ NdbEventOperationImpl::NdbEventOperationImpl(NdbEventOperation &N, const char* eventName, const int bufferLength) : NdbEventOperation(*this), m_ndb(theNdb), - m_state(ERROR), m_bufferL(bufferLength) + m_state(EO_ERROR), m_bufferL(bufferLength) { - m_eventId = 0; theFirstRecAttrs[0] = NULL; theCurrentRecAttrs[0] = NULL; @@ -71,16 +70,15 @@ NdbEventOperationImpl::NdbEventOperationImpl(NdbEventOperation &N, // we should lookup id in Dictionary, TODO // also make sure we only have one listener on each event - if (!m_ndb) { ndbout_c("m_ndb=NULL"); return; } + if (!m_ndb) abort(); NdbDictionary::Dictionary *myDict = m_ndb->getDictionary(); - if (!myDict) { ndbout_c("getDictionary=NULL"); return; } + if (!myDict) { m_error.code= m_ndb->getNdbError().code; return; } const NdbDictionary::Event *myEvnt = myDict->getEvent(eventName); - if (!myEvnt) { ndbout_c("getEvent()=NULL"); return; } + if (!myEvnt) { m_error.code= myDict->getNdbError().code; return; } m_eventImpl = &myEvnt->m_impl; - if (!m_eventImpl) { ndbout_c("m_impl=NULL"); return; } m_bufferHandle = m_ndb->getGlobalEventBufferHandle(); if (m_bufferHandle->m_bufferL > 0) @@ -88,7 +86,7 @@ NdbEventOperationImpl::NdbEventOperationImpl(NdbEventOperation &N, else m_bufferHandle->m_bufferL = m_bufferL; - m_state = CREATED; + m_state = EO_CREATED; } NdbEventOperationImpl::~NdbEventOperationImpl() @@ -106,7 +104,7 @@ NdbEventOperationImpl::~NdbEventOperationImpl() p = p_next; } } - if (m_state == NdbEventOperation::EXECUTING) { + if (m_state == EO_EXECUTING) { stop(); // m_bufferHandle->dropSubscribeEvent(m_bufferId); ; // We should send stop signal here @@ -122,7 +120,7 @@ NdbEventOperationImpl::getState() NdbRecAttr* NdbEventOperationImpl::getValue(const char *colName, char *aValue, int n) { - if (m_state != NdbEventOperation::CREATED) { + if (m_state != EO_CREATED) { ndbout_c("NdbEventOperationImpl::getValue may only be called between instantiation and execute()"); return NULL; } @@ -211,8 +209,8 @@ NdbEventOperationImpl::execute() { NdbDictionary::Dictionary *myDict = m_ndb->getDictionary(); if (!myDict) { - ndbout_c("NdbEventOperation::execute(): getDictionary=NULL"); - return 0; + m_error.code= m_ndb->getNdbError().code; + return -1; } if (theFirstRecAttrs[0] == NULL) { // defaults to get all @@ -245,14 +243,14 @@ NdbEventOperationImpl::execute() if (r) { //Error m_bufferHandle->unprepareAddSubscribeEvent(m_bufferId); - m_state = NdbEventOperation::ERROR; + m_state = EO_ERROR; } else { m_bufferHandle->addSubscribeEvent(m_bufferId, this); - m_state = NdbEventOperation::EXECUTING; + m_state = EO_EXECUTING; } } else { //Error - m_state = NdbEventOperation::ERROR; + m_state = EO_ERROR; } return r; } @@ -261,14 +259,14 @@ int NdbEventOperationImpl::stop() { DBUG_ENTER("NdbEventOperationImpl::stop"); - if (m_state != NdbEventOperation::EXECUTING) + if (m_state != EO_EXECUTING) DBUG_RETURN(-1); // ndbout_c("NdbEventOperation::stopping()"); NdbDictionary::Dictionary *myDict = m_ndb->getDictionary(); if (!myDict) { - ndbout_c("NdbEventOperation::stop(): getDictionary=NULL"); + m_error.code= m_ndb->getNdbError().code; DBUG_RETURN(-1); } @@ -299,13 +297,13 @@ NdbEventOperationImpl::stop() //Error m_bufferHandle->unprepareDropSubscribeEvent(m_bufferId); m_error.code= myDictImpl.m_error.code; - m_state = NdbEventOperation::ERROR; + m_state = EO_ERROR; } else { #ifdef EVENT_DEBUG ndbout_c("NdbEventOperation::dropping()"); #endif m_bufferHandle->dropSubscribeEvent(m_bufferId); - m_state = NdbEventOperation::CREATED; + m_state = EO_CREATED; } DBUG_RETURN(r); From 6e74893a6a7da1dadf5ca8dcc18a05b2974078cc Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 7 Jan 2005 16:43:27 +0200 Subject: [PATCH 02/23] Introduce ROW_TYPE=REDUNDANT and ROW_TYPE=COMPACT for InnoDB table formats sql/handler.cc: ha_row_type[]: Add REDUNDANT and COMPACT sql/handler.h: enum row_type: Add ROW_TYPE_REDUNDANT and ROW_TYPE_COMPACT sql/ha_innodb.cc: ha_innobase::create(): Detect ROW_TYPE=REDUNDANT sql/lex.h: Add "COMPACT" (COMPACT_SYM) and "REDUNDANT" (REDUNDANT_SYM) sql/sql_yacc.yy: row_types, keyword: Add COMPACT and REDUNDANT --- sql/ha_innodb.cc | 2 +- sql/handler.cc | 2 +- sql/handler.h | 3 ++- sql/lex.h | 2 ++ sql/sql_yacc.yy | 8 +++++++- 5 files changed, 13 insertions(+), 4 deletions(-) diff --git a/sql/ha_innodb.cc b/sql/ha_innodb.cc index 31b15f89806..0bca8c21715 100644 --- a/sql/ha_innodb.cc +++ b/sql/ha_innodb.cc @@ -3907,7 +3907,7 @@ ha_innobase::create( error = create_table_def(trx, form, norm_name, create_info->options & HA_LEX_CREATE_TMP_TABLE ? name2 : NULL, - !(form->s->db_options_in_use & HA_OPTION_PACK_RECORD)); + form->s->row_type != ROW_TYPE_REDUNDANT); if (error) { innobase_commit_low(trx); diff --git a/sql/handler.cc b/sql/handler.cc index bbe01dd93d5..b1b741dfee9 100644 --- a/sql/handler.cc +++ b/sql/handler.cc @@ -101,7 +101,7 @@ struct show_table_type_st sys_table_types[]= }; const char *ha_row_type[] = { - "", "FIXED", "DYNAMIC", "COMPRESSED","?","?","?" + "", "FIXED", "DYNAMIC", "COMPRESSED", "REDUNDANT", "COMPACT", "?","?","?" }; const char *tx_isolation_names[] = diff --git a/sql/handler.h b/sql/handler.h index b10e6bfe88c..e5a794ca1b2 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -167,7 +167,8 @@ struct show_table_type_st { }; enum row_type { ROW_TYPE_NOT_USED=-1, ROW_TYPE_DEFAULT, ROW_TYPE_FIXED, - ROW_TYPE_DYNAMIC, ROW_TYPE_COMPRESSED}; + ROW_TYPE_DYNAMIC, ROW_TYPE_COMPRESSED, + ROW_TYPE_REDUNDANT, ROW_TYPE_COMPACT }; /* struct to hold information about the table that should be created */ diff --git a/sql/lex.h b/sql/lex.h index 56d824b7bb8..871d1d99750 100644 --- a/sql/lex.h +++ b/sql/lex.h @@ -116,6 +116,7 @@ static SYMBOL symbols[] = { { "COMMENT", SYM(COMMENT_SYM)}, { "COMMIT", SYM(COMMIT_SYM)}, { "COMMITTED", SYM(COMMITTED_SYM)}, + { "COMPACT", SYM(COMPACT_SYM)}, { "COMPRESSED", SYM(COMPRESSED_SYM)}, { "CONCURRENT", SYM(CONCURRENT)}, { "CONDITION", SYM(CONDITION_SYM)}, @@ -378,6 +379,7 @@ static SYMBOL symbols[] = { { "READ", SYM(READ_SYM)}, { "READS", SYM(READS_SYM)}, { "REAL", SYM(REAL)}, + { "REDUNDANT", SYM(REDUNDANT_SYM)}, { "REFERENCES", SYM(REFERENCES)}, { "REGEXP", SYM(REGEXP)}, { "RELAY_LOG_FILE", SYM(RELAY_LOG_FILE_SYM)}, diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index fa23502ea93..6b1456dfbd3 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -227,6 +227,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); %token COLLATION_SYM %token COLUMNS %token COLUMN_SYM +%token COMPACT_SYM %token CONCURRENT %token CONDITION_SYM %token CONNECTION_SYM @@ -381,6 +382,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize); %token READ_SYM %token READS_SYM %token REAL_NUM +%token REDUNDANT_SYM %token REFERENCES %token REGEXP %token RELOAD @@ -2628,7 +2630,9 @@ row_types: DEFAULT { $$= ROW_TYPE_DEFAULT; } | FIXED_SYM { $$= ROW_TYPE_FIXED; } | DYNAMIC_SYM { $$= ROW_TYPE_DYNAMIC; } - | COMPRESSED_SYM { $$= ROW_TYPE_COMPRESSED; }; + | COMPRESSED_SYM { $$= ROW_TYPE_COMPRESSED; } + | REDUNDANT_SYM { $$= ROW_TYPE_REDUNDANT; } + | COMPACT_SYM { $$= ROW_TYPE_COMPACT; }; raid_types: RAID_STRIPED_SYM { $$= RAID_TYPE_0; } @@ -6915,6 +6919,7 @@ keyword: | COMMENT_SYM {} | COMMITTED_SYM {} | COMMIT_SYM {} + | COMPACT_SYM {} | COMPRESSED_SYM {} | CONCURRENT {} | CONSISTENT_SYM {} @@ -7046,6 +7051,7 @@ keyword: | RAID_CHUNKSIZE {} | RAID_STRIPED_SYM {} | RAID_TYPE {} + | REDUNDANT_SYM {} | RELAY_LOG_FILE_SYM {} | RELAY_LOG_POS_SYM {} | RELOAD {} From 6648761d67235ace2cd85125a54e04876a8f788b Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 00:55:19 +1000 Subject: [PATCH 03/23] Some cleanup in Ndb.hpp (testing for PDF generation). ndb/include/ndbapi/Ndb.hpp: Some editing/cleanup. --- ndb/include/ndbapi/Ndb.hpp | 25 +++++++++++++------------ 1 file changed, 13 insertions(+), 12 deletions(-) diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index dcde0a66872..9ff7f2cf5f5 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -21,7 +21,7 @@ on http://dev.mysql.com/doc/mysql/en/NDBCluster.html . Some of the fundamental ones are also described in section @ref secConcepts. - The NDB API is a MySQL Cluster application interface + The NDB API is a MySQL Cluster application interface that implements transactions. The NDB API consists of the following fundamental classes: - Ndb_cluster_connection, representing a connection to a cluster, @@ -36,7 +36,7 @@ - NdbDictionary represents meta information about tables and attributes. - NdbError contains the specification for an error. - It is also possible to receive "events" on changed data in the database. + It is also possible to receive "events" triggered when data in the database in changed. This is done through the NdbEventOperation class. There are also some auxiliary classes. @@ -44,31 +44,32 @@ The main structure of an application program is as follows: -# Construct and connect to a cluster using the Ndb_cluster_connection object. - -# Construct and initialize Ndb object(s) to connect to a database. - -# Define and execute transactions using NdbTransaction. + -# initiate a database connection by constructing and initialising one or more Ndb objects. + -# Define and execute transactions using the NdbTransaction class. -# Delete Ndb objects. - -# Delete cluster connection. + -# Terminate the connection to the cluster (terminate instance of Ndb_cluster_connection). - The main structure of a transaction is as follows: - -# Start transaction (an NdbTransaction) - -# Add and define operations associated with the transaction using - NdbOperation, NdbScanOperation, NdbIndexOperation, NdbIndexScanOperation + The procedure for using transactions is as follows: + -# Start transaction (instantiate an NdbTransaction object) + -# Add and define operations associated with the transaction using the + NdbOperation, NdbScanOperation, NdbIndexOperation, and NdbIndexScanOperation classes. -# Execute transaction The execution can be of two different types, Commit or NoCommit. If the execution is of type NoCommit, then the application program executes part of a transaction, - but without committing the transaction. + but without actually committing the transaction. After executing a NoCommit transaction, the program can continue to add and define more operations to the transaction for later execution. If the execute is of type Commit, then the transaction is - committed. The transaction must be closed after it has been + immediately committed. The transaction must be closed after it has been commited (event if commit fails), and no further addition or definition of - operations is allowed. + operations for this transaction is allowed. + @c STOP POINT -- js @section secSync Synchronous Transactions From 0c57a67ce0434fa78e2b64f569a271d166371a32 Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 7 Jan 2005 17:44:18 +0100 Subject: [PATCH 04/23] Correctly truncate integers inserted into field and double columns with a number of decimals specified. (Bug #7361) mysql-test/t/type_float.test: Add test for maximum values of float and double columns with number of decimals mysql-test/r/type_float.result: Add results for new test mysql-test/r/type_float.result.es: Add results for new test sql/field.cc: Use ::store(double nr) from ::store(longlong nr) so we get the same range checking --- mysql-test/r/type_float.result | 36 +++++++++++++++++++++++++++++++ mysql-test/r/type_float.result.es | 36 +++++++++++++++++++++++++++++++ mysql-test/t/type_float.test | 10 +++++++++ sql/field.cc | 36 ++----------------------------- 4 files changed, 84 insertions(+), 34 deletions(-) diff --git a/mysql-test/r/type_float.result b/mysql-test/r/type_float.result index 2f996382586..9dd92c13c98 100644 --- a/mysql-test/r/type_float.result +++ b/mysql-test/r/type_float.result @@ -143,3 +143,39 @@ drop table t1; create table t1 (f float(54)); ERROR 42000: Incorrect column specifier for column 'f' drop table if exists t1; +create table t1 (f float(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +Warnings: +Warning 1264 Data truncated; out of range for column 'f' at row 1 +Warning 1264 Data truncated; out of range for column 'f' at row 2 +Warning 1264 Data truncated; out of range for column 'f' at row 3 +Warning 1264 Data truncated; out of range for column 'f' at row 4 +Warning 1264 Data truncated; out of range for column 'f' at row 5 +Warning 1264 Data truncated; out of range for column 'f' at row 6 +select * from t1; +f +-9.999 +-9.999 +-9.999 +9.999 +9.999 +9.999 +drop table if exists t1; +create table t1 (f double(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +Warnings: +Warning 1264 Data truncated; out of range for column 'f' at row 1 +Warning 1264 Data truncated; out of range for column 'f' at row 2 +Warning 1264 Data truncated; out of range for column 'f' at row 3 +Warning 1264 Data truncated; out of range for column 'f' at row 4 +Warning 1264 Data truncated; out of range for column 'f' at row 5 +Warning 1264 Data truncated; out of range for column 'f' at row 6 +select * from t1; +f +-9.999 +-9.999 +-9.999 +9.999 +9.999 +9.999 +drop table if exists t1; diff --git a/mysql-test/r/type_float.result.es b/mysql-test/r/type_float.result.es index 4bfe644d7fb..64d9be7e30f 100644 --- a/mysql-test/r/type_float.result.es +++ b/mysql-test/r/type_float.result.es @@ -143,3 +143,39 @@ drop table t1; create table t1 (f float(54)); ERROR 42000: Incorrect column specifier for column 'f' drop table if exists t1; +create table t1 (f float(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +Warnings: +Warning 1264 Data truncated; out of range for column 'f' at row 1 +Warning 1264 Data truncated; out of range for column 'f' at row 2 +Warning 1264 Data truncated; out of range for column 'f' at row 3 +Warning 1264 Data truncated; out of range for column 'f' at row 4 +Warning 1264 Data truncated; out of range for column 'f' at row 5 +Warning 1264 Data truncated; out of range for column 'f' at row 6 +select * from t1; +f +-9.999 +-9.999 +-9.999 +9.999 +9.999 +9.999 +drop table if exists t1; +create table t1 (f double(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +Warnings: +Warning 1264 Data truncated; out of range for column 'f' at row 1 +Warning 1264 Data truncated; out of range for column 'f' at row 2 +Warning 1264 Data truncated; out of range for column 'f' at row 3 +Warning 1264 Data truncated; out of range for column 'f' at row 4 +Warning 1264 Data truncated; out of range for column 'f' at row 5 +Warning 1264 Data truncated; out of range for column 'f' at row 6 +select * from t1; +f +-9.999 +-9.999 +-9.999 +9.999 +9.999 +9.999 +drop table if exists t1; diff --git a/mysql-test/t/type_float.test b/mysql-test/t/type_float.test index 26ac272c6d4..3fe3afa3fac 100644 --- a/mysql-test/t/type_float.test +++ b/mysql-test/t/type_float.test @@ -93,3 +93,13 @@ create table t1 (f float(54)); # Should give an error drop table if exists t1; --enable_warnings +# Ensure that maximum values as the result of number of decimals +# being specified in table schema are enforced (Bug #7361) +create table t1 (f float(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +select * from t1; +drop table if exists t1; +create table t1 (f double(4,3)); +insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); +select * from t1; +drop table if exists t1; diff --git a/sql/field.cc b/sql/field.cc index b27a319b00e..e2c11cc7372 100644 --- a/sql/field.cc +++ b/sql/field.cc @@ -2395,23 +2395,7 @@ int Field_float::store(double nr) int Field_float::store(longlong nr) { - int error= 0; - float j= (float) nr; - if (unsigned_flag && j < 0) - { - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); - j=0; - error= 1; - } -#ifdef WORDS_BIGENDIAN - if (table->db_low_byte_first) - { - float4store(ptr,j); - } - else -#endif - memcpy_fixed(ptr,(byte*) &j,sizeof(j)); - return error; + return store((double)nr); } @@ -2690,23 +2674,7 @@ int Field_double::store(double nr) int Field_double::store(longlong nr) { - double j= (double) nr; - int error= 0; - if (unsigned_flag && j < 0) - { - set_warning(MYSQL_ERROR::WARN_LEVEL_WARN, ER_WARN_DATA_OUT_OF_RANGE, 1); - error= 1; - j=0; - } -#ifdef WORDS_BIGENDIAN - if (table->db_low_byte_first) - { - float8store(ptr,j); - } - else -#endif - doublestore(ptr,j); - return error; + return store((double)nr); } From 306767278d13f1d0ae9717558456dfd46faeb2ff Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 7 Jan 2005 19:50:41 +0100 Subject: [PATCH 05/23] Create columns_priv with correct column lengths (the alter table that used to fix it was removed in a merge, and now the alter table that fixes the length comes before the create table so it fixes pre-existing tables but not the newly-created one). scripts/mysql_fix_privilege_tables.sql: Create columns_priv with correct column lengths --- scripts/mysql_fix_privilege_tables.sql | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/scripts/mysql_fix_privilege_tables.sql b/scripts/mysql_fix_privilege_tables.sql index 975d8dddbb0..9373a888bc2 100644 --- a/scripts/mysql_fix_privilege_tables.sql +++ b/scripts/mysql_fix_privilege_tables.sql @@ -93,10 +93,10 @@ CREATE TABLE IF NOT EXISTS tables_priv ( CREATE TABLE IF NOT EXISTS columns_priv ( Host char(60) DEFAULT '' NOT NULL, - Db char(60) DEFAULT '' NOT NULL, + Db char(64) DEFAULT '' NOT NULL, User char(16) DEFAULT '' NOT NULL, - Table_name char(60) DEFAULT '' NOT NULL, - Column_name char(59) DEFAULT '' NOT NULL, + Table_name char(64) DEFAULT '' NOT NULL, + Column_name char(64) DEFAULT '' NOT NULL, Timestamp timestamp(14), Column_priv set('Select','Insert','Update','References') DEFAULT '' NOT NULL, PRIMARY KEY (Host,Db,User,Table_name,Column_name) From 5802259dc5ca818c53332b360dba09570f4f6e81 Mon Sep 17 00:00:00 2001 From: unknown Date: Fri, 7 Jan 2005 20:34:51 +0100 Subject: [PATCH 06/23] Update messages in type_float test results mysql-test/r/type_float.result: Update warning messages mysql-test/r/type_float.result.es: Update warning messages --- mysql-test/r/type_float.result | 24 ++++++++++++------------ mysql-test/r/type_float.result.es | 28 ++++++++++++++-------------- 2 files changed, 26 insertions(+), 26 deletions(-) diff --git a/mysql-test/r/type_float.result b/mysql-test/r/type_float.result index 84c931e14da..62aae177f6a 100644 --- a/mysql-test/r/type_float.result +++ b/mysql-test/r/type_float.result @@ -146,12 +146,12 @@ drop table if exists t1; create table t1 (f float(4,3)); insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); Warnings: -Warning 1264 Data truncated; out of range for column 'f' at row 1 -Warning 1264 Data truncated; out of range for column 'f' at row 2 -Warning 1264 Data truncated; out of range for column 'f' at row 3 -Warning 1264 Data truncated; out of range for column 'f' at row 4 -Warning 1264 Data truncated; out of range for column 'f' at row 5 -Warning 1264 Data truncated; out of range for column 'f' at row 6 +Warning 1264 Out of range value adjusted for column 'f' at row 1 +Warning 1264 Out of range value adjusted for column 'f' at row 2 +Warning 1264 Out of range value adjusted for column 'f' at row 3 +Warning 1264 Out of range value adjusted for column 'f' at row 4 +Warning 1264 Out of range value adjusted for column 'f' at row 5 +Warning 1264 Out of range value adjusted for column 'f' at row 6 select * from t1; f -9.999 @@ -164,12 +164,12 @@ drop table if exists t1; create table t1 (f double(4,3)); insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); Warnings: -Warning 1264 Data truncated; out of range for column 'f' at row 1 -Warning 1264 Data truncated; out of range for column 'f' at row 2 -Warning 1264 Data truncated; out of range for column 'f' at row 3 -Warning 1264 Data truncated; out of range for column 'f' at row 4 -Warning 1264 Data truncated; out of range for column 'f' at row 5 -Warning 1264 Data truncated; out of range for column 'f' at row 6 +Warning 1264 Out of range value adjusted for column 'f' at row 1 +Warning 1264 Out of range value adjusted for column 'f' at row 2 +Warning 1264 Out of range value adjusted for column 'f' at row 3 +Warning 1264 Out of range value adjusted for column 'f' at row 4 +Warning 1264 Out of range value adjusted for column 'f' at row 5 +Warning 1264 Out of range value adjusted for column 'f' at row 6 select * from t1; f -9.999 diff --git a/mysql-test/r/type_float.result.es b/mysql-test/r/type_float.result.es index 64d9be7e30f..d1c72a2ee53 100644 --- a/mysql-test/r/type_float.result.es +++ b/mysql-test/r/type_float.result.es @@ -15,8 +15,8 @@ f1 float NULL YES NULL f2 double NULL YES NULL insert into t1 values(10,10),(1e+5,1e+5),(1234567890,1234567890),(1e+10,1e+10),(1e+15,1e+15),(1e+20,1e+20),(1e+50,1e+50),(1e+150,1e+150); Warnings: -Warning 1264 Data truncated; out of range for column 'f1' at row 7 -Warning 1264 Data truncated; out of range for column 'f1' at row 8 +Warning 1264 Out of range value adjusted for column 'f1' at row 7 +Warning 1264 Out of range value adjusted for column 'f1' at row 8 insert into t1 values(-10,-10),(1e-5,1e-5),(1e-10,1e-10),(1e-15,1e-15),(1e-20,1e-20),(1e-50,1e-50),(1e-150,1e-150); select * from t1; f1 f2 @@ -146,12 +146,12 @@ drop table if exists t1; create table t1 (f float(4,3)); insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); Warnings: -Warning 1264 Data truncated; out of range for column 'f' at row 1 -Warning 1264 Data truncated; out of range for column 'f' at row 2 -Warning 1264 Data truncated; out of range for column 'f' at row 3 -Warning 1264 Data truncated; out of range for column 'f' at row 4 -Warning 1264 Data truncated; out of range for column 'f' at row 5 -Warning 1264 Data truncated; out of range for column 'f' at row 6 +Warning 1264 Out of range value adjusted for column 'f' at row 1 +Warning 1264 Out of range value adjusted for column 'f' at row 2 +Warning 1264 Out of range value adjusted for column 'f' at row 3 +Warning 1264 Out of range value adjusted for column 'f' at row 4 +Warning 1264 Out of range value adjusted for column 'f' at row 5 +Warning 1264 Out of range value adjusted for column 'f' at row 6 select * from t1; f -9.999 @@ -164,12 +164,12 @@ drop table if exists t1; create table t1 (f double(4,3)); insert into t1 values (-11.0),(-11),("-11"),(11.0),(11),("11"); Warnings: -Warning 1264 Data truncated; out of range for column 'f' at row 1 -Warning 1264 Data truncated; out of range for column 'f' at row 2 -Warning 1264 Data truncated; out of range for column 'f' at row 3 -Warning 1264 Data truncated; out of range for column 'f' at row 4 -Warning 1264 Data truncated; out of range for column 'f' at row 5 -Warning 1264 Data truncated; out of range for column 'f' at row 6 +Warning 1264 Out of range value adjusted for column 'f' at row 1 +Warning 1264 Out of range value adjusted for column 'f' at row 2 +Warning 1264 Out of range value adjusted for column 'f' at row 3 +Warning 1264 Out of range value adjusted for column 'f' at row 4 +Warning 1264 Out of range value adjusted for column 'f' at row 5 +Warning 1264 Out of range value adjusted for column 'f' at row 6 select * from t1; f -9.999 From 0338a61c8839979ee089089b5aa2fe5b4d633a2a Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 00:03:19 +0100 Subject: [PATCH 07/23] ndb - wl-1442 minor ndb/src/kernel/blocks/dbtc/DbtcMain.cpp: wl-1442 minor ndb/test/ndbapi/testOIBasic.cpp: wl-1442 minor sql/ha_ndbcluster.cc: wl-1442 minor --- ndb/src/kernel/blocks/dbtc/DbtcMain.cpp | 3 ++- ndb/test/ndbapi/testOIBasic.cpp | 2 +- sql/ha_ndbcluster.cc | 17 ++++++++++------- 3 files changed, 13 insertions(+), 9 deletions(-) diff --git a/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp b/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp index 6d4ca2d9078..5e79fc1c28f 100644 --- a/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp +++ b/ndb/src/kernel/blocks/dbtc/DbtcMain.cpp @@ -2364,7 +2364,8 @@ Dbtc::handle_special_hash(Uint32 dstHash[4], Uint32* src, Uint32 srcLen, */ Uint32 dstLen = xmul * (srcBytes - lb); ndbrequire(dstLen <= ((dstSize - dstPos) << 2)); - uint n = NdbSqlUtil::strnxfrm_bug7284(cs, dstPtr, dstLen, srcPtr + lb, len); + int n = NdbSqlUtil::strnxfrm_bug7284(cs, dstPtr, dstLen, srcPtr + lb, len); + ndbrequire(n != -1); while ((n & 3) != 0) { dstPtr[n++] = 0; } diff --git a/ndb/test/ndbapi/testOIBasic.cpp b/ndb/test/ndbapi/testOIBasic.cpp index 8a09a2ec9d1..0f31a30f1a7 100644 --- a/ndb/test/ndbapi/testOIBasic.cpp +++ b/ndb/test/ndbapi/testOIBasic.cpp @@ -1978,7 +1978,7 @@ Val::cmpchars(Par par, const unsigned char* buf1, unsigned len1, const unsigned unsigned len = maxxmulsize * col.m_bytelength; int n1 = NdbSqlUtil::strnxfrm_bug7284(cs, x1, chs->m_xmul * len, buf1, len1); int n2 = NdbSqlUtil::strnxfrm_bug7284(cs, x2, chs->m_xmul * len, buf2, len2); - assert(n1 == n2); + assert(n1 != -1 && n1 == n2); k = memcmp(x1, x2, n1); } else { k = (*cs->coll->strnncollsp)(cs, buf1, len1, buf2, len2, false); diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index 767ddc40400..a964ffe6fb9 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -3420,6 +3420,9 @@ int ndbcluster_rollback(THD *thd, void *ndb_transaction) Define NDB column based on Field. Returns 0 or mysql error code. Not member of ha_ndbcluster because NDBCOL cannot be declared. + + MySQL text types with character set "binary" are mapped to true + NDB binary types without a character set. This may change. */ static int create_ndb_column(NDBCOL &col, @@ -3509,7 +3512,7 @@ static int create_ndb_column(NDBCOL &col, col.setType(NDBCOL::Bit); col.setLength(1); } - else if (field->flags & BINARY_FLAG) + else if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) { col.setType(NDBCOL::Binary); col.setLength(field->pack_length()); @@ -3527,7 +3530,7 @@ static int create_ndb_column(NDBCOL &col, Field_varstring* f= (Field_varstring*)field; if (f->length_bytes == 1) { - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Varbinary); else { col.setType(NDBCOL::Varchar); @@ -3536,7 +3539,7 @@ static int create_ndb_column(NDBCOL &col, } else if (f->length_bytes == 2) { - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Longvarbinary); else { col.setType(NDBCOL::Longvarchar); @@ -3553,7 +3556,7 @@ static int create_ndb_column(NDBCOL &col, // Blob types (all come in as MYSQL_TYPE_BLOB) mysql_type_tiny_blob: case MYSQL_TYPE_TINY_BLOB: - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Blob); else { col.setType(NDBCOL::Text); @@ -3566,7 +3569,7 @@ static int create_ndb_column(NDBCOL &col, break; //mysql_type_blob: case MYSQL_TYPE_BLOB: - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Blob); else { col.setType(NDBCOL::Text); @@ -3588,7 +3591,7 @@ static int create_ndb_column(NDBCOL &col, break; mysql_type_medium_blob: case MYSQL_TYPE_MEDIUM_BLOB: - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Blob); else { col.setType(NDBCOL::Text); @@ -3600,7 +3603,7 @@ static int create_ndb_column(NDBCOL &col, break; mysql_type_long_blob: case MYSQL_TYPE_LONG_BLOB: - if (field->flags & BINARY_FLAG) + if ((field->flags & BINARY_FLAG) && cs == &my_charset_bin) col.setType(NDBCOL::Blob); else { col.setType(NDBCOL::Text); From 00c4dfec19aba6c40d06e24fd71976226c225ea8 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 05:32:47 +0100 Subject: [PATCH 08/23] Fix unportable 'tr' usage in libedit build process. (Bug #7669) cmd-line-utils/libedit/makelist.sh: Spell out the character range for braindead versions of tr (like /usr/xpg4/bin/tr on Sun Solaris 2.10) --- cmd-line-utils/libedit/makelist.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmd-line-utils/libedit/makelist.sh b/cmd-line-utils/libedit/makelist.sh index fbce06fcc50..b2502d16ed1 100644 --- a/cmd-line-utils/libedit/makelist.sh +++ b/cmd-line-utils/libedit/makelist.sh @@ -145,7 +145,7 @@ case $FLAG in # -fh) cat $FILES | $AWK '/el_action_t/ { print $3 }' | \ - sort | tr '[a-z]' '[A-Z]' | $AWK ' + sort | tr abcdefghijklmnopqrstuvwxyz ABCDEFGHIJKLMNOPQRSTUVWXYZ | $AWK ' BEGIN { printf("/* Automatically generated file, do not edit */\n"); printf("#ifndef _h_fcns_c\n#define _h_fcns_c\n"); From 66fe5d7c9f6668e4e49809be43cbee7154014947 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 14:37:42 +1000 Subject: [PATCH 09/23] Testing a new @ref in Ndb.hpp. ndb/include/ndbapi/Ndb.hpp: Testing a ref. --- ndb/include/ndbapi/Ndb.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index 9ff7f2cf5f5..0891682c21f 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -39,7 +39,7 @@ It is also possible to receive "events" triggered when data in the database in changed. This is done through the NdbEventOperation class. - There are also some auxiliary classes. + There are also some auxiliary classes, which are listed in the @ref hierarchy. The main structure of an application program is as follows: -# Construct and connect to a cluster using the Ndb_cluster_connection From 1084e2737938b8df3e44af957eeb1c1d52ff16b0 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 10:03:44 +0100 Subject: [PATCH 10/23] fixed some missing references in the ndbapi docs for events and dictionary --- ndb/include/ndbapi/NdbDictionary.hpp | 24 +++++++++++++++++++----- ndb/include/ndbapi/NdbEventOperation.hpp | 3 ++- 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/ndb/include/ndbapi/NdbDictionary.hpp b/ndb/include/ndbapi/NdbDictionary.hpp index 553d85f4129..ecc34072661 100644 --- a/ndb/include/ndbapi/NdbDictionary.hpp +++ b/ndb/include/ndbapi/NdbDictionary.hpp @@ -52,6 +52,7 @@ typedef struct charset_info_st CHARSET_INFO; * -# Dropping secondary indexes (Dictionary::dropIndex) * * NdbDictionary has several help (inner) classes to support this: + * -# NdbDictionary::Dictionary the dictionary handling dictionary objects * -# NdbDictionary::Table for creating tables * -# NdbDictionary::Column for creating table columns * -# NdbDictionary::Index for creating secondary indexes @@ -909,6 +910,9 @@ public: */ class Event : public Object { public: + /** + * Specifies the type of database operations an Event listens to + */ enum TableEvent { TE_INSERT=1, ///< Insert event on table TE_DELETE=2, ///< Delete event on table @@ -916,6 +920,10 @@ public: TE_ALL=7 ///< Any/all event on table (not relevant when ///< events are received) }; + /** + * Specifies the durability of an event + * (future version may supply other types) + */ enum EventDurability { ED_UNDEFINED #ifndef DOXYGEN_SHOULD_SKIP_INTERNAL @@ -930,8 +938,8 @@ public: // All API's can use it, // But's its removed when ndb is restarted #endif - ,ED_PERMANENT ///< All API's can use it, - ///< It's still defined after a restart + ,ED_PERMANENT ///< All API's can use it. + ///< It's still defined after a cluster system restart #ifndef DOXYGEN_SHOULD_SKIP_INTERNAL = 3 #endif @@ -950,9 +958,12 @@ public: Event(const char *name, const NdbDictionary::Table& table); virtual ~Event(); /** - * Set/get unique identifier for the event + * Set unique identifier for the event */ void setName(const char *name); + /** + * Get unique identifier for the event + */ const char *getName() const; /** * Define table on which events should be detected @@ -967,7 +978,7 @@ public: /** * Set table for which events should be detected * - * @note preferred way is using setTable(const NdbDictionary::Table) + * @note preferred way is using setTable(const NdbDictionary::Table&) * or constructor with table object parameter */ void setTable(const char *tableName); @@ -1224,9 +1235,12 @@ public: #endif /** - * Remove table/index from local cache + * Remove table from local cache */ void removeCachedTable(const char * table); + /** + * Remove index from local cache + */ void removeCachedIndex(const char * index, const char * table); diff --git a/ndb/include/ndbapi/NdbEventOperation.hpp b/ndb/include/ndbapi/NdbEventOperation.hpp index a0004558b39..4f8a05d589c 100644 --- a/ndb/include/ndbapi/NdbEventOperation.hpp +++ b/ndb/include/ndbapi/NdbEventOperation.hpp @@ -26,7 +26,8 @@ class NdbEventOperationImpl; * * Brief description on how to work with events: * - * - An event i created in the Database through + * - An event, represented by an NdbDictionary::Event, i created in the + * Database through * NdbDictionary::Dictionary::createEvent() (note that this can be done * by any application or thread and not necessarily by the "listener") * - To listen to events, an NdbEventOperation object is instantiated by From ce6de604c899167d930d01f8500bbd81d1f0e24b Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 13:59:57 +0100 Subject: [PATCH 11/23] ndb - wl-1442 bug#7725 datetime ordering mysql-test/t/ndb_index_ordered.test: wl-1442 datetime ordering ndb/src/common/util/NdbSqlUtil.cpp: wl-1442 datetime ordering --- mysql-test/t/ndb_index_ordered.test | 29 +++++++++++++++++++++++++++++ ndb/src/common/util/NdbSqlUtil.cpp | 24 ++++++++++-------------- 2 files changed, 39 insertions(+), 14 deletions(-) diff --git a/mysql-test/t/ndb_index_ordered.test b/mysql-test/t/ndb_index_ordered.test index 53177511bc6..c5d3a83a3ab 100644 --- a/mysql-test/t/ndb_index_ordered.test +++ b/mysql-test/t/ndb_index_ordered.test @@ -172,3 +172,32 @@ SELECT s.SubscrID,l.SbclID FROM test1 s left JOIN test2 l ON l.SbcrID=s.SubscrID WHERE s.UsrID=224 order by 1, 2; drop table test1; drop table test2; + +# bug#7424 + bug#7725 + +create table t1 ( + pk int primary key, + dt datetime not null, + da date not null, + ye year not null, + ti time not null, + ts timestamp not null, + index(dt), + index(da), + index(ye), + index(ti), + index(ts) +) engine=ndb; + +insert into t1 (pk,dt,da,ye,ti) values + (1, '1901-05-05 23:00:59', '1901-05-05', '1901', '23:00:59'), + (2, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), + (3, '1999-06-06 06:06:06', '1999-06-06', '1999', '06:06:06'), + (4, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), + (5, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); + +# datetime +select count(*) from t1 use index (dt) where dt > '1900-01-01 00:00:00'; +select count(*) from t1 use index (dt) where dt > '1955-12-31 00:00:00'; +select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:11'; +select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:12'; diff --git a/ndb/src/common/util/NdbSqlUtil.cpp b/ndb/src/common/util/NdbSqlUtil.cpp index 5b2381df50a..8491fa3c4a0 100644 --- a/ndb/src/common/util/NdbSqlUtil.cpp +++ b/ndb/src/common/util/NdbSqlUtil.cpp @@ -469,21 +469,17 @@ int NdbSqlUtil::cmpDatetime(const void* info, const Uint32* p1, const Uint32* p2, Uint32 full, Uint32 size) { assert(full >= size && size > 0); - /* - * Datetime is CC YY MM DD hh mm ss \0 - * - * Not used via MySQL. - */ - union { const Uint32* p; const unsigned char* v; } u1, u2; - u1.p = p1; - u2.p = p2; - // no format check - int k = memcmp(u1.v, u2.v, 4); - if (k != 0) - return k < 0 ? -1 : +1; if (size >= 2) { - k = memcmp(u1.v + 4, u2.v + 4, 4); - return k < 0 ? -1 : k > 0 ? +1 : 0; + union { Uint32 p[2]; Int64 v; } u1, u2; + u1.p[0] = p1[0]; + u1.p[1] = p1[1]; + u2.p[0] = p2[0]; + u2.p[1] = p2[1]; + if (u1.v < u2.v) + return -1; + if (u1.v > u2.v) + return +1; + return 0; } return CmpUnknown; } From b8a32fdcb4d3fd1e93bb091ba8fe9b0b14897ac0 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 23:40:40 +1000 Subject: [PATCH 12/23] First round of edits to Ndb.hpp for Alcatel PDF. ndb/include/ndbapi/Ndb.hpp: Edits for Alcatel PDF version (first set). --- ndb/include/ndbapi/Ndb.hpp | 164 +++++++++++++++++-------------------- 1 file changed, 77 insertions(+), 87 deletions(-) diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index 0891682c21f..20dca0ae5eb 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -39,12 +39,12 @@ It is also possible to receive "events" triggered when data in the database in changed. This is done through the NdbEventOperation class. - There are also some auxiliary classes, which are listed in the @ref hierarchy. + There are also some auxiliary classes, which are listed in the class hierarchy. The main structure of an application program is as follows: - -# Construct and connect to a cluster using the Ndb_cluster_connection + -# Connect to a cluster using the Ndb_cluster_connection object. - -# initiate a database connection by constructing and initialising one or more Ndb objects. + -# Initiate a database connection by constructing and initialising one or more Ndb objects. -# Define and execute transactions using the NdbTransaction class. -# Delete Ndb objects. -# Terminate the connection to the cluster (terminate instance of Ndb_cluster_connection). @@ -69,8 +69,6 @@ commited (event if commit fails), and no further addition or definition of operations for this transaction is allowed. - @c STOP POINT -- js - @section secSync Synchronous Transactions Synchronous transactions are defined and executed as follows: @@ -95,12 +93,12 @@ To execute several parallel synchronous transactions, one can either use multiple Ndb objects in several threads, or start multiple - applications programs. + application programs. @section secNdbOperations Operations - Each NdbTransaction consists of a list of operations which are represented - by instances of NdbOperation, NdbScanOperation, NdbIndexOperation, and/or + Each NdbTransaction consists of a list of operations, each of which is represented + by an instance of NdbOperation, NdbScanOperation, NdbIndexOperation, or NdbIndexScanOperation.

Single row operations

@@ -112,7 +110,7 @@ -# Specify attribute actions, using NdbOperation::getValue() Here are two brief examples illustrating this process. For the sake of - brevity, we omit error-handling. + brevity, we omit error handling. This first example uses an NdbOperation: @code @@ -151,17 +149,17 @@ creation and use of synchronous transactions.

Step 1: Define single row operation type

- The following types of operations exist: - -# NdbOperation::insertTuple : + The following operation types are supported: + -# NdbOperation::insertTuple() : inserts a non-existing tuple - -# NdbOperation::writeTuple : + -# NdbOperation::writeTuple() : updates an existing tuple if is exists, otherwise inserts a new tuple - -# NdbOperation::updateTuple : + -# NdbOperation::updateTuple() : updates an existing tuple - -# NdbOperation::deleteTuple : + -# NdbOperation::deleteTuple() : deletes an existing tuple - -# NdbOperation::readTuple : + -# NdbOperation::readTuple() : reads an existing tuple with specified lock mode All of these operations operate on the unique tuple key. @@ -173,20 +171,22 @@ NdbTransaction::getNdbIndexOperation() for each operation.

Step 2: Specify Search Conditions

- The search condition is used to select tuples using NdbOperation::equal() + The search condition is used to select tuples. Search conditions are set using NdbOperation::equal().

Step 3: Specify Attribute Actions

- Now it is time to define which attributes should be read or updated. - Deletes can neither read nor set values, read can only read values and - updates can only set values. - Normally the attribute is defined by its name but it is - also possible to use the attribute identity to define the + Next, it is necessary to determine which attributes should be read or updated. + It is important to remember that: + - Deletes can neither read nor set values, but only delete them + - Reads can only read values + - Updates can only set values + Normally the attribute is identified by name, but it is + also possible to use the attribute's identity to determine the attribute. NdbOperation::getValue() returns an NdbRecAttr object containing the read value. - To get the value, there is actually two methods. - The application can either + To obtain the actual value, one of two methods can be used; + the application can either - use its own memory (passed through a pointer aValue) to NdbOperation::getValue(), or - receive the attribute value in an NdbRecAttr object allocated @@ -194,28 +194,28 @@ The NdbRecAttr object is released when Ndb::closeTransaction() is called. - Thus, the application can not reference this object after - Ndb::closeTransaction() have been called. - The result of reading data from an NdbRecAttr object before - calling NdbTransaction::execute() is undefined. + Thus, the application cannot reference this object following + any subsequent call to Ndb::closeTransaction(). + Attempting to read data from an NdbRecAttr object before + calling NdbTransaction::execute() yields an undefined result. @subsection secScan Scan Operations - Scans are roughly the equivalent of SQL cursors. + Scans are roughly the equivalent of SQL cursors, providing a means to + preform high-speed row processing. A scan can be performed + on either a table (using @ref NdbScanOperation) or + an ordered index (by means of an @ref NdbIndexScanOperation). - Scans can either be performed on a table (@ref NdbScanOperation) or - on an ordered index (@ref NdbIndexScanOperation). - - Scan operation are characteriesed by the following: - - They can only perform reads (shared, exclusive or dirty) + Scan operations are characterised by the following: + - They can perform only reads (shared, exclusive or dirty) - They can potentially work with multiple rows - They can be used to update or delete multiple rows - - They can operate on several nodes in parallell + - They can operate on several nodes in parallel After the operation is created using NdbTransaction::getNdbScanOperation() (or NdbTransaction::getNdbIndexScanOperation()), - it is defined in the following three steps: + it is carried out in the following three steps: -# Define the standard operation type, using NdbScanOperation::readTuples() -# Specify search conditions, using @ref NdbScanFilter and/or @ref NdbIndexScanOperation::setBound() @@ -223,10 +223,10 @@ -# Executing the transaction, using NdbTransaction::execute() -# Iterating through the result set using NdbScanOperation::nextResult() - Here are two brief examples illustrating this process. For the sake of - brevity, we omit error-handling. + Here are two brief examples illustrating this process. Once again, in order + to keep things relatively short and simple, we will forego any error handling. - This first example uses an NdbScanOperation: + This first example performs a table scan, using an NdbScanOperation: @code // 1. Create MyOperation= MyTransaction->getNdbScanOperation("MYTABLENAME"); @@ -245,7 +245,7 @@ MyRecAttr= MyOperation->getValue("ATTR2", NULL); @endcode - The second example uses an NdbIndexScanOperation: + Our second example uses an NdbIndexScanOperation to perform an index scan: @code // 1. Create MyOperation= MyTransaction->getNdbIndexScanOperation("MYORDEREDINDEX", "MYTABLENAME"); @@ -262,77 +262,67 @@ MyRecAttr = MyOperation->getValue("ATTR2", NULL); @endcode + Some additional discussion of each step required to perform a scan follows: +

Step 1: Define scan operation operation type

- Scan operations only support 1 operation, - @ref NdbScanOperation::readTuples() - or @ref NdbIndexScanOperation::readTuples() + It is important to remember that only a single operation is supported for each scan operation + (@ref NdbScanOperation::readTuples() or @ref NdbIndexScanOperation::readTuples()). @note If you want to define multiple scan operations within the same transaction, then you need to call NdbTransaction::getNdbScanOperation() or - NdbTransaction::getNdbIndexScanOperation() for each operation. + NdbTransaction::getNdbIndexScanOperation() separately for each operation.

Step 2: Specify Search Conditions

The search condition is used to select tuples. If no search condition is specified, the scan will return all rows in the table. - Search condition can be @ref NdbScanFilter which can be used on both - @ref NdbScanOperation and @ref NdbIndexScanOperation or bounds which - can only be used on index scans, @ref NdbIndexScanOperation::setBound. - An index scan can have both NdbScanFilter and bounds + The search condition can be an @ref NdbScanFilter (which can be used on both + @ref NdbScanOperation and @ref NdbIndexScanOperation) or bounds which + can only be used on index scans (@ref NdbIndexScanOperation::setBound()). + An index scan can use both NdbScanFilter and bounds. - @note When NdbScanFilter is used each row is examined but maybe not - returned. But when using bounds, only rows within bounds will be examined. + @note When NdbScanFilter is used, each row is examined, whether or not it is + actually returned. However, when using bounds, only rows within the bounds will be examined.

Step 3: Specify Attribute Actions

- Now it is time to define which attributes should be read. - Normally the attribute is defined by its name but it is - also possible to use the attribute identity to define the - attribute. + Next, it is necessary to define which attributes should be read. + As with transaction attributes, scan attributes are defined by name but it is + also possible to use the attributes' identities to define attributes. - NdbOperation::getValue() returns an NdbRecAttr object - containing the read value. - To get the value, there is actually two methods. - The application can either - - use its own memory (passed through a pointer aValue) to - NdbOperation::getValue(), or - - receive the attribute value in an NdbRecAttr object allocated - by the NDB API. + As previously discussed (see @ref secSync), the value read is returned as an NdbRecAttr object by + the NdbOperation::getValue() method. - The NdbRecAttr object is released when Ndb::closeTransaction() - is called. Thus, the application can not reference this object after - Ndb::closeTransaction() have been called. - The result of reading data from an NdbRecAttr object before - calling NdbTransaction::execute() is undefined. - -

Using Scan to update/delete

- Scanning can also be used to update/delete rows. +

Using Scan to Update/Delete

+ Scanning can also be used to update or delete rows. This is performed by - -# Scan using exclusive locks, NdbOperation::LM_Exclusive - -# When iterating through the result set, for each row optionally call + -# Scanning using exclusive locks (using NdbOperation::LM_Exclusive) + -# When iterating through the result set, for each row optionally calling either NdbScanOperation::updateCurrentTuple() or NdbScanOperation::deleteCurrentTuple() - -# If performing NdbScanOperation::updateCurrentTuple(), - set new values on record using ordinary @ref NdbOperation::setValue(). - NdbOperation::equal() should not be called as the primary - key is retreived from the scan. + -# (If performing NdbScanOperation::updateCurrentTuple():) + Setting new values for records simply by using @ref NdbOperation::setValue(). + NdbOperation::equal() should not be called in such cases, as the primary + key is retrieved from the scan. - @note that the actual update/delete will not be performed until next - NdbTransaction::execute (as with single row operations), - NdbTransaction::execute needs to be called before locks are released, - see @ref secScanLocks + @note The actual update or delete will not be performed until the next + call to NdbTransaction::execute(), just as with single row operations. + NdbTransaction::execute() also must be called before any locks are released; + see @ref secScanLocks for more information. -

Index scans specific features

- The following features are available when performing an index scan - - Scan subset of table using @ref NdbIndexScanOperation::setBound() - - Ordering result set ascending or descending, - @ref NdbIndexScanOperation::readTuples() - - When using NdbIndexScanOperation::BoundEQ on partition key - only fragments containing rows will be scanned. +

Features Specific to Index Scans

- Rows are returned unordered unless sorted is set to true. + When performing an index scan, it is possible to + scan only a subset of a table using @ref NdbIndexScanOperation::setBound(). + In addition, result sets can be sorted in either ascending or descending order, using + @ref NdbIndexScanOperation::readTuples(). Note that rows are returned unordered + by default, that is, unless sorted is set to true. + IN addition, when using NdbIndexScanOperation::BoundEQ on a partition key, + only fragments containing rows will actually be scanned. + + @comment STOP POINT 20050108 13.35 GMT JS @note When performing sorted scan, parameter parallelism to NdbIndexScanOperation::readTuples() will From 2a3f285eb5a0c3156fc768f886e17d9cc7f1d195 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 15:18:24 +0100 Subject: [PATCH 13/23] ndb - wl-1442 updated ndb_index_ordered.result mysql-test/r/ndb_index_ordered.result: wl-1442 missed result file --- mysql-test/r/ndb_index_ordered.result | 31 +++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/mysql-test/r/ndb_index_ordered.result b/mysql-test/r/ndb_index_ordered.result index 50f904af750..a3eb5630131 100644 --- a/mysql-test/r/ndb_index_ordered.result +++ b/mysql-test/r/ndb_index_ordered.result @@ -310,3 +310,34 @@ SubscrID SbclID 3 NULL drop table test1; drop table test2; +create table t1 ( +pk int primary key, +dt datetime not null, +da date not null, +ye year not null, +ti time not null, +ts timestamp not null, +index(dt), +index(da), +index(ye), +index(ti), +index(ts) +) engine=ndb; +insert into t1 (pk,dt,da,ye,ti) values +(1, '1901-05-05 23:00:59', '1901-05-05', '1901', '23:00:59'), +(2, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), +(3, '1999-06-06 06:06:06', '1999-06-06', '1999', '06:06:06'), +(4, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), +(5, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); +select count(*) from t1 use index (dt) where dt > '1900-01-01 00:00:00'; +count(*) +5 +select count(*) from t1 use index (dt) where dt > '1955-12-31 00:00:00'; +count(*) +3 +select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:11'; +count(*) +3 +select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:12'; +count(*) +4 From 633ee9b09994333dd4ccdd85daa6aec4594d9346 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 16:57:51 +0100 Subject: [PATCH 14/23] ndb - wl-1442 fix Date ordering mysql-test/r/ndb_index_ordered.result: wl-1442 fix Date. reuses old unused Timespec type id mysql-test/t/ndb_index_ordered.test: wl-1442 fix Date. reuses old unused Timespec type id ndb/include/kernel/signaldata/DictTabInfo.hpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/include/ndbapi/NdbDictionary.hpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/include/util/NdbSqlUtil.hpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/src/common/util/NdbSqlUtil.cpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/src/ndbapi/NdbDictionary.cpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/src/ndbapi/NdbDictionaryImpl.cpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/test/include/NdbSchemaOp.hpp: wl-1442 fix Date. reuses old unused Timespec type id ndb/tools/restore/consumer.cpp: wl-1442 fix Date. reuses old unused Timespec type id sql/ha_ndbcluster.cc: wl-1442 fix Date. reuses old unused Timespec type id --- mysql-test/r/ndb_index_ordered.result | 66 ++++++++++++++----- mysql-test/t/ndb_index_ordered.test | 32 ++++++--- ndb/include/kernel/signaldata/DictTabInfo.hpp | 6 +- ndb/include/ndbapi/NdbDictionary.hpp | 2 +- ndb/include/util/NdbSqlUtil.hpp | 4 +- ndb/src/common/util/NdbSqlUtil.cpp | 52 +++++++-------- ndb/src/ndbapi/NdbDictionary.cpp | 4 +- ndb/src/ndbapi/NdbDictionaryImpl.cpp | 4 +- ndb/test/include/NdbSchemaOp.hpp | 2 +- ndb/tools/restore/consumer.cpp | 4 +- sql/ha_ndbcluster.cc | 9 ++- 11 files changed, 118 insertions(+), 67 deletions(-) diff --git a/mysql-test/r/ndb_index_ordered.result b/mysql-test/r/ndb_index_ordered.result index a3eb5630131..466523aafa7 100644 --- a/mysql-test/r/ndb_index_ordered.result +++ b/mysql-test/r/ndb_index_ordered.result @@ -325,19 +325,53 @@ index(ts) ) engine=ndb; insert into t1 (pk,dt,da,ye,ti) values (1, '1901-05-05 23:00:59', '1901-05-05', '1901', '23:00:59'), -(2, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), -(3, '1999-06-06 06:06:06', '1999-06-06', '1999', '06:06:06'), -(4, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), -(5, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); -select count(*) from t1 use index (dt) where dt > '1900-01-01 00:00:00'; -count(*) -5 -select count(*) from t1 use index (dt) where dt > '1955-12-31 00:00:00'; -count(*) -3 -select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:11'; -count(*) -3 -select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:12'; -count(*) -4 +(2, '1912-09-05 13:00:59', '1912-09-05', '1912', '13:00:59'), +(3, '1945-12-31 00:00:00', '1945-12-31', '1945', '00:00:00'), +(4, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), +(5, '1963-06-06 06:06:06', '1963-06-06', '1963', '06:06:06'), +(6, '1993-06-06 06:06:06', '1993-06-06', '1993', '06:06:06'), +(7, '2001-01-01 10:11:10', '2001-01-01', '2001', '10:11:10'), +(8, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), +(9, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); +select count(*)-9 from t1 use index (dt) where dt > '1900-01-01 00:00:00'; +count(*)-9 +0 +select count(*)-6 from t1 use index (dt) where dt >= '1955-12-31 00:00:00'; +count(*)-6 +0 +select count(*)-5 from t1 use index (dt) where dt > '1955-12-31 00:00:00'; +count(*)-5 +0 +select count(*)-5 from t1 use index (dt) where dt < '1970-03-03 22:22:22'; +count(*)-5 +0 +select count(*)-7 from t1 use index (dt) where dt < '2001-01-01 10:11:11'; +count(*)-7 +0 +select count(*)-8 from t1 use index (dt) where dt <= '2001-01-01 10:11:11'; +count(*)-8 +0 +select count(*)-9 from t1 use index (dt) where dt <= '2055-01-01 00:00:00'; +count(*)-9 +0 +select count(*)-9 from t1 use index (da) where da > '1900-01-01'; +count(*)-9 +0 +select count(*)-6 from t1 use index (da) where da >= '1955-12-31'; +count(*)-6 +0 +select count(*)-5 from t1 use index (da) where da > '1955-12-31'; +count(*)-5 +0 +select count(*)-5 from t1 use index (da) where da < '1970-03-03'; +count(*)-5 +0 +select count(*)-6 from t1 use index (da) where da < '2001-01-01'; +count(*)-6 +0 +select count(*)-8 from t1 use index (da) where da <= '2001-01-02'; +count(*)-8 +0 +select count(*)-9 from t1 use index (da) where da <= '2055-01-01'; +count(*)-9 +0 diff --git a/mysql-test/t/ndb_index_ordered.test b/mysql-test/t/ndb_index_ordered.test index c5d3a83a3ab..ae2f7db53fb 100644 --- a/mysql-test/t/ndb_index_ordered.test +++ b/mysql-test/t/ndb_index_ordered.test @@ -191,13 +191,29 @@ create table t1 ( insert into t1 (pk,dt,da,ye,ti) values (1, '1901-05-05 23:00:59', '1901-05-05', '1901', '23:00:59'), - (2, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), - (3, '1999-06-06 06:06:06', '1999-06-06', '1999', '06:06:06'), - (4, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), - (5, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); + (2, '1912-09-05 13:00:59', '1912-09-05', '1912', '13:00:59'), + (3, '1945-12-31 00:00:00', '1945-12-31', '1945', '00:00:00'), + (4, '1955-12-31 00:00:00', '1955-12-31', '1955', '00:00:00'), + (5, '1963-06-06 06:06:06', '1963-06-06', '1963', '06:06:06'), + (6, '1993-06-06 06:06:06', '1993-06-06', '1993', '06:06:06'), + (7, '2001-01-01 10:11:10', '2001-01-01', '2001', '10:11:10'), + (8, '2001-01-01 10:11:11', '2001-01-01', '2001', '10:11:11'), + (9, '2005-01-31 23:59:59', '2005-01-31', '2005', '23:59:59'); # datetime -select count(*) from t1 use index (dt) where dt > '1900-01-01 00:00:00'; -select count(*) from t1 use index (dt) where dt > '1955-12-31 00:00:00'; -select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:11'; -select count(*) from t1 use index (dt) where dt < '2001-01-01 10:11:12'; +select count(*)-9 from t1 use index (dt) where dt > '1900-01-01 00:00:00'; +select count(*)-6 from t1 use index (dt) where dt >= '1955-12-31 00:00:00'; +select count(*)-5 from t1 use index (dt) where dt > '1955-12-31 00:00:00'; +select count(*)-5 from t1 use index (dt) where dt < '1970-03-03 22:22:22'; +select count(*)-7 from t1 use index (dt) where dt < '2001-01-01 10:11:11'; +select count(*)-8 from t1 use index (dt) where dt <= '2001-01-01 10:11:11'; +select count(*)-9 from t1 use index (dt) where dt <= '2055-01-01 00:00:00'; + +# date +select count(*)-9 from t1 use index (da) where da > '1900-01-01'; +select count(*)-6 from t1 use index (da) where da >= '1955-12-31'; +select count(*)-5 from t1 use index (da) where da > '1955-12-31'; +select count(*)-5 from t1 use index (da) where da < '1970-03-03'; +select count(*)-6 from t1 use index (da) where da < '2001-01-01'; +select count(*)-8 from t1 use index (da) where da <= '2001-01-02'; +select count(*)-9 from t1 use index (da) where da <= '2055-01-01'; diff --git a/ndb/include/kernel/signaldata/DictTabInfo.hpp b/ndb/include/kernel/signaldata/DictTabInfo.hpp index ae78c023c2a..392b691ae1e 100644 --- a/ndb/include/kernel/signaldata/DictTabInfo.hpp +++ b/ndb/include/kernel/signaldata/DictTabInfo.hpp @@ -308,7 +308,7 @@ public: ExtBinary = NdbSqlUtil::Type::Binary, ExtVarbinary = NdbSqlUtil::Type::Varbinary, ExtDatetime = NdbSqlUtil::Type::Datetime, - ExtTimespec = NdbSqlUtil::Type::Timespec, + ExtDate = NdbSqlUtil::Type::Date, ExtBlob = NdbSqlUtil::Type::Blob, ExtText = NdbSqlUtil::Type::Text }; @@ -428,10 +428,10 @@ public: AttributeSize = DictTabInfo::an8Bit; AttributeArraySize = 8 * AttributeExtLength; return true; - case DictTabInfo::ExtTimespec: + case DictTabInfo::ExtDate: AttributeType = DictTabInfo::StringType; AttributeSize = DictTabInfo::an8Bit; - AttributeArraySize = 12 * AttributeExtLength; + AttributeArraySize = 3 * AttributeExtLength; return true; case DictTabInfo::ExtBlob: case DictTabInfo::ExtText: diff --git a/ndb/include/ndbapi/NdbDictionary.hpp b/ndb/include/ndbapi/NdbDictionary.hpp index f0c8a10f488..0ca3744a3d9 100644 --- a/ndb/include/ndbapi/NdbDictionary.hpp +++ b/ndb/include/ndbapi/NdbDictionary.hpp @@ -185,7 +185,7 @@ public: Binary, ///< Len Varbinary, ///< Max len Datetime, ///< Precision down to 1 sec (sizeof(Datetime) == 8 bytes ) - Timespec, ///< Precision down to 1 nsec(sizeof(Datetime) == 12 bytes ) + Date, ///< Precision down to 1 day(sizeof(Date) == 4 bytes ) Blob, ///< Binary large object (see NdbBlob) Text ///< Text blob }; diff --git a/ndb/include/util/NdbSqlUtil.hpp b/ndb/include/util/NdbSqlUtil.hpp index 3062d1e4e1b..47bb2157e1a 100644 --- a/ndb/include/util/NdbSqlUtil.hpp +++ b/ndb/include/util/NdbSqlUtil.hpp @@ -81,7 +81,7 @@ public: Binary, // Len Varbinary, // Max len Datetime, // Precision down to 1 sec (size 8 bytes) - Timespec, // Precision down to 1 nsec (size 12 bytes) + Date, // Precision down to 1 day (size 4 bytes) Blob, // Blob Text // Text blob }; @@ -132,7 +132,7 @@ private: static Cmp cmpBinary; static Cmp cmpVarbinary; static Cmp cmpDatetime; - static Cmp cmpTimespec; + static Cmp cmpDate; static Cmp cmpBlob; static Cmp cmpText; }; diff --git a/ndb/src/common/util/NdbSqlUtil.cpp b/ndb/src/common/util/NdbSqlUtil.cpp index 8491fa3c4a0..6f490c7f611 100644 --- a/ndb/src/common/util/NdbSqlUtil.cpp +++ b/ndb/src/common/util/NdbSqlUtil.cpp @@ -153,8 +153,8 @@ NdbSqlUtil::m_typeList[] = { cmpDatetime }, { - Type::Timespec, - cmpTimespec + Type::Date, + cmpDate }, { Type::Blob, @@ -485,36 +485,34 @@ NdbSqlUtil::cmpDatetime(const void* info, const Uint32* p1, const Uint32* p2, Ui } int -NdbSqlUtil::cmpTimespec(const void* info, const Uint32* p1, const Uint32* p2, Uint32 full, Uint32 size) +NdbSqlUtil::cmpDate(const void* info, const Uint32* p1, const Uint32* p2, Uint32 full, Uint32 size) { +#ifdef ndb_date_is_4_byte_native_int + assert(full >= size && size > 0); + union { Uint32 p[2]; Int32 v; } u1, u2; + u1.p[0] = p1[0]; + u2.p[0] = p2[0]; + if (u1.v < u2.v) + return -1; + if (u1.v > u2.v) + return +1; + return 0; +#else assert(full >= size && size > 0); - /* - * Timespec is CC YY MM DD hh mm ss \0 NN NN NN NN - * - * Not used via MySQL. - */ union { const Uint32* p; const unsigned char* v; } u1, u2; u1.p = p1; u2.p = p2; - // no format check - int k = memcmp(u1.v, u2.v, 4); - if (k != 0) - return k < 0 ? -1 : +1; - if (size >= 2) { - k = memcmp(u1.v + 4, u2.v + 4, 4); - if (k != 0) - return k < 0 ? -1 : +1; - if (size >= 3) { - Uint32 n1 = *(const Uint32*)(u1.v + 8); - Uint32 n2 = *(const Uint32*)(u2.v + 8); - if (n1 < n2) - return -1; - if (n2 > n1) - return +1; - return 0; - } - } - return CmpUnknown; + // from Field_newdate::val_int + Uint64 j1 = uint3korr(u1.v); + Uint64 j2 = uint3korr(u2.v); + j1 = (j1 % 32L)+(j1 / 32L % 16L)*100L + (j1/(16L*32L))*10000L; + j2 = (j2 % 32L)+(j2 / 32L % 16L)*100L + (j2/(16L*32L))*10000L; + if (j1 < j2) + return -1; + if (j1 > j2) + return +1; + return 0; +#endif } int diff --git a/ndb/src/ndbapi/NdbDictionary.cpp b/ndb/src/ndbapi/NdbDictionary.cpp index f88bbc907a6..b47f7d2c15c 100644 --- a/ndb/src/ndbapi/NdbDictionary.cpp +++ b/ndb/src/ndbapi/NdbDictionary.cpp @@ -936,8 +936,8 @@ operator<<(NdbOut& out, const NdbDictionary::Column& col) case NdbDictionary::Column::Datetime: out << "Datetime"; break; - case NdbDictionary::Column::Timespec: - out << "Timespec"; + case NdbDictionary::Column::Date: + out << "Date"; break; case NdbDictionary::Column::Blob: out << "Blob(" << col.getInlineSize() << "," << col.getPartSize() diff --git a/ndb/src/ndbapi/NdbDictionaryImpl.cpp b/ndb/src/ndbapi/NdbDictionaryImpl.cpp index 7a293463c94..195fdce7e3f 100644 --- a/ndb/src/ndbapi/NdbDictionaryImpl.cpp +++ b/ndb/src/ndbapi/NdbDictionaryImpl.cpp @@ -130,7 +130,7 @@ NdbColumnImpl::init(Type t) case Binary: case Varbinary: case Datetime: - case Timespec: + case Date: m_precision = 0; m_scale = 0; m_length = 1; @@ -1174,7 +1174,7 @@ columnTypeMapping[] = { { DictTabInfo::ExtBinary, NdbDictionary::Column::Binary }, { DictTabInfo::ExtVarbinary, NdbDictionary::Column::Varbinary }, { DictTabInfo::ExtDatetime, NdbDictionary::Column::Datetime }, - { DictTabInfo::ExtTimespec, NdbDictionary::Column::Timespec }, + { DictTabInfo::ExtDate, NdbDictionary::Column::Date }, { DictTabInfo::ExtBlob, NdbDictionary::Column::Blob }, { DictTabInfo::ExtText, NdbDictionary::Column::Text }, { -1, -1 } diff --git a/ndb/test/include/NdbSchemaOp.hpp b/ndb/test/include/NdbSchemaOp.hpp index ac859f8abe8..b54c011ae8b 100644 --- a/ndb/test/include/NdbSchemaOp.hpp +++ b/ndb/test/include/NdbSchemaOp.hpp @@ -576,7 +576,7 @@ convertColumnTypeToAttrType(NdbDictionary::Column::Type _type) case NdbDictionary::Column::Varbinary: return String; case NdbDictionary::Column::Datetime: - case NdbDictionary::Column::Timespec: + case NdbDictionary::Column::Date: case NdbDictionary::Column::Undefined: default: return NoAttrTypeDef; diff --git a/ndb/tools/restore/consumer.cpp b/ndb/tools/restore/consumer.cpp index e94c31b2666..dc0567803dd 100644 --- a/ndb/tools/restore/consumer.cpp +++ b/ndb/tools/restore/consumer.cpp @@ -71,8 +71,8 @@ BackupConsumer::create_table_string(const TableS & table, case NdbDictionary::Column::Datetime: pos += sprintf(buf+pos, "%s", "datetime"); break; - case NdbDictionary::Column::Timespec: - pos += sprintf(buf+pos, "%s", "time"); + case NdbDictionary::Column::Date: + pos += sprintf(buf+pos, "%s", "date"); break; case NdbDictionary::Column::Undefined: // pos += sprintf(buf+pos, "%s", "varchar binary"); diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index 3c6cd83d5dc..e181b421e29 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -2259,9 +2259,9 @@ void ha_ndbcluster::print_results() fprintf(DBUG_FILE, "Datetime\t%llu", value); break; } - case NdbDictionary::Column::Timespec: { + case NdbDictionary::Column::Date: { Uint64 value= (Uint64) *field->ptr; - fprintf(DBUG_FILE, "Timespec\t%llu", value); + fprintf(DBUG_FILE, "Date\t%llu", value); break; } case NdbDictionary::Column::Blob: { @@ -3323,8 +3323,11 @@ static int create_ndb_column(NDBCOL &col, col.setType(NDBCOL::Datetime); col.setLength(1); break; - case MYSQL_TYPE_DATE: case MYSQL_TYPE_NEWDATE: + col.setType(NDBCOL::Date); + col.setLength(1); + break; + case MYSQL_TYPE_DATE: // ? case MYSQL_TYPE_TIME: case MYSQL_TYPE_YEAR: col.setType(NDBCOL::Char); From 17f32ed6d9a8367837b46e780937e5053955bb0a Mon Sep 17 00:00:00 2001 From: unknown Date: Sun, 9 Jan 2005 03:11:59 +1000 Subject: [PATCH 15/23] More documentation fixes/edits to Ndb.hpp (NDB Programmers Guide section.) ndb/include/ndbapi/Ndb.hpp: More fixes/edits (finished NDB Programmers Guide section.) --- ndb/include/ndbapi/Ndb.hpp | 109 +++++++++++++++++++------------------ 1 file changed, 57 insertions(+), 52 deletions(-) diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index 20dca0ae5eb..a6c543093c3 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -318,32 +318,29 @@ scan only a subset of a table using @ref NdbIndexScanOperation::setBound(). In addition, result sets can be sorted in either ascending or descending order, using @ref NdbIndexScanOperation::readTuples(). Note that rows are returned unordered - by default, that is, unless sorted is set to true. - IN addition, when using NdbIndexScanOperation::BoundEQ on a partition key, - only fragments containing rows will actually be scanned. + by default, that is, unless sorted is set to true. + It is also important to note that, when using NdbIndexScanOperation::BoundEQ + on a partition key, only fragments containing rows will actually be scanned. - @comment STOP POINT 20050108 13.35 GMT JS - - @note When performing sorted scan, parameter parallelism to + @note When performing a sorted scan, parameter parallelism to NdbIndexScanOperation::readTuples() will be ignored and max parallelism will be used instead. @subsection secScanLocks Lock handling with scans - When scanning a table or an index potentially - a lot of records will be returned. - - But Ndb will only lock a batch of rows per fragment at a time. + Performing scans on either a tables or an index has the potential + return a great many records; however, Ndb will lock only a predetermined + number of rows per fragment at a time. How many rows will be locked per fragment is controlled by the - batch parameter to NdbScanOperation::readTuples(). + batch parameter passed to NdbScanOperation::readTuples(). - To let the application handle how locks are released - NdbScanOperation::nextResult() have a parameter fetch_allow. - If NdbScanOperation::nextResult() is called with fetch_allow = false, no - locks may be released as result of the function call. Otherwise the locks - for the current batch may be released. + In order to allow the application to handle how locks are released, + NdbScanOperation::nextResult() has a Boolean parameter fetch_allow. + If NdbScanOperation::nextResult() is called with fetch_allow equal to + false, then no locks may be released as result of the function call. + Otherwise the locks for the current batch may be released. - This example shows scan delete, handling locks in an efficient manner. + This next example shows a scan delete that handle locks in an efficient manner. For the sake of brevity, we omit error-handling. @code int check; @@ -355,40 +352,31 @@ { // Inner loop for each row within batch MyScanOperation->deleteCurrentTuple(); - } while((check = MyScanOperation->nextResult(false) == 0)); + } while((check = MyScanOperation->nextResult(false)) == 0); // When no more rows in batch, exeute all defined deletes MyTransaction->execute(NoCommit); } @endcode - See @ref ndbapi_scan.cpp for full example of scan. + See @ref ndbapi_scan.cpp for a more complete example of a scan. @section secError Error Handling - Errors can occur when - -# operations are being defined, or when the - -# transaction is being executed. + Errors can occur either when operations making up a transaction are being + defined, or when the transaction is actually being executed. Catching and + handling either sort of error requires testing the value returned by + NdbTransaction::execute(), and then, if an error is indicated (that is, + if this value is equal to -1), using the following two methods in order to + identify the error's type and location: - One recommended way to handle a transaction failure - (i.e. an error is reported) is to: - -# Rollback transaction (NdbTransaction::execute() with a special parameter) - -# Close transaction - -# Restart transaction (if the error was temporary) - - @note Transactions are not automatically closed when an error occur. Call - Ndb::closeTransaction() to close. - - Several errors can occur when a transaction holds multiple - operations which are simultaneously executed. - In this case the application has to go through the operation - objects and query for their NdbError objects to find out what really - happened. - - NdbTransaction::getNdbErrorOperation() returns a reference to the - operation causing the latest error. - NdbTransaction::getNdbErrorLine() delivers the method number of the - erroneous method in the operation. + - NdbTransaction::getNdbErrorOperation() returns a reference to the + operation causing the most recent error. + - NdbTransaction::getNdbErrorLine() yields the method number of the + erroneous method in the operation. + + This short example illustrates how to detect an error and to use these + two methods to identify it: @code theTransaction = theNdb->startTransaction(); @@ -396,26 +384,43 @@ if (theOperation == NULL) goto error; theOperation->readTuple(NdbOperation::LM_Read); theOperation->setValue("ATTR_1", at1); - theOperation->setValue("ATTR_2", at1); //Here an error occurs + theOperation->setValue("ATTR_2", at1); // Error occurs here theOperation->setValue("ATTR_3", at1); theOperation->setValue("ATTR_4", at1); if (theTransaction->execute(Commit) == -1) { errorLine = theTransaction->getNdbErrorLine(); errorOperation = theTransaction->getNdbErrorOperation(); + } @endcode - Here errorLine will be 3 as the error occurred in the third method - on the operation object. - Getting errorLine == 0 means that the error occurred when executing the - operations. - Here errorOperation will be a pointer to the theOperation object. - NdbTransaction::getNdbError() will return the NdbError object - including holding information about the error. + Here errorLine will be 3 as the error occurred in the + third method called on the NdbOperation object (in this case, + theOperation); if the result of + NdbTransaction::getNdbErrorLine() is 0, this means that the error + occurred when the operations were executed. In this example, + errorOperation will be a pointer to the theOperation + object. The NdbTransaction::getNdbError() method returns an NdbError + object providing information about the error. - Since errors could have occurred even when a commit was reported, - there is also a special method, NdbTransaction::commitStatus(), - to check the commit status of the transaction. + @note Transactions are not automatically closed when an error occurs. Call + Ndb::closeTransaction() to close the transaction. + + One recommended way to handle a transaction failure + (i.e. an error is reported) is to: + -# Rollback transaction (call NdbTransaction::execute() with a special parameter) + -# Close transaction (call NdbTransaction::closeTransaction()) + -# If the error was temporary, attempt to restart the transaction + + Several errors can occur when a transaction contains multiple + operations which are simultaneously executed. + In this case the application has to go through all operations + and query their NdbError objects to find out what really happened. + + It is also important to note that errors can occur even when a commit is + reported as successful. In order to handle such situations, the NDB API + provides an additional NdbTransaction::commitStatus() method to check the + transactions's commit status. ******************************************************************************/ From c16322ada6d6f5fce5137618e535d91fedb690b3 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 18:25:41 +0100 Subject: [PATCH 16/23] fixed some mgmapi docs added example to ndbapi docs ndb/include/mgmapi/mgmapi.h: fixed some mgmapi docs ndb/include/ndbapi/Ndb.hpp: added examples ndb/src/mgmapi/mgmapi.cpp: removed unused parameter --- ndb/include/mgmapi/mgmapi.h | 303 +++++++++++++++++++++++------------- ndb/include/ndbapi/Ndb.hpp | 9 ++ ndb/src/mgmapi/mgmapi.cpp | 1 - 3 files changed, 204 insertions(+), 109 deletions(-) diff --git a/ndb/include/mgmapi/mgmapi.h b/ndb/include/mgmapi/mgmapi.h index fb2a31d6ee2..093186179b7 100644 --- a/ndb/include/mgmapi/mgmapi.h +++ b/ndb/include/mgmapi/mgmapi.h @@ -22,7 +22,7 @@ * * The NDB Cluster Management API (MGM API) is a C API * that is used to: - * - Start and stop database nodes (DB nodes) + * - Start and stop database nodes (ndbd processes) * - Start and stop NDB Cluster backups * - Control the NDB Cluster log * - Perform other administrative tasks @@ -30,18 +30,23 @@ * @section General Concepts * * Each MGM API function needs a management server handle - * of type Mgm_C_Api::NdbMgmHandle. + * of type @ref NdbMgmHandle. * This handle is initally created by calling the - * function ndb_mgm_create_handle(). + * function ndb_mgm_create_handle() and freed by calling + * ndb_mgm_destroy_handle(). * * A function can return: * -# An integer value. * A value of -1 indicates an error. - * -# A pointer value. A NULL value indicates an error; - * otherwise, the return value must be freed by the user of the MGM API. + * -# A non-const pointer value. A NULL value indicates an error; + * otherwise, the return value must be freed + * by the user of the MGM API + * -# A const pointer value. A NULL value indicates an error. + * Returned value should not be freed. * * Error conditions can be identified by using the appropriate - * error-reporting functions. + * error-reporting functions ndb_mgm_get_latest_error() and + * @ref ndb_mgm_error. */ /** @addtogroup MGM_C_API @@ -64,32 +69,54 @@ extern "C" { * NDB Cluster node types */ enum ndb_mgm_node_type { - NDB_MGM_NODE_TYPE_UNKNOWN = -1, /*< Node type not known*/ - NDB_MGM_NODE_TYPE_API = NODE_TYPE_API,/*< An application node (API)*/ - NDB_MGM_NODE_TYPE_NDB = NODE_TYPE_DB, /*< A database node (DB)*/ - NDB_MGM_NODE_TYPE_MGM = NODE_TYPE_MGM,/*< A mgmt server node (MGM)*/ - NDB_MGM_NODE_TYPE_REP = NODE_TYPE_REP,/*< A replication node */ - - NDB_MGM_NODE_TYPE_MIN = 0, /*< Min valid value*/ - NDB_MGM_NODE_TYPE_MAX = 3 /*< Max valid value*/ + NDB_MGM_NODE_TYPE_UNKNOWN = -1 /** Node type not known*/ + ,NDB_MGM_NODE_TYPE_API /** An application node (API) */ +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + = NODE_TYPE_API +#endif + ,NDB_MGM_NODE_TYPE_NDB /** A database node (DB) */ +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + = NODE_TYPE_DB +#endif + ,NDB_MGM_NODE_TYPE_MGM /** A mgmt server node (MGM)*/ +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + = NODE_TYPE_MGM +#endif +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + ,NDB_MGM_NODE_TYPE_REP = NODE_TYPE_REP /** A replication node */ + ,NDB_MGM_NODE_TYPE_MIN = 0 /** Min valid value*/ + ,NDB_MGM_NODE_TYPE_MAX = 3 /** Max valid value*/ +#endif }; /** * Database node status */ enum ndb_mgm_node_status { - NDB_MGM_NODE_STATUS_UNKNOWN = 0, /*< Node status not known*/ - NDB_MGM_NODE_STATUS_NO_CONTACT = 1, /*< No contact with node*/ - NDB_MGM_NODE_STATUS_NOT_STARTED = 2, /*< Has not run starting protocol*/ - NDB_MGM_NODE_STATUS_STARTING = 3, /*< Is running starting protocol*/ - NDB_MGM_NODE_STATUS_STARTED = 4, /*< Running*/ - NDB_MGM_NODE_STATUS_SHUTTING_DOWN = 5, /*< Is shutting down*/ - NDB_MGM_NODE_STATUS_RESTARTING = 6, /*< Is restarting*/ - NDB_MGM_NODE_STATUS_SINGLEUSER = 7, /*< Maintenance mode*/ - NDB_MGM_NODE_STATUS_RESUME = 8, /*< Resume mode*/ - - NDB_MGM_NODE_STATUS_MIN = 0, /*< Min valid value*/ - NDB_MGM_NODE_STATUS_MAX = 6 /*< Max valid value*/ + /** Node status not known*/ + NDB_MGM_NODE_STATUS_UNKNOWN = 0, + /** No contact with node*/ + NDB_MGM_NODE_STATUS_NO_CONTACT = 1, + /** Has not run starting protocol*/ + NDB_MGM_NODE_STATUS_NOT_STARTED = 2, + /** Is running starting protocol*/ + NDB_MGM_NODE_STATUS_STARTING = 3, + /** Running*/ + NDB_MGM_NODE_STATUS_STARTED = 4, + /** Is shutting down*/ + NDB_MGM_NODE_STATUS_SHUTTING_DOWN = 5, + /** Is restarting*/ + NDB_MGM_NODE_STATUS_RESTARTING = 6, + /** Maintenance mode*/ + NDB_MGM_NODE_STATUS_SINGLEUSER = 7, + /** Resume mode*/ + NDB_MGM_NODE_STATUS_RESUME = 8, +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + /** Min valid value*/ + NDB_MGM_NODE_STATUS_MIN = 0, + /** Max valid value*/ + NDB_MGM_NODE_STATUS_MAX = 8 +#endif }; /** @@ -128,14 +155,15 @@ extern "C" { NDB_MGM_USAGE_ERROR = 5001 }; +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL struct Ndb_Mgm_Error_Msg { enum ndb_mgm_error code; const char * msg; }; - const struct Ndb_Mgm_Error_Msg ndb_mgm_error_msgs[] = { { NDB_MGM_NO_ERROR, "No error" }, + /* Request for service errors */ { NDB_MGM_ILLEGAL_CONNECT_STRING, "Illegal connect string" }, { NDB_MGM_ILLEGAL_PORT_NUMBER, "Illegal port number" }, { NDB_MGM_ILLEGAL_SOCKET, "Illegal socket" }, @@ -167,66 +195,86 @@ extern "C" { { NDB_MGM_USAGE_ERROR, "Usage error" } }; - const int ndb_mgm_noOfErrorMsgs = sizeof(ndb_mgm_error_msgs)/sizeof(struct Ndb_Mgm_Error_Msg); +#endif /** - * Structure returned by ndb_mgm_get_status + * Status of a node in the cluster + * + * Sub-structure in enum ndb_mgm_cluster_state + * returned by ndb_mgm_get_status() */ struct ndb_mgm_node_state { - int node_id; /*< NDB Cluster node id*/ - enum ndb_mgm_node_type node_type; /*< Type of NDB Cluster node*/ - enum ndb_mgm_node_status node_status; /*< State of node*/ - int start_phase; /*< Start phase. - *< @note Start phase is only - *< valid if - *< node_type is - *< NDB_MGM_NODE_TYPE_NDB and - *< node_status is - *< NDB_MGM_NODE_STATUS_STARTING - */ - int dynamic_id; /*< Id for heartbeats and - *< master take-over - *< (only valid for DB nodes) - */ - int node_group; /*< Node group of node - *< (only valid for DB nodes)*/ - int version; /*< Internal version number*/ - int connect_count; /*< Number of times node has connected - *< or disconnected to the mgm srv - */ - char connect_address[sizeof("000.000.000.000")+1]; + /** NDB Cluster node id*/ + int node_id; + /** Type of NDB Cluster node*/ + enum ndb_mgm_node_type node_type; + /** State of node*/ + enum ndb_mgm_node_status node_status; + /** Start phase. + * + * @note Start phase is only valid if node_type is + * NDB_MGM_NODE_TYPE_NDB and node_status is + * NDB_MGM_NODE_STATUS_STARTING + */ + int start_phase; + /** Id for heartbeats and master take-over (only valid for DB nodes) + */ + int dynamic_id; + /** Node group of node (only valid for DB nodes)*/ + int node_group; + /** Internal version number*/ + int version; + /** Number of times node has connected or disconnected to the + * management server + */ + int connect_count; + /** Ip adress of node when it connected to the management server. + * @note it will be empty if the management server has restarted + * after the node connected. + */ + char connect_address[ +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + sizeof("000.000.000.000")+1 +#endif + ]; }; /** - * Cluster status + * State of all nodes in the cluster returned from + * ndb_mgm_get_status() */ struct ndb_mgm_cluster_state { - int no_of_nodes; /*< No of entries in the - *< node_states array - */ - struct ndb_mgm_node_state /*< An array with node_states*/ - node_states[1]; - const char *hostname; + /** No of entries in the node_states array */ + int no_of_nodes; + /** An array with node_states*/ + struct ndb_mgm_node_state node_states[ +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + 1 +#endif + ]; }; /** - * Default reply from the server + * Default reply from the server (for future use, not used today) */ struct ndb_mgm_reply { - int return_code; /*< 0 if successful, - *< otherwise error code. - */ - char message[256]; /*< Error or reply message.*/ + /** 0 if successful, otherwise error code. */ + int return_code; + /** Error or reply message.*/ + char message[256]; }; +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL /** * Default information types */ enum ndb_mgm_info { - NDB_MGM_INFO_CLUSTER, /*< ?*/ - NDB_MGM_INFO_CLUSTERLOG /*< Cluster log*/ + /** ?*/ + NDB_MGM_INFO_CLUSTER, + /** Cluster log*/ + NDB_MGM_INFO_CLUSTERLOG }; /** @@ -234,11 +282,16 @@ extern "C" { * (Used only in the development of NDB Cluster.) */ enum ndb_mgm_signal_log_mode { - NDB_MGM_SIGNAL_LOG_MODE_IN, /*< Log receiving signals */ - NDB_MGM_SIGNAL_LOG_MODE_OUT, /*< Log sending signals*/ - NDB_MGM_SIGNAL_LOG_MODE_INOUT, /*< Log both sending/receiving*/ - NDB_MGM_SIGNAL_LOG_MODE_OFF /*< Log off*/ + /** Log receiving signals */ + NDB_MGM_SIGNAL_LOG_MODE_IN, + /** Log sending signals*/ + NDB_MGM_SIGNAL_LOG_MODE_OUT, + /** Log both sending/receiving*/ + NDB_MGM_SIGNAL_LOG_MODE_INOUT, + /** Log off*/ + NDB_MGM_SIGNAL_LOG_MODE_OFF }; +#endif /** * Log severities (used to filter the cluster log) @@ -246,32 +299,31 @@ extern "C" { enum ndb_mgm_clusterlog_level { NDB_MGM_ILLEGAL_CLUSTERLOG_LEVEL = -1, /* must range from 0 and up, indexes into an array */ - NDB_MGM_CLUSTERLOG_ON = 0, /*< Cluster log on*/ - NDB_MGM_CLUSTERLOG_DEBUG = 1, /*< Used in NDB Cluster - *< developement - */ - NDB_MGM_CLUSTERLOG_INFO = 2, /*< Informational messages*/ - NDB_MGM_CLUSTERLOG_WARNING = 3, /*< Conditions that are not - *< error condition, but - *< might require handling - */ - NDB_MGM_CLUSTERLOG_ERROR = 4, /*< Conditions that should be - *< corrected - */ - NDB_MGM_CLUSTERLOG_CRITICAL = 5, /*< Critical conditions, like - *< device errors or out of - *< resources - */ - NDB_MGM_CLUSTERLOG_ALERT = 6, /*< A condition that should be - *< corrected immediately, - *< such as a corrupted system - */ + /** Cluster log on*/ + NDB_MGM_CLUSTERLOG_ON = 0, + /** Used in NDB Cluster developement */ + NDB_MGM_CLUSTERLOG_DEBUG = 1, + /** Informational messages*/ + NDB_MGM_CLUSTERLOG_INFO = 2, + /** Conditions that are not error condition, but might require handling + */ + NDB_MGM_CLUSTERLOG_WARNING = 3, + /** Conditions that should be corrected */ + NDB_MGM_CLUSTERLOG_ERROR = 4, + /** Critical conditions, like device errors or out of resources */ + NDB_MGM_CLUSTERLOG_CRITICAL = 5, + /** A condition that should be corrected immediately, + * such as a corrupted system + */ + NDB_MGM_CLUSTERLOG_ALERT = 6, /* must be next number, works as bound in loop */ - NDB_MGM_CLUSTERLOG_ALL = 7 /*< All severities */ + /** All severities */ + NDB_MGM_CLUSTERLOG_ALL = 7 }; /** - * Log categories + * Log categories, used to set filter on the clusterlog using + * ndb_mgm_set_loglevel_clusterlog() */ enum ndb_mgm_event_category { /** @@ -282,28 +334,56 @@ extern "C" { * Events during all kinds of startups */ NDB_MGM_EVENT_CATEGORY_STARTUP = CFG_LOGLEVEL_STARTUP, - /** * Events during shutdown */ NDB_MGM_EVENT_CATEGORY_SHUTDOWN = CFG_LOGLEVEL_SHUTDOWN, - /** * Transaction statistics (Job level, TCP/IP speed) */ NDB_MGM_EVENT_CATEGORY_STATISTIC = CFG_LOGLEVEL_STATISTICS, + /** + * Events regarding checkpoints + */ NDB_MGM_EVENT_CATEGORY_CHECKPOINT = CFG_LOGLEVEL_CHECKPOINT, + /** + * Events during node restart + */ NDB_MGM_EVENT_CATEGORY_NODE_RESTART = CFG_LOGLEVEL_NODERESTART, + /** + * Events on connection between cluster nodes + */ NDB_MGM_EVENT_CATEGORY_CONNECTION = CFG_LOGLEVEL_CONNECTION, - NDB_MGM_EVENT_CATEGORY_DEBUG = CFG_LOGLEVEL_DEBUG, - NDB_MGM_EVENT_CATEGORY_INFO = CFG_LOGLEVEL_INFO, - NDB_MGM_EVENT_CATEGORY_WARNING = CFG_LOGLEVEL_WARNING, - NDB_MGM_EVENT_CATEGORY_ERROR = CFG_LOGLEVEL_ERROR, - NDB_MGM_EVENT_CATEGORY_GREP = CFG_LOGLEVEL_GREP, + /** + * Backup events + */ NDB_MGM_EVENT_CATEGORY_BACKUP = CFG_LOGLEVEL_BACKUP, - + /** + * Loglevel debug + */ + NDB_MGM_EVENT_CATEGORY_DEBUG = CFG_LOGLEVEL_DEBUG, + /** + * Loglevel info + */ + NDB_MGM_EVENT_CATEGORY_INFO = CFG_LOGLEVEL_INFO, + /** + * Loglevel warning + */ + NDB_MGM_EVENT_CATEGORY_WARNING = CFG_LOGLEVEL_WARNING, + /** + * Loglevel error + */ + NDB_MGM_EVENT_CATEGORY_ERROR = CFG_LOGLEVEL_ERROR, +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL + /** + * + */ + NDB_MGM_EVENT_CATEGORY_GREP = CFG_LOGLEVEL_GREP, +#endif +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL NDB_MGM_MIN_EVENT_CATEGORY = CFG_MIN_LOGLEVEL, NDB_MGM_MAX_EVENT_CATEGORY = CFG_MAX_LOGLEVEL +#endif }; /***************************************************************************/ @@ -618,7 +698,7 @@ extern "C" { /** @} *********************************************************************/ /** - * @name Functions: Logging and Statistics + * @name Functions: Logging * @{ */ @@ -670,6 +750,17 @@ extern "C" { enum ndb_mgm_event_category category, int level, struct ndb_mgm_reply* reply); + + /** + * Listen to log events + * + * @param filter pairs of { level, ndb_mgm_event_category } that will be + * pushed to fd, level=0 ends lists + * + * @return fd which events will be pushed to + */ + int ndb_mgm_listen_event(NdbMgmHandle handle, int filter[]); + #ifndef DOXYGEN_SHOULD_SKIP_INTERNAL /** * Set log category and levels for the Node @@ -760,15 +851,11 @@ extern "C" { int ndb_mgm_exit_single_user(NdbMgmHandle handle, struct ndb_mgm_reply* reply); + /** @} *********************************************************************/ /** - * Listen event - * - * @param filter pairs of { level, category } that will be - * pushed to fd, level=0 ends lists - * - * @return fd which events will be pushed to + * @name Configuration handling + * @{ */ - int ndb_mgm_listen_event(NdbMgmHandle handle, int filter[]); /** * Get configuration @@ -778,7 +865,7 @@ extern "C" { * * @return configuration * - * @note the caller must call ndb_mgm_detroy_configuration + * @note the caller must call ndb_mgm_destroy_configuration() */ struct ndb_mgm_configuration * ndb_mgm_get_configuration(NdbMgmHandle handle, unsigned version); diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index 0891682c21f..64cb5b6f34b 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -435,6 +435,10 @@ */ #ifndef DOXYGEN_SHOULD_SKIP_INTERNAL +/** + * @page ndbapi_async.cpp ndbapi_async.cpp + * @include ndbapi_async.cpp + */ /** * @page ndbapi_async1.cpp ndbapi_async1.cpp * @include ndbapi_async1.cpp @@ -456,6 +460,11 @@ * @include ndbapi_scan.cpp */ +/** + * @page ndbapi_event.cpp ndbapi_event.cpp + * @include ndbapi_event.cpp + */ + /** @page secAdapt Adaptive Send Algorithm diff --git a/ndb/src/mgmapi/mgmapi.cpp b/ndb/src/mgmapi/mgmapi.cpp index 166bd45d48b..747178301f0 100644 --- a/ndb/src/mgmapi/mgmapi.cpp +++ b/ndb/src/mgmapi/mgmapi.cpp @@ -629,7 +629,6 @@ ndb_mgm_get_status(NdbMgmHandle handle) malloc(sizeof(ndb_mgm_cluster_state)+ noOfNodes*(sizeof(ndb_mgm_node_state)+sizeof("000.000.000.000#"))); - state->hostname= 0; state->no_of_nodes= noOfNodes; ndb_mgm_node_state * ptr = &state->node_states[0]; int nodeId = 0; From 6e38a4cd0d4770df6bbacbf22b705b7e7b26c83f Mon Sep 17 00:00:00 2001 From: unknown Date: Sun, 9 Jan 2005 03:47:47 +1000 Subject: [PATCH 17/23] Ndb.hpp: Fixed some typos and added note about parallelism (Guide section). ndb/include/ndbapi/Ndb.hpp: Fixed some typos and added note about parallelism (Guide section). --- ndb/include/ndbapi/Ndb.hpp | 21 ++++++++++++--------- 1 file changed, 12 insertions(+), 9 deletions(-) diff --git a/ndb/include/ndbapi/Ndb.hpp b/ndb/include/ndbapi/Ndb.hpp index 705c7ed47d9..66cd15f190c 100644 --- a/ndb/include/ndbapi/Ndb.hpp +++ b/ndb/include/ndbapi/Ndb.hpp @@ -97,7 +97,7 @@ @section secNdbOperations Operations - Each NdbTransaction consists of a list of operations, each of which is represented + A NdbTransaction consists of a list of operations, each of which is represented by an instance of NdbOperation, NdbScanOperation, NdbIndexOperation, or NdbIndexScanOperation. @@ -221,7 +221,8 @@ @ref NdbIndexScanOperation::setBound() -# Specify attribute actions, using NdbOperation::getValue() -# Executing the transaction, using NdbTransaction::execute() - -# Iterating through the result set using NdbScanOperation::nextResult() + -# Traversing the result set by means of succssive calls to + NdbScanOperation::nextResult() Here are two brief examples illustrating this process. Once again, in order to keep things relatively short and simple, we will forego any error handling. @@ -264,7 +265,7 @@ Some additional discussion of each step required to perform a scan follows: -

Step 1: Define scan operation operation type

+

Step 1: Define Scan Operation Type

It is important to remember that only a single operation is supported for each scan operation (@ref NdbScanOperation::readTuples() or @ref NdbIndexScanOperation::readTuples()). @@ -292,8 +293,8 @@ As with transaction attributes, scan attributes are defined by name but it is also possible to use the attributes' identities to define attributes. - As previously discussed (see @ref secSync), the value read is returned as an NdbRecAttr object by - the NdbOperation::getValue() method. + As previously discussed (see @ref secSync), the value read is returned as + an NdbRecAttr object by the NdbOperation::getValue() method.

Using Scan to Update/Delete

Scanning can also be used to update or delete rows. @@ -322,9 +323,11 @@ It is also important to note that, when using NdbIndexScanOperation::BoundEQ on a partition key, only fragments containing rows will actually be scanned. - @note When performing a sorted scan, parameter parallelism to - NdbIndexScanOperation::readTuples() will - be ignored and max parallelism will be used instead. + @note When performing a sorted scan, any value passed as the + NdbIndexScanOperation::readTuples() method's parallel argument + will be ignored and maximum parallelism will be used instead. In other words, all + fragments which it is possible to scan will be scanned simultaneously and in parallel + in such cases. @subsection secScanLocks Lock handling with scans @@ -394,7 +397,7 @@ } @endcode - Here errorLine will be 3 as the error occurred in the + Here errorLine will be 3, as the error occurred in the third method called on the NdbOperation object (in this case, theOperation); if the result of NdbTransaction::getNdbErrorLine() is 0, this means that the error From 3186b340da79252758a4b1c47ea0a3b8b1b0d2a8 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 19:28:44 +0100 Subject: [PATCH 18/23] ndb - wl-1442 fix Time ordering mysql-test/r/ndb_index_ordered.result: wl-1442 fix Time. adds new type id 25 mysql-test/t/ndb_index_ordered.test: wl-1442 fix Time. adds new type id 25 ndb/include/kernel/signaldata/DictTabInfo.hpp: wl-1442 fix Time. adds new type id 25 ndb/include/ndbapi/NdbDictionary.hpp: wl-1442 fix Time. adds new type id 25 ndb/include/util/NdbSqlUtil.hpp: wl-1442 fix Time. adds new type id 25 ndb/src/common/util/NdbSqlUtil.cpp: wl-1442 fix Time. adds new type id 25 ndb/src/ndbapi/NdbDictionary.cpp: wl-1442 fix Time. adds new type id 25 ndb/src/ndbapi/NdbDictionaryImpl.cpp: wl-1442 fix Time. adds new type id 25 ndb/test/include/NdbSchemaOp.hpp: wl-1442 fix Time. adds new type id 25 ndb/tools/restore/consumer.cpp: wl-1442 fix Time. adds new type id 25 sql/ha_ndbcluster.cc: wl-1442 fix Time. adds new type id 25 --- mysql-test/r/ndb_index_ordered.result | 45 +++++++++++++++++++ mysql-test/t/ndb_index_ordered.test | 19 ++++++++ ndb/include/kernel/signaldata/DictTabInfo.hpp | 8 +++- ndb/include/ndbapi/NdbDictionary.hpp | 3 +- ndb/include/util/NdbSqlUtil.hpp | 4 +- ndb/src/common/util/NdbSqlUtil.cpp | 33 ++++++++++++++ ndb/src/ndbapi/NdbDictionary.cpp | 3 ++ ndb/src/ndbapi/NdbDictionaryImpl.cpp | 7 +++ ndb/test/include/NdbSchemaOp.hpp | 1 + ndb/tools/restore/consumer.cpp | 3 ++ sql/ha_ndbcluster.cc | 10 ++++- 11 files changed, 132 insertions(+), 4 deletions(-) diff --git a/mysql-test/r/ndb_index_ordered.result b/mysql-test/r/ndb_index_ordered.result index 466523aafa7..75a5e42732b 100644 --- a/mysql-test/r/ndb_index_ordered.result +++ b/mysql-test/r/ndb_index_ordered.result @@ -375,3 +375,48 @@ count(*)-8 select count(*)-9 from t1 use index (da) where da <= '2055-01-01'; count(*)-9 0 +select count(*)-9 from t1 use index (ye) where ye > '1900'; +count(*)-9 +0 +select count(*)-6 from t1 use index (ye) where ye >= '1955'; +count(*)-6 +0 +select count(*)-5 from t1 use index (ye) where ye > '1955'; +count(*)-5 +0 +select count(*)-5 from t1 use index (ye) where ye < '1970'; +count(*)-5 +0 +select count(*)-6 from t1 use index (ye) where ye < '2001'; +count(*)-6 +0 +select count(*)-8 from t1 use index (ye) where ye <= '2001'; +count(*)-8 +0 +select count(*)-9 from t1 use index (ye) where ye <= '2055'; +count(*)-9 +0 +select count(*)-9 from t1 use index (ti) where ti >= '00:00:00'; +count(*)-9 +0 +select count(*)-7 from t1 use index (ti) where ti > '00:00:00'; +count(*)-7 +0 +select count(*)-7 from t1 use index (ti) where ti > '05:05:05'; +count(*)-7 +0 +select count(*)-5 from t1 use index (ti) where ti > '06:06:06'; +count(*)-5 +0 +select count(*)-5 from t1 use index (ti) where ti < '10:11:11'; +count(*)-5 +0 +select count(*)-6 from t1 use index (ti) where ti <= '10:11:11'; +count(*)-6 +0 +select count(*)-8 from t1 use index (ti) where ti < '23:59:59'; +count(*)-8 +0 +select count(*)-9 from t1 use index (ti) where ti <= '23:59:59'; +count(*)-9 +0 diff --git a/mysql-test/t/ndb_index_ordered.test b/mysql-test/t/ndb_index_ordered.test index ae2f7db53fb..71635159604 100644 --- a/mysql-test/t/ndb_index_ordered.test +++ b/mysql-test/t/ndb_index_ordered.test @@ -217,3 +217,22 @@ select count(*)-5 from t1 use index (da) where da < '1970-03-03'; select count(*)-6 from t1 use index (da) where da < '2001-01-01'; select count(*)-8 from t1 use index (da) where da <= '2001-01-02'; select count(*)-9 from t1 use index (da) where da <= '2055-01-01'; + +# year +select count(*)-9 from t1 use index (ye) where ye > '1900'; +select count(*)-6 from t1 use index (ye) where ye >= '1955'; +select count(*)-5 from t1 use index (ye) where ye > '1955'; +select count(*)-5 from t1 use index (ye) where ye < '1970'; +select count(*)-6 from t1 use index (ye) where ye < '2001'; +select count(*)-8 from t1 use index (ye) where ye <= '2001'; +select count(*)-9 from t1 use index (ye) where ye <= '2055'; + +# time +select count(*)-9 from t1 use index (ti) where ti >= '00:00:00'; +select count(*)-7 from t1 use index (ti) where ti > '00:00:00'; +select count(*)-7 from t1 use index (ti) where ti > '05:05:05'; +select count(*)-5 from t1 use index (ti) where ti > '06:06:06'; +select count(*)-5 from t1 use index (ti) where ti < '10:11:11'; +select count(*)-6 from t1 use index (ti) where ti <= '10:11:11'; +select count(*)-8 from t1 use index (ti) where ti < '23:59:59'; +select count(*)-9 from t1 use index (ti) where ti <= '23:59:59'; diff --git a/ndb/include/kernel/signaldata/DictTabInfo.hpp b/ndb/include/kernel/signaldata/DictTabInfo.hpp index 392b691ae1e..3e73ae67ebe 100644 --- a/ndb/include/kernel/signaldata/DictTabInfo.hpp +++ b/ndb/include/kernel/signaldata/DictTabInfo.hpp @@ -310,7 +310,8 @@ public: ExtDatetime = NdbSqlUtil::Type::Datetime, ExtDate = NdbSqlUtil::Type::Date, ExtBlob = NdbSqlUtil::Type::Blob, - ExtText = NdbSqlUtil::Type::Text + ExtText = NdbSqlUtil::Type::Text, + ExtTime = NdbSqlUtil::Type::Time }; // Attribute data interpretation @@ -440,6 +441,11 @@ public: // head + inline part [ attr precision lower half ] AttributeArraySize = (NDB_BLOB_HEAD_SIZE << 2) + (AttributeExtPrecision & 0xFFFF); return true; + case DictTabInfo::ExtTime: + AttributeType = DictTabInfo::StringType; + AttributeSize = DictTabInfo::an8Bit; + AttributeArraySize = 3 * AttributeExtLength; + return true; }; return false; } diff --git a/ndb/include/ndbapi/NdbDictionary.hpp b/ndb/include/ndbapi/NdbDictionary.hpp index 0ca3744a3d9..454b267d1b0 100644 --- a/ndb/include/ndbapi/NdbDictionary.hpp +++ b/ndb/include/ndbapi/NdbDictionary.hpp @@ -187,7 +187,8 @@ public: Datetime, ///< Precision down to 1 sec (sizeof(Datetime) == 8 bytes ) Date, ///< Precision down to 1 day(sizeof(Date) == 4 bytes ) Blob, ///< Binary large object (see NdbBlob) - Text ///< Text blob + Text, ///< Text blob + Time = 25 ///< Time without date }; /** diff --git a/ndb/include/util/NdbSqlUtil.hpp b/ndb/include/util/NdbSqlUtil.hpp index 47bb2157e1a..10024d9b616 100644 --- a/ndb/include/util/NdbSqlUtil.hpp +++ b/ndb/include/util/NdbSqlUtil.hpp @@ -83,7 +83,8 @@ public: Datetime, // Precision down to 1 sec (size 8 bytes) Date, // Precision down to 1 day (size 4 bytes) Blob, // Blob - Text // Text blob + Text, // Text blob + Time = 25 // Time without date }; Enum m_typeId; Cmp* m_cmp; // comparison method @@ -135,6 +136,7 @@ private: static Cmp cmpDate; static Cmp cmpBlob; static Cmp cmpText; + static Cmp cmpTime; }; #endif diff --git a/ndb/src/common/util/NdbSqlUtil.cpp b/ndb/src/common/util/NdbSqlUtil.cpp index 6f490c7f611..233698ae52b 100644 --- a/ndb/src/common/util/NdbSqlUtil.cpp +++ b/ndb/src/common/util/NdbSqlUtil.cpp @@ -163,6 +163,22 @@ NdbSqlUtil::m_typeList[] = { { Type::Text, cmpText + }, + { + Type::Undefined, // 5.0 Bit + NULL + }, + { + Type::Undefined, // 5.0 Longvarchar + NULL + }, + { + Type::Undefined, // 5.0 Longvarbinary + NULL + }, + { + Type::Time, + cmpTime } }; @@ -559,6 +575,23 @@ NdbSqlUtil::cmpText(const void* info, const Uint32* p1, const Uint32* p2, Uint32 return CmpUnknown; } +int +NdbSqlUtil::cmpTime(const void* info, const Uint32* p1, const Uint32* p2, Uint32 full, Uint32 size) +{ + assert(full >= size && size > 0); + union { const Uint32* p; const unsigned char* v; } u1, u2; + u1.p = p1; + u2.p = p2; + // from Field_time::val_int + Int32 j1 = sint3korr(u1.v); + Int32 j2 = sint3korr(u2.v); + if (j1 < j2) + return -1; + if (j1 > j2) + return +1; + return 0; +} + // check charset bool diff --git a/ndb/src/ndbapi/NdbDictionary.cpp b/ndb/src/ndbapi/NdbDictionary.cpp index b47f7d2c15c..0508d8bf277 100644 --- a/ndb/src/ndbapi/NdbDictionary.cpp +++ b/ndb/src/ndbapi/NdbDictionary.cpp @@ -947,6 +947,9 @@ operator<<(NdbOut& out, const NdbDictionary::Column& col) out << "Text(" << col.getInlineSize() << "," << col.getPartSize() << ";" << col.getStripeSize() << ";" << csname << ")"; break; + case NdbDictionary::Column::Time: + out << "Time"; + break; case NdbDictionary::Column::Undefined: out << "Undefined"; break; diff --git a/ndb/src/ndbapi/NdbDictionaryImpl.cpp b/ndb/src/ndbapi/NdbDictionaryImpl.cpp index 195fdce7e3f..59474943f3b 100644 --- a/ndb/src/ndbapi/NdbDictionaryImpl.cpp +++ b/ndb/src/ndbapi/NdbDictionaryImpl.cpp @@ -148,6 +148,12 @@ NdbColumnImpl::init(Type t) m_length = 4; m_cs = default_cs; break; + case Time: + m_precision = 0; + m_scale = 0; + m_length = 1; + m_cs = NULL; + break; case Undefined: assert(false); break; @@ -1177,6 +1183,7 @@ columnTypeMapping[] = { { DictTabInfo::ExtDate, NdbDictionary::Column::Date }, { DictTabInfo::ExtBlob, NdbDictionary::Column::Blob }, { DictTabInfo::ExtText, NdbDictionary::Column::Text }, + { DictTabInfo::ExtTime, NdbDictionary::Column::Time }, { -1, -1 } }; diff --git a/ndb/test/include/NdbSchemaOp.hpp b/ndb/test/include/NdbSchemaOp.hpp index b54c011ae8b..e2fb4015b88 100644 --- a/ndb/test/include/NdbSchemaOp.hpp +++ b/ndb/test/include/NdbSchemaOp.hpp @@ -577,6 +577,7 @@ convertColumnTypeToAttrType(NdbDictionary::Column::Type _type) return String; case NdbDictionary::Column::Datetime: case NdbDictionary::Column::Date: + case NdbDictionary::Column::Time: case NdbDictionary::Column::Undefined: default: return NoAttrTypeDef; diff --git a/ndb/tools/restore/consumer.cpp b/ndb/tools/restore/consumer.cpp index dc0567803dd..4d228230423 100644 --- a/ndb/tools/restore/consumer.cpp +++ b/ndb/tools/restore/consumer.cpp @@ -74,6 +74,9 @@ BackupConsumer::create_table_string(const TableS & table, case NdbDictionary::Column::Date: pos += sprintf(buf+pos, "%s", "date"); break; + case NdbDictionary::Column::Time: + pos += sprintf(buf+pos, "%s", "time"); + break; case NdbDictionary::Column::Undefined: // pos += sprintf(buf+pos, "%s", "varchar binary"); return -1; diff --git a/sql/ha_ndbcluster.cc b/sql/ha_ndbcluster.cc index e181b421e29..e4c45490050 100644 --- a/sql/ha_ndbcluster.cc +++ b/sql/ha_ndbcluster.cc @@ -2264,6 +2264,11 @@ void ha_ndbcluster::print_results() fprintf(DBUG_FILE, "Date\t%llu", value); break; } + case NdbDictionary::Column::Time: { + Uint64 value= (Uint64) *field->ptr; + fprintf(DBUG_FILE, "Time\t%llu", value); + break; + } case NdbDictionary::Column::Blob: { Uint64 len= 0; ndb_blob->getLength(len); @@ -3327,8 +3332,11 @@ static int create_ndb_column(NDBCOL &col, col.setType(NDBCOL::Date); col.setLength(1); break; - case MYSQL_TYPE_DATE: // ? case MYSQL_TYPE_TIME: + col.setType(NDBCOL::Time); + col.setLength(1); + break; + case MYSQL_TYPE_DATE: // ? case MYSQL_TYPE_YEAR: col.setType(NDBCOL::Char); col.setLength(field->pack_length()); From 39aa7b102cc10b66193edd7a373e31ad6cd5e46f Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 19:37:50 +0100 Subject: [PATCH 19/23] ndb_constants.h: wl-1442 comment for 4.1->5.0 ndb/include/ndb_constants.h: wl-1442 comment for 4.1->5.0 --- ndb/include/ndb_constants.h | 3 +++ 1 file changed, 3 insertions(+) diff --git a/ndb/include/ndb_constants.h b/ndb/include/ndb_constants.h index 40a3d963955..b4e42fb83f5 100644 --- a/ndb/include/ndb_constants.h +++ b/ndb/include/ndb_constants.h @@ -61,6 +61,9 @@ #define NDB_TYPE_LONG_VARCHAR 23 #define NDB_TYPE_LONG_VARBINARY 24 +// add at next merge 4.1->5.0 +// #define NDB_TYPE_TIME 25 + #define NDB_TYPE_MAX 25 #endif From 4c8d52aa80ce2a2131783bc2df5b02f21baa1c96 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 21:25:31 +0100 Subject: [PATCH 20/23] few harmless warnings from automated code-checking tools fixed client/mysql.cc: few harmless warnings from automated code-checking tools fixed cleanup --- client/completion_hash.cc | 3 ++- client/mysql.cc | 9 ++++++--- cmd-line-utils/libedit/parse.c | 3 ++- pstack/pstack.c | 2 +- 4 files changed, 11 insertions(+), 6 deletions(-) diff --git a/client/completion_hash.cc b/client/completion_hash.cc index 536e7f9373a..7a3b363c93c 100644 --- a/client/completion_hash.cc +++ b/client/completion_hash.cc @@ -79,7 +79,8 @@ int completion_hash_update(HashTable *ht, char *arKey, uint nKeyLength, if (!memcmp(p->arKey, arKey, nKeyLength)) { entry *n; - n = (entry *) alloc_root(&ht->mem_root,sizeof(entry)); + if (!(n = (entry *) alloc_root(&ht->mem_root,sizeof(entry)))) + return FAILURE; n->pNext = p->pData; n->str = str; p->pData = n; diff --git a/client/mysql.cc b/client/mysql.cc index 0ea0f10f5d7..bfa827a6e95 100644 --- a/client/mysql.cc +++ b/client/mysql.cc @@ -1502,7 +1502,10 @@ You can turn off this feature to get a quicker startup with -A\n\n"); if (!(field_names[i] = (char **) alloc_root(&hash_mem_root, sizeof(char *) * (num_fields*2+1)))) - break; + { + mysql_free_result(fields); + break; + } field_names[i][num_fields*2]= '\0'; j=0; while ((sql_field=mysql_fetch_field(fields))) @@ -2077,10 +2080,10 @@ print_table_data_html(MYSQL_RES *result) } while ((cur = mysql_fetch_row(result))) { + ulong *lengths=mysql_fetch_lengths(result); (void) tee_fputs("", PAGER); for (uint i=0; i < mysql_num_fields(result); i++) { - ulong *lengths=mysql_fetch_lengths(result); (void) tee_fputs("", PAGER); safe_put_field(cur[i],lengths[i]); (void) tee_fputs("", PAGER); @@ -2106,10 +2109,10 @@ print_table_data_xml(MYSQL_RES *result) fields = mysql_fetch_fields(result); while ((cur = mysql_fetch_row(result))) { + ulong *lengths=mysql_fetch_lengths(result); (void) tee_fputs("\n \n", PAGER); for (uint i=0; i < mysql_num_fields(result); i++) { - ulong *lengths=mysql_fetch_lengths(result); tee_fprintf(PAGER, "\t<%s>", (fields[i].name ? (fields[i].name[0] ? fields[i].name : "   ") : "NULL")); diff --git a/cmd-line-utils/libedit/parse.c b/cmd-line-utils/libedit/parse.c index b113353d464..d09b890c1ab 100644 --- a/cmd-line-utils/libedit/parse.c +++ b/cmd-line-utils/libedit/parse.c @@ -87,7 +87,8 @@ parse_line(EditLine *el, const char *line) int argc; Tokenizer *tok; - tok = tok_init(NULL); + if (!(tok = tok_init(NULL))) + return -1; tok_line(tok, line, &argc, &argv); argc = el_parse(el, argc, argv); tok_end(tok); diff --git a/pstack/pstack.c b/pstack/pstack.c index 75869686e35..4cdd80d68b5 100644 --- a/pstack/pstack.c +++ b/pstack/pstack.c @@ -1663,7 +1663,7 @@ pr_tag_type (p, name, id, kind) { struct pr_handle *info = (struct pr_handle *) p; const char *t, *tag; - char idbuf[20]; + char idbuf[30]; switch (kind) { From 09a487266171a297db9fab88710c224e7526e8b6 Mon Sep 17 00:00:00 2001 From: unknown Date: Sat, 8 Jan 2005 23:24:25 +0100 Subject: [PATCH 21/23] ndb - wl-1442 4.1->5.0 merge fixes ndb/include/kernel/signaldata/DictTabInfo.hpp: wl-1442 4.1->5.0 merge fixes ndb/include/ndb_constants.h: wl-1442 4.1->5.0 merge fixes ndb/include/util/NdbSqlUtil.hpp: wl-1442 4.1->5.0 merge fixes ndb/src/common/util/NdbSqlUtil.cpp: wl-1442 4.1->5.0 merge fixes --- ndb/include/kernel/signaldata/DictTabInfo.hpp | 1 - ndb/include/ndb_constants.h | 10 +++++++--- ndb/include/util/NdbSqlUtil.hpp | 2 +- ndb/src/common/util/NdbSqlUtil.cpp | 11 ++++++----- 4 files changed, 14 insertions(+), 10 deletions(-) diff --git a/ndb/include/kernel/signaldata/DictTabInfo.hpp b/ndb/include/kernel/signaldata/DictTabInfo.hpp index 10e78e9a4d2..65937cae0d1 100644 --- a/ndb/include/kernel/signaldata/DictTabInfo.hpp +++ b/ndb/include/kernel/signaldata/DictTabInfo.hpp @@ -384,7 +384,6 @@ public: AttributeArraySize = (NDB_BLOB_HEAD_SIZE << 2) + (AttributeExtPrecision & 0xFFFF); return true; case DictTabInfo::ExtTime: - AttributeType = DictTabInfo::StringType; AttributeSize = DictTabInfo::an8Bit; AttributeArraySize = 3 * AttributeExtLength; return true; diff --git a/ndb/include/ndb_constants.h b/ndb/include/ndb_constants.h index 04d86e267f7..91b026fdb53 100644 --- a/ndb/include/ndb_constants.h +++ b/ndb/include/ndb_constants.h @@ -53,12 +53,16 @@ #define NDB_TYPE_VARCHAR 15 #define NDB_TYPE_BINARY 16 #define NDB_TYPE_VARBINARY 17 -#define NDB_TYPE_DATETIME 18 // need to fix -#define NDB_TYPE_TIMESPEC 19 // need to fix +#define NDB_TYPE_DATETIME 18 +#define NDB_TYPE_DATE 19 #define NDB_TYPE_BLOB 20 #define NDB_TYPE_TEXT 21 #define NDB_TYPE_BIT 22 -#define NDB_TYPE_MAX 23 +// fill in NDB_TYPE_LONGVAR* at next merge 5.0-ndb -> 5.0 + +#define NDB_TYPE_TIME 25 + +#define NDB_TYPE_MAX 26 #endif diff --git a/ndb/include/util/NdbSqlUtil.hpp b/ndb/include/util/NdbSqlUtil.hpp index ec637566f54..058c00df93d 100644 --- a/ndb/include/util/NdbSqlUtil.hpp +++ b/ndb/include/util/NdbSqlUtil.hpp @@ -83,7 +83,7 @@ public: Binary = NDB_TYPE_BINARY, Varbinary = NDB_TYPE_VARBINARY, Datetime = NDB_TYPE_DATETIME, - Timespec = NDB_TYPE_TIMESPEC, + Date = NDB_TYPE_DATE, Blob = NDB_TYPE_BLOB, Text = NDB_TYPE_TEXT, Bit = NDB_TYPE_BIT, diff --git a/ndb/src/common/util/NdbSqlUtil.cpp b/ndb/src/common/util/NdbSqlUtil.cpp index 1c85c920f88..e82b83aff63 100644 --- a/ndb/src/common/util/NdbSqlUtil.cpp +++ b/ndb/src/common/util/NdbSqlUtil.cpp @@ -449,6 +449,7 @@ NdbSqlUtil::cmpVarchar(const void* info, const void* p1, unsigned n1, const void return 0; } +int NdbSqlUtil::cmpBinary(const void* info, const void* p1, unsigned n1, const void* p2, unsigned n2, bool full) { const uchar* v1 = (const uchar*)p1; @@ -505,7 +506,7 @@ NdbSqlUtil::cmpDate(const void* info, const void* p1, unsigned n1, const void* p return 0; } assert(! full); - return cmpUnknown; + return CmpUnknown; #else if (n2 >= 4) { // may access 4-th byte const uchar* v1 = (const uchar*)p1; @@ -522,7 +523,7 @@ NdbSqlUtil::cmpDate(const void* info, const void* p1, unsigned n1, const void* p return 0; } assert(! full); - return cmpUnknown; + return CmpUnknown; #endif } @@ -543,14 +544,14 @@ NdbSqlUtil::cmpText(const void* info, const void* p1, unsigned n1, const void* p } int -NdbSqlUtil::cmpTime(const void* info, const Uint32* p1, const Uint32* p2, Uint32 full, Uint32 size) +NdbSqlUtil::cmpTime(const void* info, const void* p1, unsigned n1, const void* p2, unsigned n2, bool full) { if (n2 >= 4) { // may access 4-th byte const uchar* v1 = (const uchar*)p1; const uchar* v2 = (const uchar*)p2; // from Field_time::val_int - Int32 j1 = sint3korr(u1.v); - Int32 j2 = sint3korr(u2.v); + Int32 j1 = sint3korr(v1); + Int32 j2 = sint3korr(v2); if (j1 < j2) return -1; if (j1 > j2) From 3fbb1dd5fff45824f25916ad40488592a067ca86 Mon Sep 17 00:00:00 2001 From: unknown Date: Sun, 9 Jan 2005 00:45:05 +0100 Subject: [PATCH 22/23] updated some mgmapi docs --- ndb/include/mgmapi/mgmapi.h | 29 ++++++++++++++++++++--------- ndb/src/mgmapi/mgmapi.cpp | 1 + 2 files changed, 21 insertions(+), 9 deletions(-) diff --git a/ndb/include/mgmapi/mgmapi.h b/ndb/include/mgmapi/mgmapi.h index 093186179b7..5d426e5753b 100644 --- a/ndb/include/mgmapi/mgmapi.h +++ b/ndb/include/mgmapi/mgmapi.h @@ -464,6 +464,15 @@ extern "C" { * @param connect_string Connect string to the management server, * * @return -1 on error. + * + * @code + * := [,][,] + * := nodeid= + * := [:] + * is an integer larger than 1 identifying a node in config.ini + * is an integer referring to a regular unix port + * is a string which is a valid Internet host address + * @endcode */ int ndb_mgm_set_connectstring(NdbMgmHandle handle, const char *connect_string); @@ -471,8 +480,8 @@ extern "C" { /** * Get connectstring used for connection * - * @note returns what the connectstring defaults to if the above call has - * not been performed + * @note returns what the connectstring defaults to if the + * ndb_mgm_set_connectstring() call has not been performed * * @param handle Management handle * @@ -481,7 +490,8 @@ extern "C" { const char *ndb_mgm_get_connectstring(NdbMgmHandle handle, char *buf, int buf_sz); /** - * Connect to a management server + * Connect to a management server. Coonect string is set by + * ndb_mgm_set_connectstring(). * * @param handle Management handle. * @return -1 on error. @@ -502,7 +512,8 @@ extern "C" { * * @param handle Management handle * - * @return node id + * @return node id, 0 indicated that no nodeid has been + * specified */ int ndb_mgm_get_configuration_nodeid(NdbMgmHandle handle); @@ -524,6 +535,7 @@ extern "C" { */ const char *ndb_mgm_get_connected_host(NdbMgmHandle handle); +#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL /** @} *********************************************************************/ /** * @name Functions: Convert between different data formats @@ -572,7 +584,6 @@ extern "C" { const char * ndb_mgm_get_node_status_string(enum ndb_mgm_node_status status); const char * ndb_mgm_get_clusterlog_level_string(enum ndb_mgm_clusterlog_level); -#ifndef DOXYGEN_SHOULD_SKIP_INTERNAL ndb_mgm_event_category ndb_mgm_match_event_category(const char *); const char * ndb_mgm_get_event_category_string(enum ndb_mgm_event_category); #endif @@ -799,9 +810,9 @@ extern "C" { * Start backup * * @param handle NDB management handle. - * @param wait_completed 0=don't wait for confirmation - 1=wait for backup started - 2=wait for backup completed + * @param wait_completed 0=don't wait for confirmation, + * 1=wait for backup started, + * 2=wait for backup completed * @param backup_id Backup id is returned from function. * @param reply Reply message. * @return -1 on error. @@ -861,7 +872,7 @@ extern "C" { * Get configuration * @param handle NDB management handle. * @param version Version of configuration, 0 means latest - * @see MAKE_VERSION + * (which is the only supported input at this point) * * @return configuration * diff --git a/ndb/src/mgmapi/mgmapi.cpp b/ndb/src/mgmapi/mgmapi.cpp index 747178301f0..a5e01919781 100644 --- a/ndb/src/mgmapi/mgmapi.cpp +++ b/ndb/src/mgmapi/mgmapi.cpp @@ -1045,6 +1045,7 @@ struct ndb_mgm_event_categories { "CHECKPOINT", NDB_MGM_EVENT_CATEGORY_CHECKPOINT }, { "DEBUG", NDB_MGM_EVENT_CATEGORY_DEBUG }, { "INFO", NDB_MGM_EVENT_CATEGORY_INFO }, + { "WARNING", NDB_MGM_EVENT_CATEGORY_WARNING }, { "ERROR", NDB_MGM_EVENT_CATEGORY_ERROR }, { "GREP", NDB_MGM_EVENT_CATEGORY_GREP }, { "BACKUP", NDB_MGM_EVENT_CATEGORY_BACKUP }, From 91a3e90baf0a515470622f7720fcea64745f70fa Mon Sep 17 00:00:00 2001 From: unknown Date: Sun, 9 Jan 2005 01:14:11 +0100 Subject: [PATCH 23/23] ndb - wl-1442 merge fix 5.0 -> 5.0-ndb ndb/include/util/NdbSqlUtil.hpp: wl-1442 merge fix 5.0 -> 5.0-ndb --- ndb/include/util/NdbSqlUtil.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/ndb/include/util/NdbSqlUtil.hpp b/ndb/include/util/NdbSqlUtil.hpp index 529e02f1d89..75e2a819174 100644 --- a/ndb/include/util/NdbSqlUtil.hpp +++ b/ndb/include/util/NdbSqlUtil.hpp @@ -89,7 +89,7 @@ public: Date = NDB_TYPE_DATE, Blob = NDB_TYPE_BLOB, Text = NDB_TYPE_TEXT, - Bit = NDB_TYPE_BIT + Bit = NDB_TYPE_BIT, Longvarchar = NDB_TYPE_LONG_VARCHAR, Longvarbinary = NDB_TYPE_LONG_VARBINARY, Time = NDB_TYPE_TIME