diff options
author | unknown <monty@mysql.com> | 2004-04-28 17:45:08 +0300 |
---|---|---|
committer | unknown <monty@mysql.com> | 2004-04-28 17:45:08 +0300 |
commit | 8b9ecce08ccccf645546465b505550a9241dff9d (patch) | |
tree | 44b9496a8f3b14561950eae22c33c0f3de67bd70 | |
parent | b0a8fde89732a11475144f0f2ab88acedcebdf86 (diff) | |
download | mariadb-git-8b9ecce08ccccf645546465b505550a9241dff9d.tar.gz |
Fixed http address in some scripts (Bug #3460)
Output TIMESTAMP in 4.1 format for 4.1 tables (or for TIMESTAMP(19)) (portability fix)
Fixed that INTERVAL can handle big integers. (Bug #3498)
Fixed that hostname="" works identical as hostname="%" for table/column grants (Bug #3473)
mysql-test/mysql-test-run.sh:
Fixed wrong http address (Bug #3460)
mysql-test/r/func_time.result:
Results for new test cases
mysql-test/t/func_time.test:
Added test of INTERVAL with big integers
scripts/mysqld_safe.sh:
Added html address to manual in case of error
sql/field.cc:
Output TIMESTAMP in 4.1 format for 4.1 tables (or for TIMESTAMP(19))
sql/item_timefunc.cc:
Fixed that INTERVAL can handle big integers. (Bug #3498)
sql/mysql_priv.h:
Removed not needed prototype
sql/sql_acl.cc:
Fixed that hostname="" works identical as hostname="%" for table/column grants (Bug #3473)
Moved GRANT_TABLE::GRANT_TABLE functions ou from class definition to make it possible to debug them
sql/structs.h:
Fix for long values to INTERVAL
-rw-r--r-- | mysql-test/mysql-test-run.sh | 2 | ||||
-rw-r--r-- | mysql-test/r/func_time.result | 30 | ||||
-rw-r--r-- | mysql-test/t/func_time.test | 19 | ||||
-rw-r--r-- | scripts/mysqld_safe.sh | 2 | ||||
-rw-r--r-- | sql/field.cc | 2 | ||||
-rw-r--r-- | sql/item_timefunc.cc | 91 | ||||
-rw-r--r-- | sql/mysql_priv.h | 3 | ||||
-rw-r--r-- | sql/sql_acl.cc | 211 | ||||
-rw-r--r-- | sql/structs.h | 3 |
9 files changed, 214 insertions, 149 deletions
diff --git a/mysql-test/mysql-test-run.sh b/mysql-test/mysql-test-run.sh index 9fa5f72a2e2..ccbd8586967 100644 --- a/mysql-test/mysql-test-run.sh +++ b/mysql-test/mysql-test-run.sh @@ -587,7 +587,7 @@ show_failed_diff () $DIFF -c $result_file $reject_file echo "-------------------------------------------------------" echo "Please follow the instructions outlined at" - echo "http://www.mysql.com/doc/R/e/Reporting_mysqltest_bugs.html" + echo "http://www.mysql.com/doc/en/Reporting_mysqltest_bugs.html" echo "to find the reason to this problem and how to report this." fi } diff --git a/mysql-test/r/func_time.result b/mysql-test/r/func_time.result index 4715227425e..877ca0e2d51 100644 --- a/mysql-test/r/func_time.result +++ b/mysql-test/r/func_time.result @@ -352,6 +352,36 @@ extract(SECOND FROM "1999-01-02 10:11:12") select extract(MONTH FROM "2001-02-00"); extract(MONTH FROM "2001-02-00") 2 +SELECT "1900-01-01 00:00:00" + INTERVAL 2147483648 SECOND; +"1900-01-01 00:00:00" + INTERVAL 2147483648 SECOND +1968-01-20 03:14:08 +SELECT "1900-01-01 00:00:00" + INTERVAL "1:2147483647" MINUTE_SECOND; +"1900-01-01 00:00:00" + INTERVAL "1:2147483647" MINUTE_SECOND +1968-01-20 03:15:07 +SELECT "1900-01-01 00:00:00" + INTERVAL "100000000:214748364700" MINUTE_SECOND; +"1900-01-01 00:00:00" + INTERVAL "100000000:214748364700" MINUTE_SECOND +8895-03-27 22:11:40 +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<37 SECOND; +"1900-01-01 00:00:00" + INTERVAL 1<<37 SECOND +6255-04-08 15:04:32 +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<31 MINUTE; +"1900-01-01 00:00:00" + INTERVAL 1<<31 MINUTE +5983-01-24 02:08:00 +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<20 HOUR; +"1900-01-01 00:00:00" + INTERVAL 1<<20 HOUR +2019-08-15 16:00:00 +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<38 SECOND; +"1900-01-01 00:00:00" + INTERVAL 1<<38 SECOND +NULL +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<33 MINUTE; +"1900-01-01 00:00:00" + INTERVAL 1<<33 MINUTE +NULL +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<30 HOUR; +"1900-01-01 00:00:00" + INTERVAL 1<<30 HOUR +NULL +SELECT "1900-01-01 00:00:00" + INTERVAL "1000000000:214748364700" MINUTE_SECOND; +"1900-01-01 00:00:00" + INTERVAL "1000000000:214748364700" MINUTE_SECOND +NULL create table t1 (ctime varchar(20)); insert into t1 values ('2001-01-12 12:23:40'); select ctime, hour(ctime) from t1; diff --git a/mysql-test/t/func_time.test b/mysql-test/t/func_time.test index 99824ab121d..fffda12c14e 100644 --- a/mysql-test/t/func_time.test +++ b/mysql-test/t/func_time.test @@ -136,10 +136,27 @@ select extract(MINUTE_SECOND FROM "10:11:12"); select extract(SECOND FROM "1999-01-02 10:11:12"); select extract(MONTH FROM "2001-02-00"); +# +# Test big intervals (Bug #3498) +# +SELECT "1900-01-01 00:00:00" + INTERVAL 2147483648 SECOND; +SELECT "1900-01-01 00:00:00" + INTERVAL "1:2147483647" MINUTE_SECOND; +SELECT "1900-01-01 00:00:00" + INTERVAL "100000000:214748364700" MINUTE_SECOND;SELECT "1900-01-01 00:00:00" + INTERVAL 1<<37 SECOND; +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<31 MINUTE; +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<20 HOUR; + +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<38 SECOND; +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<33 MINUTE; +SELECT "1900-01-01 00:00:00" + INTERVAL 1<<30 HOUR; +SELECT "1900-01-01 00:00:00" + INTERVAL "1000000000:214748364700" MINUTE_SECOND; + +# +# Bug #614 (multiple extracts in where) +# + create table t1 (ctime varchar(20)); insert into t1 values ('2001-01-12 12:23:40'); select ctime, hour(ctime) from t1; -# test bug 614 (multiple extracts in where) select ctime from t1 where extract(MONTH FROM ctime) = 1 AND extract(YEAR FROM ctime) = 2001; drop table t1; diff --git a/scripts/mysqld_safe.sh b/scripts/mysqld_safe.sh index 0f415ccd5f0..779438e75c3 100644 --- a/scripts/mysqld_safe.sh +++ b/scripts/mysqld_safe.sh @@ -162,6 +162,8 @@ then echo "Please do a cd to the mysql installation directory and restart" echo "this script from there as follows:" echo "./bin/mysqld_safe". + echo "See http://dev.mysql.com/doc/mysql/en/mysqld_safe.html for more" + echo "information" exit 1 fi diff --git a/sql/field.cc b/sql/field.cc index ac3ebb4bfc7..4e9718ca458 100644 --- a/sql/field.cc +++ b/sql/field.cc @@ -2668,7 +2668,7 @@ String *Field_timestamp::val_str(String *val_buffer, time_t time_arg; struct tm *l_time; struct tm tm_tmp; - my_bool new_format= (current_thd->variables.new_mode), + my_bool new_format= (current_thd->variables.new_mode) || field_length == 19, full_year=(field_length == 8 || field_length == 14 || new_format); int real_field_length= new_format ? 19 : field_length; diff --git a/sql/item_timefunc.cc b/sql/item_timefunc.cc index f2b4a041b6c..638bbcf5b3f 100644 --- a/sql/item_timefunc.cc +++ b/sql/item_timefunc.cc @@ -44,8 +44,8 @@ static String day_names[] = { "Monday", "Tuesday", "Wednesday", ** DAY_TO_SECOND as "D MM:HH:SS", "MM:HH:SS" "HH:SS" or as seconds. */ -bool get_interval_info(const char *str,uint length,uint count, - long *values) +static bool get_interval_info(const char *str,uint length,uint count, + ulonglong *values) { const char *end=str+length; uint i; @@ -54,9 +54,9 @@ bool get_interval_info(const char *str,uint length,uint count, for (i=0 ; i < count ; i++) { - long value; + longlong value; for (value=0; str != end && isdigit(*str) ; str++) - value=value*10L + (long) (*str - '0'); + value=value*10LL + (long) (*str - '0'); values[i]= value; while (str != end && !isdigit(*str)) str++; @@ -65,8 +65,8 @@ bool get_interval_info(const char *str,uint length,uint count, i++; /* Change values[0...i-1] -> values[0...count-1] */ bmove_upp((char*) (values+count), (char*) (values+i), - sizeof(long)*i); - bzero((char*) values, sizeof(long)*(count-i)); + sizeof(*values)*i); + bzero((char*) values, sizeof(*values)*(count-i)); break; } } @@ -302,7 +302,8 @@ longlong Item_func_time_to_sec::val_int() static bool get_interval_value(Item *args,interval_type int_type, String *str_value, INTERVAL *t) { - long array[4],value; + ulonglong array[4]; + longlong value; const char *str; uint32 length; LINT_INIT(value); LINT_INIT(str); LINT_INIT(length); @@ -310,7 +311,7 @@ static bool get_interval_value(Item *args,interval_type int_type, bzero((char*) t,sizeof(*t)); if ((int) int_type <= INTERVAL_SECOND) { - value=(long) args->val_int(); + value= args->val_int(); if (args->null_value) return 1; if (value < 0) @@ -340,68 +341,68 @@ static bool get_interval_value(Item *args,interval_type int_type, switch (int_type) { case INTERVAL_YEAR: - t->year=value; + t->year= (ulong) value; break; case INTERVAL_MONTH: - t->month=value; + t->month= (ulong) value; break; case INTERVAL_DAY: - t->day=value; + t->day= (ulong) value; break; case INTERVAL_HOUR: - t->hour=value; + t->hour= (ulong) value; break; case INTERVAL_MINUTE: - t->minute=value; + t->minute= value; break; case INTERVAL_SECOND: - t->second=value; + t->second= value; break; case INTERVAL_YEAR_MONTH: // Allow YEAR-MONTH YYYYYMM if (get_interval_info(str,length,2,array)) return (1); - t->year=array[0]; - t->month=array[1]; + t->year= (ulong) array[0]; + t->month= (ulong) array[1]; break; case INTERVAL_DAY_HOUR: if (get_interval_info(str,length,2,array)) return (1); - t->day=array[0]; - t->hour=array[1]; + t->day= (ulong) array[0]; + t->hour= (ulong) array[1]; break; case INTERVAL_DAY_MINUTE: if (get_interval_info(str,length,3,array)) return (1); - t->day=array[0]; - t->hour=array[1]; - t->minute=array[2]; + t->day= (ulong) array[0]; + t->hour= (ulong) array[1]; + t->minute= array[2]; break; case INTERVAL_DAY_SECOND: if (get_interval_info(str,length,4,array)) return (1); - t->day=array[0]; - t->hour=array[1]; - t->minute=array[2]; - t->second=array[3]; + t->day= (ulong) array[0]; + t->hour= (ulong) array[1]; + t->minute= array[2]; + t->second= array[3]; break; case INTERVAL_HOUR_MINUTE: if (get_interval_info(str,length,2,array)) return (1); - t->hour=array[0]; - t->minute=array[1]; + t->hour= (ulong) array[0]; + t->minute= array[1]; break; case INTERVAL_HOUR_SECOND: if (get_interval_info(str,length,3,array)) return (1); - t->hour=array[0]; - t->minute=array[1]; - t->second=array[2]; + t->hour= (ulong) array[0]; + t->minute= array[1]; + t->second= array[2]; break; case INTERVAL_MINUTE_SECOND: if (get_interval_info(str,length,2,array)) return (1); - t->minute=array[0]; - t->second=array[1]; + t->minute= array[0]; + t->second= array[1]; break; } return 0; @@ -999,37 +1000,39 @@ bool Item_date_add_interval::get_date(TIME *ltime, bool fuzzy_date) case INTERVAL_DAY_SECOND: case INTERVAL_DAY_MINUTE: case INTERVAL_DAY_HOUR: - long sec,days,daynr; + longlong sec, days, daynr; ltime->time_type=TIMESTAMP_FULL; // Return full date sec=((ltime->day-1)*3600*24L+ltime->hour*3600+ltime->minute*60+ ltime->second + - sign*(interval.day*3600*24L + - interval.hour*3600+interval.minute*60+interval.second)); - days=sec/(3600*24L); sec=sec-days*3600*24L; + sign*(longlong) (interval.day*3600*24L + + interval.hour*LL(3600)+interval.minute*LL(60)+ + interval.second)); + days= sec/(3600*LL(24)); + sec-= days*3600*LL(24); if (sec < 0) { days--; - sec+=3600*24L; + sec+=3600*LL(24); } ltime->second=sec % 60; ltime->minute=sec/60 % 60; ltime->hour=sec/3600; daynr= calc_daynr(ltime->year,ltime->month,1) + days; - get_date_from_daynr(daynr,<ime->year,<ime->month,<ime->day); - if (daynr < 0 || daynr >= 3652424) // Day number from year 0 to 9999-12-31 + if ((ulonglong) daynr >= 3652424) // Day number from year 0 to 9999-12-31 goto null_date; + get_date_from_daynr((long) daynr,<ime->year,<ime->month,<ime->day); break; case INTERVAL_DAY: period= calc_daynr(ltime->year,ltime->month,ltime->day) + - sign*interval.day; + sign* (long) interval.day; if (period < 0 || period >= 3652424) // Daynumber from year 0 to 9999-12-31 goto null_date; get_date_from_daynr((long) period,<ime->year,<ime->month,<ime->day); break; case INTERVAL_YEAR: - ltime->year += sign*interval.year; - if ((int) ltime->year < 0 || ltime->year >= 10000L) + ltime->year += sign*(long) interval.year; + if ((long) ltime->year < 0 || ltime->year >= 10000L) goto null_date; if (ltime->month == 2 && ltime->day == 29 && calc_days_in_year(ltime->year) != 366) @@ -1037,8 +1040,8 @@ bool Item_date_add_interval::get_date(TIME *ltime, bool fuzzy_date) break; case INTERVAL_YEAR_MONTH: case INTERVAL_MONTH: - period= (ltime->year*12 + sign*interval.year*12 + - ltime->month-1 + sign*interval.month); + period= (ltime->year*12 + sign*(long) interval.year*12 + + ltime->month-1 + sign*(long) interval.month); if (period < 0 || period >= 120000L) goto null_date; ltime->year= (uint) (period / 12); diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index c21a2f6f31d..d4fe5968eff 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -847,8 +847,7 @@ void reset_host_errors(struct in_addr *in); bool hostname_cache_init(); void hostname_cache_free(); void hostname_cache_refresh(void); -bool get_interval_info(const char *str,uint length,uint count, - long *values); + /* sql_cache.cc */ extern bool sql_cache_init(); extern void sql_cache_free(); diff --git a/sql/sql_acl.cc b/sql/sql_acl.cc index 596619b3955..9385c4aa7f5 100644 --- a/sql/sql_acl.cc +++ b/sql/sql_acl.cc @@ -740,12 +740,12 @@ static void acl_insert_user(const char *user, const char *host, { ACL_USER acl_user; acl_user.user=*user ? strdup_root(&mem,user) : 0; - update_hostname(&acl_user.host,strdup_root(&mem,host)); + update_hostname(&acl_user.host, *host ? strdup_root(&mem,host): 0); acl_user.password=0; acl_user.access=privileges; acl_user.user_resource = *mqh; acl_user.sort=get_sort(2,acl_user.host.hostname,acl_user.user); - acl_user.hostname_length=(uint) strlen(acl_user.host.hostname); + acl_user.hostname_length=(uint) strlen(host); acl_user.ssl_type= (ssl_type != SSL_TYPE_NOT_SPECIFIED ? ssl_type : SSL_TYPE_NONE); acl_user.ssl_cipher= ssl_cipher ? strdup_root(&mem,ssl_cipher) : 0; @@ -1611,107 +1611,121 @@ static byte* get_key_column(GRANT_COLUMN *buff,uint *length, class GRANT_TABLE :public Sql_alloc { public: - char *host,*db,*user,*tname, *hash_key; + char *host,*db,*user,*tname, *hash_key, *orig_host; ulong privs, cols; ulong sort; uint key_length; HASH hash_columns; - GRANT_TABLE (const char *h, const char *d,const char *u, const char *t, - ulong p, ulong c) - : privs(p), cols(c) - { - host = strdup_root(&memex,h); - db = strdup_root(&memex,d); - user = strdup_root(&memex,u); - sort= get_sort(3,host,db,user); - tname= strdup_root(&memex,t); - if (lower_case_table_names) - { - casedn_str(db); - casedn_str(tname); - } - key_length =(uint) strlen(d)+(uint) strlen(u)+(uint) strlen(t)+3; - hash_key = (char*) alloc_root(&memex,key_length); - strmov(strmov(strmov(hash_key,user)+1,db)+1,tname); - (void) hash_init(&hash_columns,0,0,0, (hash_get_key) get_key_column,0, - HASH_CASE_INSENSITIVE); - } + GRANT_TABLE(const char *h, const char *d,const char *u, const char *t, + ulong p, ulong c); + GRANT_TABLE(TABLE *form, TABLE *col_privs); + bool ok() { return privs != 0 || cols != 0; } +}; - GRANT_TABLE (TABLE *form, TABLE *col_privs) + +GRANT_TABLE::GRANT_TABLE(const char *h, const char *d,const char *u, + const char *t, ulong p, ulong c) + :privs(p), cols(c) +{ + /* Host given by user */ + orig_host= strdup_root(&memex,h); + /* Convert empty hostname to '%' for easy comparision */ + host= orig_host[0] ? orig_host : (char*) "%"; + db = strdup_root(&memex,d); + user = strdup_root(&memex,u); + sort= get_sort(3,host,db,user); + tname= strdup_root(&memex,t); + if (lower_case_table_names) { - byte key[MAX_KEY_LENGTH]; + casedn_str(db); + casedn_str(tname); + } + key_length =(uint) strlen(d)+(uint) strlen(u)+(uint) strlen(t)+3; + hash_key = (char*) alloc_root(&memex,key_length); + strmov(strmov(strmov(hash_key,user)+1,db)+1,tname); + (void) hash_init(&hash_columns,0,0,0, (hash_get_key) get_key_column,0, + HASH_CASE_INSENSITIVE); +} + + +GRANT_TABLE::GRANT_TABLE(TABLE *form, TABLE *col_privs) +{ + byte key[MAX_KEY_LENGTH]; - host = get_field(&memex,form,0); - db = get_field(&memex,form,1); - user = get_field(&memex,form,2); - if (!user) - user=(char*) ""; - sort= get_sort(3,host,db,user); - tname = get_field(&memex,form,3); - if (!host || !db || !tname) + orig_host= host= get_field(&memex,form,0); + db = get_field(&memex,form,1); + user = get_field(&memex,form,2); + if (!user) + user= (char*) ""; + if (!orig_host) + { + orig_host= (char*) ""; + host= (char*) "%"; + } + sort= get_sort(3,orig_host,db,user); + tname = get_field(&memex,form,3); + if (!db || !tname) + { + /* Wrong table row; Ignore it */ + privs = cols = 0; /* purecov: inspected */ + return; /* purecov: inspected */ + } + if (lower_case_table_names) + { + casedn_str(db); + casedn_str(tname); + } + key_length = ((uint) strlen(db) + (uint) strlen(user) + + (uint) strlen(tname) + 3); + hash_key = (char*) alloc_root(&memex,key_length); + strmov(strmov(strmov(hash_key,user)+1,db)+1,tname); + privs = (ulong) form->field[6]->val_int(); + cols = (ulong) form->field[7]->val_int(); + privs = fix_rights_for_table(privs); + cols = fix_rights_for_column(cols); + + (void) hash_init(&hash_columns,0,0,0, (hash_get_key) get_key_column,0, + HASH_CASE_INSENSITIVE); + if (cols) + { + int key_len; + col_privs->field[0]->store(orig_host,(uint) strlen(orig_host)); + col_privs->field[1]->store(db,(uint) strlen(db)); + col_privs->field[2]->store(user,(uint) strlen(user)); + col_privs->field[3]->store(tname,(uint) strlen(tname)); + key_len=(col_privs->field[0]->pack_length()+ + col_privs->field[1]->pack_length()+ + col_privs->field[2]->pack_length()+ + col_privs->field[3]->pack_length()); + key_copy(key,col_privs,0,key_len); + col_privs->field[4]->store("",0); + col_privs->file->index_init(0); + if (col_privs->file->index_read(col_privs->record[0], + (byte*) col_privs->field[0]->ptr, + key_len, HA_READ_KEY_EXACT)) { - /* Wrong table row; Ignore it */ - privs = cols = 0; /* purecov: inspected */ - return; /* purecov: inspected */ + cols = 0; /* purecov: deadcode */ + return; } - if (lower_case_table_names) - { - casedn_str(db); - casedn_str(tname); - } - key_length = ((uint) strlen(db) + (uint) strlen(user) + - (uint) strlen(tname) + 3); - hash_key = (char*) alloc_root(&memex,key_length); - strmov(strmov(strmov(hash_key,user)+1,db)+1,tname); - privs = (ulong) form->field[6]->val_int(); - cols = (ulong) form->field[7]->val_int(); - privs = fix_rights_for_table(privs); - cols = fix_rights_for_column(cols); - - (void) hash_init(&hash_columns,0,0,0, (hash_get_key) get_key_column,0, - HASH_CASE_INSENSITIVE); - if (cols) + do { - int key_len; - col_privs->field[0]->store(host,(uint) strlen(host)); - col_privs->field[1]->store(db,(uint) strlen(db)); - col_privs->field[2]->store(user,(uint) strlen(user)); - col_privs->field[3]->store(tname,(uint) strlen(tname)); - key_len=(col_privs->field[0]->pack_length()+ - col_privs->field[1]->pack_length()+ - col_privs->field[2]->pack_length()+ - col_privs->field[3]->pack_length()); - key_copy(key,col_privs,0,key_len); - col_privs->field[4]->store("",0); - col_privs->file->index_init(0); - if (col_privs->file->index_read(col_privs->record[0], - (byte*) col_privs->field[0]->ptr, - key_len, HA_READ_KEY_EXACT)) + String *res,column_name; + GRANT_COLUMN *mem_check; + /* As column name is a string, we don't have to supply a buffer */ + res=col_privs->field[4]->val_str(&column_name,&column_name); + ulong priv= (ulong) col_privs->field[6]->val_int(); + if (!(mem_check = new GRANT_COLUMN(*res, + fix_rights_for_column(priv)))) { - cols = 0; /* purecov: deadcode */ - return; + /* Don't use this entry */ + privs = cols = 0; /* purecov: deadcode */ + return; /* purecov: deadcode */ } - do - { - String *res,column_name; - GRANT_COLUMN *mem_check; - /* As column name is a string, we don't have to supply a buffer */ - res=col_privs->field[4]->val_str(&column_name,&column_name); - ulong priv= (ulong) col_privs->field[6]->val_int(); - if (!(mem_check = new GRANT_COLUMN(*res, - fix_rights_for_column(priv)))) - { - /* Don't use this entry */ - privs = cols = 0; /* purecov: deadcode */ - return; /* purecov: deadcode */ - } - hash_insert(&hash_columns, (byte *) mem_check); - } while (!col_privs->file->index_next(col_privs->record[0]) && - !key_cmp(col_privs,key,0,key_len)); - } + hash_insert(&hash_columns, (byte *) mem_check); + } while (!col_privs->file->index_next(col_privs->record[0]) && + !key_cmp(col_privs,key,0,key_len)); } - bool ok() { return privs != 0 || cols != 0; } -}; +} static byte* get_grant_table(GRANT_TABLE *buff,uint *length, @@ -2286,8 +2300,8 @@ int mysql_table_grant(THD *thd, TABLE_LIST *table_list, } -int mysql_grant (THD *thd, const char *db, List <LEX_USER> &list, - ulong rights, bool revoke_grant) +int mysql_grant(THD *thd, const char *db, List <LEX_USER> &list, + ulong rights, bool revoke_grant) { List_iterator <LEX_USER> str_list (list); LEX_USER *Str; @@ -2538,7 +2552,7 @@ void grant_reload(THD *thd) /**************************************************************************** - Check grants + Check table level grants All errors are written directly to the client if no_errors is given ! ****************************************************************************/ @@ -2898,7 +2912,7 @@ int mysql_show_grants(THD *thd,LEX_USER *lex_user) if (!(user=acl_user->user)) user=""; if (!(host=acl_user->host.hostname)) - host="%"; + host=""; if (!strcmp(lex_user->user.str,user) && !my_strcasecmp(lex_user->host.str,host)) break; @@ -3079,19 +3093,17 @@ int mysql_show_grants(THD *thd,LEX_USER *lex_user) } } - /* Add column access */ + /* Add table & column access */ for (index=0 ; index < hash_tables.records ; index++) { const char *user,*host; GRANT_TABLE *grant_table= (GRANT_TABLE*) hash_element(&hash_tables,index); if (!(user=grant_table->user)) - user=""; - if (!(host=grant_table->host)) - host=""; + user= ""; if (!strcmp(lex_user->user.str,user) && - !my_strcasecmp(lex_user->host.str,host)) + !my_strcasecmp(lex_user->host.str, grant_table->orig_host)) { ulong table_access= grant_table->privs; if ((table_access | grant_table->cols) != 0) @@ -3108,6 +3120,7 @@ int mysql_show_grants(THD *thd,LEX_USER *lex_user) global.append("USAGE",5); else { + /* Add specific column access */ int found= 0; ulong j; diff --git a/sql/structs.h b/sql/structs.h index 77fed422d21..156bf7745af 100644 --- a/sql/structs.h +++ b/sql/structs.h @@ -119,7 +119,8 @@ typedef struct st_time { } TIME; typedef struct { - long year,month,day,hour,minute,second,second_part; + ulong year,month,day,hour; + ulonglong minute,second,second_part; bool neg; } INTERVAL; |