From e99ce4fa658db655b0b2153a65dc4043bb98893f Mon Sep 17 00:00:00 2001 From: unknown Date: Thu, 5 Oct 2006 17:29:50 +0500 Subject: [PATCH 1/4] Fix for bug #22377: iNCONSISTENCY WITH null Backport. See #20910: NOT NULL column reported as NULL in SHOW FIELDS or INFORMATION_SCHEMA mysql-test/r/type_ranges.result: Fix for bug #22377: iNCONSISTENCY WITH null - results adjusted. mysql-test/r/type_timestamp.result: Fix for bug #22377: iNCONSISTENCY WITH null - results adjusted. sql/sql_show.cc: Fix for bug #22377: iNCONSISTENCY WITH null - as NULL values cannot be stored in 'timestamp not null' fields, don't make an exception for them. --- mysql-test/r/type_ranges.result | 6 +++--- mysql-test/r/type_timestamp.result | 18 +++++++++--------- sql/sql_show.cc | 11 +---------- 3 files changed, 13 insertions(+), 22 deletions(-) diff --git a/mysql-test/r/type_ranges.result b/mysql-test/r/type_ranges.result index 90207f39417..2e8fa4c26b7 100644 --- a/mysql-test/r/type_ranges.result +++ b/mysql-test/r/type_ranges.result @@ -54,7 +54,7 @@ ushort smallint(5) unsigned zerofill NULL MUL 00000 # umedium mediumint(8) unsigned NULL MUL 0 # ulong int(11) unsigned NULL MUL 0 # ulonglong bigint(13) unsigned NULL MUL 0 # -time_stamp timestamp NULL YES CURRENT_TIMESTAMP # +time_stamp timestamp NULL CURRENT_TIMESTAMP # date_field date NULL YES NULL # time_field time NULL YES NULL # date_time datetime NULL YES NULL # @@ -222,7 +222,7 @@ ushort smallint(5) unsigned zerofill NULL 00000 # umedium mediumint(8) unsigned NULL MUL 0 # ulong int(11) unsigned NULL MUL 0 # ulonglong bigint(13) unsigned NULL MUL 0 # -time_stamp timestamp NULL YES CURRENT_TIMESTAMP # +time_stamp timestamp NULL CURRENT_TIMESTAMP # date_field varchar(10) latin1_swedish_ci YES NULL # time_field time NULL YES NULL # date_time datetime NULL YES NULL # @@ -248,7 +248,7 @@ ushort smallint(5) unsigned zerofill NULL 00000 # umedium mediumint(8) unsigned NULL 0 # ulong int(11) unsigned NULL 0 # ulonglong bigint(13) unsigned NULL 0 # -time_stamp timestamp NULL YES 0000-00-00 00:00:00 # +time_stamp timestamp NULL 0000-00-00 00:00:00 # date_field varchar(10) latin1_swedish_ci YES NULL # time_field time NULL YES NULL # date_time datetime NULL YES NULL # diff --git a/mysql-test/r/type_timestamp.result b/mysql-test/r/type_timestamp.result index c0396e4640d..4e71d76785a 100644 --- a/mysql-test/r/type_timestamp.result +++ b/mysql-test/r/type_timestamp.result @@ -188,9 +188,9 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES 2003-01-01 00:00:00 +t1 timestamp 2003-01-01 00:00:00 t2 datetime YES NULL -t3 timestamp YES 0000-00-00 00:00:00 +t3 timestamp 0000-00-00 00:00:00 drop table t1; create table t1 (t1 timestamp default now(), t2 datetime, t3 timestamp); SET TIMESTAMP=1000000002; @@ -212,9 +212,9 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES CURRENT_TIMESTAMP +t1 timestamp CURRENT_TIMESTAMP t2 datetime YES NULL -t3 timestamp YES 0000-00-00 00:00:00 +t3 timestamp 0000-00-00 00:00:00 drop table t1; create table t1 (t1 timestamp default '2003-01-01 00:00:00' on update now(), t2 datetime); SET TIMESTAMP=1000000004; @@ -238,7 +238,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES 2003-01-01 00:00:00 +t1 timestamp 2003-01-01 00:00:00 t2 datetime YES NULL drop table t1; create table t1 (t1 timestamp default now() on update now(), t2 datetime); @@ -263,7 +263,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES CURRENT_TIMESTAMP +t1 timestamp CURRENT_TIMESTAMP t2 datetime YES NULL drop table t1; create table t1 (t1 timestamp, t2 datetime, t3 timestamp); @@ -289,9 +289,9 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES CURRENT_TIMESTAMP +t1 timestamp CURRENT_TIMESTAMP t2 datetime YES NULL -t3 timestamp YES 0000-00-00 00:00:00 +t3 timestamp 0000-00-00 00:00:00 drop table t1; create table t1 (t1 timestamp default current_timestamp on update current_timestamp, t2 datetime); SET TIMESTAMP=1000000009; @@ -315,7 +315,7 @@ t1 CREATE TABLE `t1` ( ) ENGINE=MyISAM DEFAULT CHARSET=latin1 show columns from t1; Field Type Null Key Default Extra -t1 timestamp YES CURRENT_TIMESTAMP +t1 timestamp CURRENT_TIMESTAMP t2 datetime YES NULL delete from t1; insert into t1 values ('2004-04-01 00:00:00', '2004-04-01 00:00:00'); diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 41e145790e9..bd4d7c4d851 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -714,16 +714,7 @@ mysqld_show_fields(THD *thd, TABLE_LIST *table_list,const char *wild, if (verbose) protocol->store(field->has_charset() ? field->charset()->name : "NULL", system_charset_info); - /* - Even if TIMESTAMP field can't contain NULL as its value it - will accept NULL if you will try to insert such value and will - convert NULL value to current TIMESTAMP. So YES here means - that NULL is allowed for assignment (but may be won't be - returned). - */ - pos=(byte*) ((flags & NOT_NULL_FLAG) && - field->type() != FIELD_TYPE_TIMESTAMP ? - "" : "YES"); + pos= (byte*) ((flags & NOT_NULL_FLAG) ? "" : "YES"); protocol->store((const char*) pos, system_charset_info); pos=(byte*) ((field->flags & PRI_KEY_FLAG) ? "PRI" : (field->flags & UNIQUE_KEY_FLAG) ? "UNI" : From 4693771f28844ec2abd3756414b42fc619baf9f6 Mon Sep 17 00:00:00 2001 From: unknown Date: Mon, 11 Dec 2006 15:39:15 +0100 Subject: [PATCH 2/4] Bug#20225 mysqltest runs in an endless loop when trying to start rpl_sys test suite - Add printout in safe_connect indicating that mysqltest is in a loop waiting for connection to mysqld. Will be printed when --verbose is passed as argument to mysqltest client/mysqltest.c: Bug#20225 mysqltest runs in an endless loop when trying to start rpl_sys test suite - Add printout in safe_connect indicating that mysqltest is in a loop waiting for connection to mysqld --- client/mysqltest.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/client/mysqltest.c b/client/mysqltest.c index ad7124601ab..6f0a1ba3498 100644 --- a/client/mysqltest.c +++ b/client/mysqltest.c @@ -2970,7 +2970,12 @@ void safe_connect(MYSQL* mysql, const char *name, const char *host, if ((mysql_errno(mysql) == CR_CONN_HOST_ERROR || mysql_errno(mysql) == CR_CONNECTION_ERROR) && failed_attempts < opt_max_connect_retries) + { + verbose_msg("Connect attempt %d/%d failed: %d: %s", failed_attempts, + opt_max_connect_retries, mysql_errno(mysql), + mysql_error(mysql)); my_sleep(connection_retry_sleep); + } else { if (failed_attempts > 0) From 58558f0686973d643525b0efd40304179496b18e Mon Sep 17 00:00:00 2001 From: unknown Date: Mon, 11 Dec 2006 16:43:21 +0100 Subject: [PATCH 3/4] Wait for INSERT DELAYED to finish i.e sleep in while loop until "select count" is one more. --- mysql-test/r/archive.result | 6 ++++++ mysql-test/t/archive.test | 10 +++++++--- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/mysql-test/r/archive.result b/mysql-test/r/archive.result index 3be1cdcf15a..f73a80dde65 100644 --- a/mysql-test/r/archive.result +++ b/mysql-test/r/archive.result @@ -11120,7 +11120,13 @@ auto fld1 companynr fld3 fld4 fld5 fld6 2 011401 37 breaking dreaded Steinberg W 3 011402 37 Romans scholastics jarring 4 011403 37 intercepted audiology tinily +SELECT COUNT(auto) FROM t2; +COUNT(auto) +1213 INSERT DELAYED INTO t2 VALUES (4,011403,37,'intercepted','audiology','tinily',''); +SELECT COUNT(auto) FROM t2; +COUNT(auto) +1214 ALTER TABLE t2 DROP COLUMN fld6; SHOW CREATE TABLE t2; Table Create Table diff --git a/mysql-test/t/archive.test b/mysql-test/t/archive.test index f712a770712..80533f21311 100644 --- a/mysql-test/t/archive.test +++ b/mysql-test/t/archive.test @@ -1345,10 +1345,14 @@ SELECT * FROM t2; CHECK TABLE t2; SELECT * FROM t2; - -# Just test syntax, we will never know if the output is right or wrong -# Must be the last test +# Test INSERT DELAYED and wait until the table has one more record +SELECT COUNT(auto) FROM t2; INSERT DELAYED INTO t2 VALUES (4,011403,37,'intercepted','audiology','tinily',''); +while (`SELECT COUNT(auto)!=1214 FROM t2`) +{ + sleep 0.1; +} +SELECT COUNT(auto) FROM t2; # Adding test for alter table ALTER TABLE t2 DROP COLUMN fld6; From 29bcffd77e32abc94600b9078f254b159a2dde8d Mon Sep 17 00:00:00 2001 From: unknown Date: Thu, 14 Dec 2006 15:23:44 +0100 Subject: [PATCH 4/4] BUG#24687 func_misc test fails on win64 - Use same precision (milliseconds) for all time functions used when calculating time for pthread_cond_timedwait - Use 'GetSystemTimeAsFileTime' for both start and curr time include/config-win.h: Move all defines for 'pthread_cond_timedwait' to my_pthread.h include/my_global.h: Move all defines for 'pthread_cond_timedwait' to my_pthread.h include/my_pthread.h: Redefine "struct timespec" to better suite the needs of 'pthread_cond_timedwait' for windows implementation Add windows specific define for set_timespec_nsec Move all defines related to pthread_cond_timed wait to same file Declare union for reading FILETIME as __int64 with correct alignment mysys/my_wincond.c: Use 'GetSystemTimeAsFileTime()' both for getting start and current time Use new members of "struct timespec" Make sure the calculated timeout value never exceeds the value passed to set_timespec/set_timespec_nsec server-tools/instance-manager/guardian.cc: Use set_timespec macro server-tools/instance-manager/instance.cc: Use set_timespec macro --- include/config-win.h | 1 - include/my_global.h | 36 +---------- include/my_pthread.h | 79 ++++++++++++++++++++--- mysys/my_wincond.c | 28 ++++++-- server-tools/instance-manager/guardian.cc | 5 +- server-tools/instance-manager/instance.cc | 5 +- 6 files changed, 96 insertions(+), 58 deletions(-) diff --git a/include/config-win.h b/include/config-win.h index 75133ddc837..3c76dee40a1 100644 --- a/include/config-win.h +++ b/include/config-win.h @@ -249,7 +249,6 @@ inline double ulonglong2double(ulonglong value) #define tell(A) _telli64(A) #endif -#define set_timespec(ABSTIME,SEC) { (ABSTIME).tv_sec=time((time_t*)0) + (time_t) (SEC); (ABSTIME).tv_nsec=0; } #define STACK_DIRECTION -1 diff --git a/include/my_global.h b/include/my_global.h index 7c072b2fc5c..d297f6f543c 100644 --- a/include/my_global.h +++ b/include/my_global.h @@ -1010,41 +1010,7 @@ typedef char bool; /* Ordinary boolean values 0 1 */ #define MY_HOW_OFTEN_TO_ALARM 2 /* How often we want info on screen */ #define MY_HOW_OFTEN_TO_WRITE 1000 /* How often we want info on screen */ -#ifdef HAVE_TIMESPEC_TS_SEC -#ifndef set_timespec -#define set_timespec(ABSTIME,SEC) \ -{ \ - (ABSTIME).ts_sec=time(0) + (time_t) (SEC); \ - (ABSTIME).ts_nsec=0; \ -} -#endif /* !set_timespec */ -#ifndef set_timespec_nsec -#define set_timespec_nsec(ABSTIME,NSEC) \ -{ \ - ulonglong now= my_getsystime() + (NSEC/100); \ - (ABSTIME).ts_sec= (now / ULL(10000000)); \ - (ABSTIME).ts_nsec= (now % ULL(10000000) * 100 + ((NSEC) % 100)); \ -} -#endif /* !set_timespec_nsec */ -#else -#ifndef set_timespec -#define set_timespec(ABSTIME,SEC) \ -{\ - struct timeval tv;\ - gettimeofday(&tv,0);\ - (ABSTIME).tv_sec=tv.tv_sec+(time_t) (SEC);\ - (ABSTIME).tv_nsec=tv.tv_usec*1000;\ -} -#endif /* !set_timespec */ -#ifndef set_timespec_nsec -#define set_timespec_nsec(ABSTIME,NSEC) \ -{\ - ulonglong now= my_getsystime() + (NSEC/100); \ - (ABSTIME).tv_sec= (time_t) (now / ULL(10000000)); \ - (ABSTIME).tv_nsec= (long) (now % ULL(10000000) * 100 + ((NSEC) % 100)); \ -} -#endif /* !set_timespec_nsec */ -#endif /* HAVE_TIMESPEC_TS_SEC */ + /* Define-funktions for reading and storing in machine independent format diff --git a/include/my_pthread.h b/include/my_pthread.h index 300291610d3..ebba0ab32e1 100644 --- a/include/my_pthread.h +++ b/include/my_pthread.h @@ -69,14 +69,6 @@ typedef struct { #endif } pthread_cond_t; - -#ifndef OS2 -struct timespec { /* For pthread_cond_timedwait() */ - time_t tv_sec; - long tv_nsec; -}; -#endif - typedef int pthread_mutexattr_t; #define win_pthread_self my_thread_var->pthread_self #ifdef OS2 @@ -87,6 +79,34 @@ typedef void * (_Optlink *pthread_handler)(void *); typedef void * (__cdecl *pthread_handler)(void *); #endif +/* + Struct and macros to be used in combination with the + windows implementation of pthread_cond_timedwait +*/ + +/* + Declare a union to make sure FILETIME is properly aligned + so it can be used directly as a 64 bit value. The value + stored is in 100ns units. + */ + union ft64 { + FILETIME ft; + __int64 i64; + }; +struct timespec { + union ft64 start; + /* The max timeout value in millisecond for pthread_cond_timedwait */ + long timeout_msec; +}; +#define set_timespec(ABSTIME,SEC) { \ + GetSystemTimeAsFileTime(&((ABSTIME).start.ft)); \ + (ABSTIME).timeout_msec= (long)((SEC)*1000); \ +} +#define set_timespec_nsec(ABSTIME,NSEC) { \ + GetSystemTimeAsFileTime(&((ABSTIME).start.ft)); \ + (ABSTIME).timeout_msec= (long)((NSEC)/1000000); \ +} + void win_pthread_init(void); int win_pthread_setspecific(void *A,void *B,uint length); int pthread_create(pthread_t *,pthread_attr_t *,pthread_handler,void *); @@ -164,8 +184,6 @@ extern int pthread_mutex_destroy (pthread_mutex_t *); #define pthread_condattr_init(A) #define pthread_condattr_destroy(A) -/*Irena: compiler does not like this: */ -/*#define my_pthread_getprio(pthread_t thread_id) pthread_dummy(0) */ #define my_pthread_getprio(thread_id) pthread_dummy(0) #elif defined(HAVE_UNIXWARE7_THREADS) @@ -473,6 +491,47 @@ void my_pthread_attr_getstacksize(pthread_attr_t *attrib, size_t *size); int my_pthread_mutex_trylock(pthread_mutex_t *mutex); #endif +/* + The defines set_timespec and set_timespec_nsec should be used + for calculating an absolute time at which + pthread_cond_timedwait should timeout +*/ +#ifdef HAVE_TIMESPEC_TS_SEC +#ifndef set_timespec +#define set_timespec(ABSTIME,SEC) \ +{ \ + (ABSTIME).ts_sec=time(0) + (time_t) (SEC); \ + (ABSTIME).ts_nsec=0; \ +} +#endif /* !set_timespec */ +#ifndef set_timespec_nsec +#define set_timespec_nsec(ABSTIME,NSEC) \ +{ \ + ulonglong now= my_getsystime() + (NSEC/100); \ + (ABSTIME).ts_sec= (now / ULL(10000000)); \ + (ABSTIME).ts_nsec= (now % ULL(10000000) * 100 + ((NSEC) % 100)); \ +} +#endif /* !set_timespec_nsec */ +#else +#ifndef set_timespec +#define set_timespec(ABSTIME,SEC) \ +{\ + struct timeval tv;\ + gettimeofday(&tv,0);\ + (ABSTIME).tv_sec=tv.tv_sec+(time_t) (SEC);\ + (ABSTIME).tv_nsec=tv.tv_usec*1000;\ +} +#endif /* !set_timespec */ +#ifndef set_timespec_nsec +#define set_timespec_nsec(ABSTIME,NSEC) \ +{\ + ulonglong now= my_getsystime() + (NSEC/100); \ + (ABSTIME).tv_sec= (time_t) (now / ULL(10000000)); \ + (ABSTIME).tv_nsec= (long) (now % ULL(10000000) * 100 + ((NSEC) % 100)); \ +} +#endif /* !set_timespec_nsec */ +#endif /* HAVE_TIMESPEC_TS_SEC */ + /* safe_mutex adds checking to mutex for easier debugging */ #if defined(__NETWARE__) && !defined(SAFE_MUTEX_DETECT_DESTROY) diff --git a/mysys/my_wincond.c b/mysys/my_wincond.c index 8c497e8f250..327addff2cc 100644 --- a/mysys/my_wincond.c +++ b/mysys/my_wincond.c @@ -54,14 +54,30 @@ int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex) int pthread_cond_timedwait(pthread_cond_t *cond, pthread_mutex_t *mutex, struct timespec *abstime) { - struct _timeb curtime; int result; - long timeout; - _ftime(&curtime); - timeout= ((long) (abstime->tv_sec - curtime.time)*1000L + - (long)((abstime->tv_nsec/1000) - curtime.millitm)/1000L); - if (timeout < 0) /* Some safety */ + long timeout; + union ft64 now; + + GetSystemTimeAsFileTime(&now.ft); + + /* + - subtract start time from current time(values are in 100ns units + - convert to millisec by dividing with 10000 + - subtract time since start from max timeout + */ + timeout= abstime->timeout_msec - (long)((now.i64 - abstime->start.i64) / 10000); + + /* Don't allow the timeout to be negative */ + if (timeout < 0) timeout = 0L; + + /* + Make sure the calucated time does not exceed original timeout + value which could cause "wait for ever" if system time changes + */ + if (timeout > abstime->timeout_msec) + timeout= abstime->timeout_msec; + InterlockedIncrement(&cond->waiting); LeaveCriticalSection(mutex); result=WaitForSingleObject(cond->semaphore,timeout); diff --git a/server-tools/instance-manager/guardian.cc b/server-tools/instance-manager/guardian.cc index 0a037b5b98a..9fabb1923a8 100644 --- a/server-tools/instance-manager/guardian.cc +++ b/server-tools/instance-manager/guardian.cc @@ -228,9 +228,8 @@ void Guardian_thread::run() node= node->next; } - timeout.tv_sec= time(NULL) + monitoring_interval; - timeout.tv_nsec= 0; - + set_timespec(timeout, monitoring_interval); + /* check the loop predicate before sleeping */ if (!(shutdown_requested && (!(guarded_instances)))) thread_registry.cond_timedwait(&thread_info, &COND_guardian, diff --git a/server-tools/instance-manager/instance.cc b/server-tools/instance-manager/instance.cc index daa8082ef2f..39793b9a234 100644 --- a/server-tools/instance-manager/instance.cc +++ b/server-tools/instance-manager/instance.cc @@ -476,10 +476,9 @@ int Instance::stop() waitchild= options.shutdown_delay_val; kill_instance(SIGTERM); - /* sleep on condition to wait for SIGCHLD */ - timeout.tv_sec= time(NULL) + waitchild; - timeout.tv_nsec= 0; + /* sleep on condition to wait for SIGCHLD */ + set_timespec(timeout, waitchild); if (pthread_mutex_lock(&LOCK_instance)) return ER_STOP_INSTANCE;