summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--Docs/manual.texi71
-rw-r--r--isam/_locking.c2
-rw-r--r--mysql-test/r/rpl000014.result16
-rw-r--r--mysql-test/r/rpl000015.result16
-rw-r--r--mysql-test/r/rpl000016.result12
-rw-r--r--mysql-test/r/rpl_log.result4
-rw-r--r--mysys/mf_iocache.c2
-rw-r--r--mysys/mf_iocache2.c1
-rw-r--r--sql/log.cc42
-rw-r--r--sql/mysqld.cc2
-rw-r--r--sql/slave.cc111
-rw-r--r--sql/slave.h8
-rw-r--r--sql/sql_class.h17
-rw-r--r--sql/sql_repl.cc2
14 files changed, 226 insertions, 80 deletions
diff --git a/Docs/manual.texi b/Docs/manual.texi
index e0c39f49058..2f0ad4f4458 100644
--- a/Docs/manual.texi
+++ b/Docs/manual.texi
@@ -28438,6 +28438,12 @@ will be unsigned! @xref{Cast Functions}.
A very small integer. The signed range is @code{-128} to @code{127}. The
unsigned range is @code{0} to @code{255}.
+@tindex BOOL
+@tindex BIT
+@item BIT
+@itemx BOOL
+These are synonyms for @code{TINYINT(1)}.
+
@tindex SMALLINT
@item SMALLINT[(M)] [UNSIGNED] [ZEROFILL]
@@ -28505,14 +28511,14 @@ integers) you may get unexpected results when the result is larger than
@cindex floating-point number
@tindex FLOAT
@tindex FLOAT(precision)
-@item FLOAT(precision) [ZEROFILL]
+@item FLOAT(precision) [UNSIGNED] [ZEROFILL]
-A floating-point number. Cannot be unsigned. @code{precision} can be
+A floating-point number. @code{precision} can be
@code{<=24} for a single-precision floating-point number and between 25
and 53 for a double-precision floating-point number. These types are like
the @code{FLOAT} and @code{DOUBLE} types described immediately below.
@code{FLOAT(X)} has the same range as the corresponding @code{FLOAT} and
-@code{DOUBLE} types, but the display size and number of decimals is undefined.
+@code{DOUBLE} types, but the display size and number of decimals are undefined.
In MySQL Version 3.23, this is a true floating-point value. In
earlier MySQL versions, @code{FLOAT(precision)} always has 2 decimals.
@@ -28527,38 +28533,40 @@ This syntax is provided for ODBC compatibility.
@tindex FLOAT
@tindex FLOAT(M,D)
-@item FLOAT[(M,D)] [ZEROFILL]
+@item FLOAT[(M,D)] [UNSIGNED] [ZEROFILL]
-A small (single-precision) floating-point number. Cannot be unsigned.
-Allowable values are @code{@w{-3.402823466E+38}} to
-@code{@w{-1.175494351E-38}}, @code{0}, and @code{@w{1.175494351E-38}} to
-@code{3.402823466E+38}. The @code{M} is the display width and @code{D} is the
-number of decimals. @code{FLOAT} without arguments or @code{FLOAT(X)} where
-@code{X} <= 24 stands for a single-precision floating-point number.
+A small (single-precision) floating-point number. Allowable values are
+@code{@w{-3.402823466E+38}} to @code{@w{-1.175494351E-38}}, @code{0},
+and @code{@w{1.175494351E-38}} to @code{3.402823466E+38}. If
+@code{UNSIGNED} is specified, negative values are disallowed. The @code{M}
+is the display width and @code{D} is the number of decimals. @code{FLOAT}
+without arguments or @code{FLOAT(X)} where @code{X} <= 24 stands for a
+single-precision floating-point number.
@tindex DOUBLE
@tindex FLOAT(precision)
-@item DOUBLE[(M,D)] [ZEROFILL]
+@item DOUBLE[(M,D)] [UNSIGNED] [ZEROFILL]
-A normal-size (double-precision) floating-point number. Cannot be
-unsigned. Allowable values are @code{@w{-1.7976931348623157E+308}} to
+A normal-size (double-precision) floating-point number.
+Allowable values are @code{@w{-1.7976931348623157E+308}} to
@code{@w{-2.2250738585072014E-308}}, @code{0}, and
-@code{2.2250738585072014E-308} to @code{1.7976931348623157E+308}. The
+@code{2.2250738585072014E-308} to @code{1.7976931348623157E+308}. If
+@code{UNSIGNED} is specified, negative values are disallowed. The
@code{M} is the display width and @code{D} is the number of decimals.
@code{DOUBLE} without arguments or @code{FLOAT(X)} where 25 <= @code{X}
<= 53 stands for a double-precision floating-point number.
@tindex DOUBLE PRECISION
@tindex REAL
-@item DOUBLE PRECISION[(M,D)] [ZEROFILL]
-@itemx REAL[(M,D)] [ZEROFILL]
+@item DOUBLE PRECISION[(M,D)] [UNSIGNED] [ZEROFILL]
+@itemx REAL[(M,D)] [UNSIGNED] [ZEROFILL]
These are synonyms for @code{DOUBLE}.
@tindex DECIMAL
-@item DECIMAL[(M[,D])] [ZEROFILL]
+@item DECIMAL[(M[,D])] [UNSIGNED] [ZEROFILL]
-An unpacked floating-point number. Cannot be unsigned. Behaves like a
+An unpacked floating-point number. Behaves like a
@code{CHAR} column: ``unpacked'' means the number is stored as a string,
using one character for each digit of the value. The decimal point and,
for negative numbers, the @samp{-} sign, are not counted in @code{M} (but
@@ -28566,7 +28574,7 @@ space for these is reserved). If @code{D} is 0, values will have no decimal
point or fractional part. The maximum range of @code{DECIMAL} values is
the same as for @code{DOUBLE}, but the actual range for a given
@code{DECIMAL} column may be constrained by the choice of @code{M} and
-@code{D}.
+@code{D}. If @code{UNSIGNED} is specified, negative values are disallowed.
If @code{D} is omitted, the default is 0. If @code{M} is omitted, the
default is 10.
@@ -28576,8 +28584,8 @@ needed for the sign and the decimal point.
@tindex DEC
@tindex NUMERIC
-@item DEC[(M[,D])] [ZEROFILL]
-@itemx NUMERIC[(M[,D])] [ZEROFILL]
+@item DEC[(M[,D])] [UNSIGNED] [ZEROFILL]
+@itemx NUMERIC[(M[,D])] [UNSIGNED] [ZEROFILL]
These are synonyms for @code{DECIMAL}.
@@ -28667,12 +28675,8 @@ column that only can take 2 values: A @code{CHAR(0)}, that is not defined
as @code{NOT NULL}, will occupy only one bit and can take only 2 values:
@code{NULL} or @code{""}. @xref{CHAR, , @code{CHAR}}.
-@tindex BOOL
-@tindex BIT
-@item BIT
-@itemx BOOL
-@itemx CHAR
-These three are synonyms for @code{CHAR(1)}.
+@item CHAR
+This is a synonym for @code{CHAR(1)}.
@tindex CHARACTER VARYING
@tindex CHAR VARYING
@@ -28809,10 +28813,10 @@ MySQL stores the value representing the corresponding end
point of that range.
As an extension to the ANSI/ISO SQL92 standard, MySQL also
-supports the integral types @code{TINYINT}, @code{MEDIUMINT}, and
+supports the integer types @code{TINYINT}, @code{MEDIUMINT}, and
@code{BIGINT} as listed in the tables above. Another extension is
supported by MySQL for optionally specifying the display width
-of an integral value in parentheses following the base keyword for the
+of an integer value in parentheses following the base keyword for the
type (for example, @code{INT(4)}). This optional width specification is
used to left-pad the display of values whose width is less than the
width specified for the column, but does not constrain the range of
@@ -28827,11 +28831,16 @@ problems when MySQL generates temporary tables for some
complicated joins, as in these cases MySQL trusts that the
data did fit into the original column width.
-All integral types can have an optional (non-standard) attribute
+All integer types can have an optional (non-standard) attribute
@code{UNSIGNED}. Unsigned values can be used when you want to allow
only positive numbers in a column and you need a little bigger numeric
range for the column.
+As of MySQL 4.0.2, floating-point types also can be @code{UNSIGNED}.
+As with integer types, this attribute prevents negative values from
+being stored in the column. Unlike the integer types, the upper range
+of column values remains the same.
+
The @code{FLOAT} type is used to represent approximate numeric data
types. The ANSI/ISO SQL92 standard allows an optional specification of
the precision (but not the range of the exponent) in bits following the
@@ -54046,7 +54055,7 @@ ODBC or ANSI SQL92 syntax.
Fixed syntax of @code{ALTER TABLE tbl_name ALTER COLUMN col_name SET DEFAULT
NULL}.
@item
-Added @code{CHAR} and @code{BIT} as synonyms for @code{CHAR(1)}.
+Added @code{CHAR} (with no length specifier) as a synonym for @code{CHAR(1)}.
@item
Fixed core dump when updating as a user who has only @strong{select} privilege.
@item
diff --git a/isam/_locking.c b/isam/_locking.c
index cccedbd16c8..be9741a4237 100644
--- a/isam/_locking.c
+++ b/isam/_locking.c
@@ -306,8 +306,8 @@ int _nisam_writeinfo(register N_INFO *info, uint flags)
MYF(MY_WME | MY_SEEK_NOT_DONE)) && !error)
DBUG_RETURN(1);
}
- }
#endif
+ }
my_errno=olderror;
}
else if (flags)
diff --git a/mysql-test/r/rpl000014.result b/mysql-test/r/rpl000014.result
index 7a691119e5c..ded11a9bb95 100644
--- a/mysql-test/r/rpl000014.result
+++ b/mysql-test/r/rpl000014.result
@@ -7,22 +7,22 @@ show master status;
File Position Binlog_do_db Binlog_ignore_db
master-bin.001 79
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 1 master-bin.001 79 slave-relay-bin.002 120 master-bin.001 Yes Yes 0 0 79
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 1 master-bin.001 79 slave-relay-bin.002 120 master-bin.001 Yes Yes 0 0 79 124
change master to master_log_pos=73;
slave stop;
change master to master_log_pos=73;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 1 master-bin.001 73 slave-relay-bin.001 4 master-bin.001 No No 0 0 73
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 1 master-bin.001 73 slave-relay-bin.001 4 master-bin.001 No No 0 0 73 4
slave start;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 1 master-bin.001 73 slave-relay-bin.001 4 master-bin.001 Yes Yes 0 0 73
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 1 master-bin.001 73 slave-relay-bin.001 4 master-bin.001 Yes Yes 0 0 73 4
change master to master_log_pos=173;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 1 master-bin.001 173 slave-relay-bin.001 4 master-bin.001 Yes Yes 0 0 173
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 1 master-bin.001 173 slave-relay-bin.001 4 master-bin.001 Yes Yes 0 0 173 4
show master status;
File Position Binlog_do_db Binlog_ignore_db
master-bin.001 79
diff --git a/mysql-test/r/rpl000015.result b/mysql-test/r/rpl000015.result
index 1546e5eb48d..a35004298e0 100644
--- a/mysql-test/r/rpl000015.result
+++ b/mysql-test/r/rpl000015.result
@@ -4,21 +4,21 @@ File Position Binlog_do_db Binlog_ignore_db
master-bin.001 79
reset slave;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
- 0 0 0 0 No No 0 0 0
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+ 0 0 0 0 No No 0 0 0 0
change master to master_host='127.0.0.1';
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 test MASTER_PORT 7 4 slave-relay-bin.001 4 No No 0 0 0
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 test MASTER_PORT 7 4 slave-relay-bin.001 4 No No 0 0 0 4
change master to master_host='127.0.0.1',master_user='root',
master_password='',master_port=MASTER_PORT;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 7 4 slave-relay-bin.001 4 No No 0 0 0
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 7 4 slave-relay-bin.001 4 No No 0 0 0 4
slave start;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 7 master-bin.001 79 slave-relay-bin.001 120 master-bin.001 Yes Yes 0 0 79
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 7 master-bin.001 79 slave-relay-bin.001 120 master-bin.001 Yes Yes 0 0 79 120
drop table if exists t1;
create table t1 (n int);
insert into t1 values (10),(45),(90);
diff --git a/mysql-test/r/rpl000016.result b/mysql-test/r/rpl000016.result
index 6a91309c29c..9d6ba071200 100644
--- a/mysql-test/r/rpl000016.result
+++ b/mysql-test/r/rpl000016.result
@@ -14,8 +14,8 @@ drop table if exists t1;
create table t1 (s text);
insert into t1 values('Could not break slave'),('Tried hard');
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 60 master-bin.001 234 slave-relay-bin.001 275 master-bin.001 Yes Yes 0 0 234
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 60 master-bin.001 234 slave-relay-bin.001 275 master-bin.001 Yes Yes 0 0 234 275
select * from t1;
s
Could not break slave
@@ -41,8 +41,8 @@ Log_name
master-bin.003
insert into t2 values (65);
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 60 master-bin.003 155 slave-relay-bin.001 755 master-bin.003 Yes Yes 0 0 155
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 60 master-bin.003 155 slave-relay-bin.001 755 master-bin.003 Yes Yes 0 0 155 755
select * from t2;
m
34
@@ -64,8 +64,8 @@ master-bin.006 445
slave stop;
slave start;
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 60 master-bin.006 445 slave-relay-bin.004 1229 master-bin.006 Yes Yes 0 0 445
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 60 master-bin.006 445 slave-relay-bin.004 1229 master-bin.006 Yes Yes 0 0 445 1229
lock tables t3 read;
select count(*) from t3 where n >= 4;
count(*)
diff --git a/mysql-test/r/rpl_log.result b/mysql-test/r/rpl_log.result
index e91d17426c8..70fbe32845d 100644
--- a/mysql-test/r/rpl_log.result
+++ b/mysql-test/r/rpl_log.result
@@ -74,8 +74,8 @@ slave-bin.002 57 Query 1 4 use test; create table t1 (n int)
slave-bin.002 115 Query 1 62 use test; insert into t1 values (1)
slave-bin.002 175 Query 1 122 use test; drop table t1
show slave status;
-Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos
-127.0.0.1 root MASTER_PORT 1 master-bin.002 170 slave-relay-bin.002 916 master-bin.002 Yes Yes 0 0 170
+Master_Host Master_User Master_Port Connect_retry Master_Log_File Read_Master_Log_Pos Relay_Log_File Relay_Log_Pos Relay_Master_Log_File Slave_IO_Running Slave_SQL_Running Replicate_do_db Replicate_ignore_db Last_errno Last_error Skip_counter Exec_master_log_pos Relay_log_space
+127.0.0.1 root MASTER_PORT 1 master-bin.002 170 slave-relay-bin.002 916 master-bin.002 Yes Yes 0 0 170 920
show new master for slave with master_log_file='master-bin.001' and
master_log_pos=4 and master_server_id=1;
Log_name Log_pos
diff --git a/mysys/mf_iocache.c b/mysys/mf_iocache.c
index 872757f77c5..a0247003a81 100644
--- a/mysys/mf_iocache.c
+++ b/mysys/mf_iocache.c
@@ -906,7 +906,7 @@ int _flush_io_cache(IO_CACHE *info, int need_append_buffer_lock)
uint length;
my_bool append_cache;
my_off_t pos_in_file;
- DBUG_ENTER("flush_io_cache");
+ DBUG_ENTER("_flush_io_cache");
if (!(append_cache = (info->type == SEQ_READ_APPEND)))
need_append_buffer_lock=0;
diff --git a/mysys/mf_iocache2.c b/mysys/mf_iocache2.c
index 127bf20e8fe..c56022e93e8 100644
--- a/mysys/mf_iocache2.c
+++ b/mysys/mf_iocache2.c
@@ -117,6 +117,7 @@ void my_b_seek(IO_CACHE *info,my_off_t pos)
}
info->pos_in_file=pos;
info->seek_not_done=1;
+ DBUG_VOID_RETURN;
}
diff --git a/sql/log.cc b/sql/log.cc
index dc6b1d35cef..c393d2eb413 100644
--- a/sql/log.cc
+++ b/sql/log.cc
@@ -83,7 +83,7 @@ static int find_uniq_filename(char *name)
MYSQL_LOG::MYSQL_LOG(): last_time(0), query_start(0),index_file(-1),
name(0), log_type(LOG_CLOSED),write_error(0),
inited(0), file_id(1),no_rotate(0),
- need_start_event(1)
+ need_start_event(1),bytes_written(0)
{
/*
We don't want to intialize LOCK_Log here as the thread system may
@@ -99,6 +99,7 @@ MYSQL_LOG::~MYSQL_LOG()
{
(void) pthread_mutex_destroy(&LOCK_log);
(void) pthread_mutex_destroy(&LOCK_index);
+ (void) pthread_cond_destroy(&update_cond);
}
}
@@ -233,18 +234,14 @@ void MYSQL_LOG::open(const char *log_name, enum_log_type log_type_arg,
}
else if (log_type == LOG_BIN)
{
- bool error;
- /*
- Explanation of the boolean black magic:
- if we are supposed to write magic number try write
- clean
-up if failed
- then if index_file has not been previously opened, try to open it
- clean up if failed
- */
- if ((do_magic && my_b_write(&log_file, (byte*) BINLOG_MAGIC, 4)) ||
+ bool error;
+ if (do_magic)
+ {
+ if (my_b_write(&log_file, (byte*) BINLOG_MAGIC, 4) ||
open_index(O_APPEND | O_RDWR | O_CREAT))
- goto err;
+ goto err;
+ bytes_written += 4;
+ }
if (need_start_event && !no_auto_events)
{
@@ -462,12 +459,30 @@ err:
my_delete(fname, MYF(0)); // do not report error if the file is not there
else
{
+ MY_STAT s;
my_close(index_file, MYF(MY_WME));
+ if (!my_stat(rli->relay_log_name,&s,MYF(0)))
+ {
+ sql_print_error("The first log %s failed to stat during purge",
+ rli->relay_log_name);
+ error=1;
+ goto err;
+ }
if (my_rename(fname,index_file_name,MYF(MY_WME)) ||
(index_file=my_open(index_file_name,O_BINARY|O_RDWR|O_APPEND,
MYF(MY_WME)))<0 ||
my_delete(rli->relay_log_name, MYF(MY_WME)))
error=1;
+
+ pthread_mutex_lock(&rli->log_space_lock);
+ rli->log_space_total -= s.st_size;
+ fprintf(stderr,"purge_first_log: %ld\n", rli->log_space_total);
+ pthread_mutex_unlock(&rli->log_space_lock);
+ // ok to broadcast after the critical region as there is no risk of
+ // the mutex being destroyed by this thread later - this helps save
+ // context switches
+ pthread_cond_broadcast(&rli->log_space_cond);
+
if ((error=find_first_log(&rli->linfo,"",0/*no mutex*/)))
{
char buff[22];
@@ -695,6 +710,7 @@ void MYSQL_LOG::new_file(bool inside_mutex)
if (thd && thd->slave_thread)
r.flags |= LOG_EVENT_FORCED_ROTATE_F;
r.write(&log_file);
+ bytes_written += r.get_event_len();
}
// update needs to be signaled even if there is no rotate event
// log rotation should give the waiting thread a signal to
@@ -728,6 +744,7 @@ bool MYSQL_LOG::append(Log_event* ev)
error=1;
goto err;
}
+ bytes_written += ev->get_event_len();
if ((uint)my_b_append_tell(&log_file) > max_binlog_size)
{
new_file(1);
@@ -754,6 +771,7 @@ bool MYSQL_LOG::appendv(const char* buf, uint len,...)
error = 1;
break;
}
+ bytes_written += len;
} while ((buf=va_arg(args,const char*)) && (len=va_arg(args,uint)));
if ((uint) my_b_append_tell(&log_file) > max_binlog_size)
diff --git a/sql/mysqld.cc b/sql/mysqld.cc
index 3ecb59d415a..0dda582da59 100644
--- a/sql/mysqld.cc
+++ b/sql/mysqld.cc
@@ -3042,6 +3042,8 @@ CHANGEABLE_VAR changeable_vars[] = {
128*1024L, IO_SIZE*2+MALLOC_OVERHEAD, ~0L, MALLOC_OVERHEAD, IO_SIZE },
{ "record_rnd_buffer", (long*) &record_rnd_cache_size,
0, IO_SIZE*2+MALLOC_OVERHEAD, ~0L, MALLOC_OVERHEAD, IO_SIZE },
+ { "relay_log_space_limit", (long*) &relay_log_space_limit, 0L, 0L,ULONG_MAX,
+ 0, 1},
{ "slave_net_timeout", (long*) &slave_net_timeout,
SLAVE_NET_TIMEOUT, 1, LONG_TIMEOUT, 0, 1 },
{ "slow_launch_time", (long*) &slow_launch_time,
diff --git a/sql/slave.cc b/sql/slave.cc
index 919cf362238..25b29732000 100644
--- a/sql/slave.cc
+++ b/sql/slave.cc
@@ -42,6 +42,8 @@ bool do_table_inited = 0, ignore_table_inited = 0;
bool wild_do_table_inited = 0, wild_ignore_table_inited = 0;
bool table_rules_on = 0;
static TABLE* save_temporary_tables = 0;
+ulong relay_log_space_limit = 0; /* TODO: fix variables to access ulonglong
+ values and make it ulonglong */
// when slave thread exits, we need to remember the temporary tables so we
// can re-use them on slave start
@@ -60,8 +62,10 @@ static int process_io_rotate(MASTER_INFO* mi, Rotate_log_event* rev);
static int process_io_create_file(MASTER_INFO* mi, Create_file_log_event* cev);
static int queue_old_event(MASTER_INFO* mi, const char* buf,
uint event_len);
+static bool wait_for_relay_log_space(RELAY_LOG_INFO* rli);
static inline bool io_slave_killed(THD* thd,MASTER_INFO* mi);
static inline bool sql_slave_killed(THD* thd,RELAY_LOG_INFO* rli);
+static int count_relay_log_space(RELAY_LOG_INFO* rli);
static int init_slave_thread(THD* thd, SLAVE_THD_TYPE thd_type);
static int safe_connect(THD* thd, MYSQL* mysql, MASTER_INFO* mi);
static int safe_reconnect(THD* thd, MYSQL* mysql, MASTER_INFO* mi);
@@ -264,8 +268,9 @@ void init_slave_skip_errors(char* arg)
// are not running
int purge_relay_logs(RELAY_LOG_INFO* rli, bool just_reset, const char** errmsg)
{
+ DBUG_ENTER("purge_relay_logs");
if (!rli->inited)
- return 0; /* successfully do nothing */
+ DBUG_RETURN(0); /* successfully do nothing */
DBUG_ASSERT(rli->slave_running == 0);
DBUG_ASSERT(rli->mi->slave_running == 0);
int error=0;
@@ -282,14 +287,20 @@ int purge_relay_logs(RELAY_LOG_INFO* rli, bool just_reset, const char** errmsg)
goto err;
}
strnmov(rli->relay_log_name,rli->linfo.log_file_name,
- sizeof(rli->relay_log_name));
+ sizeof(rli->relay_log_name)-1);
+ rli->log_space_total=4; //just first log with magic number and nothing else
rli->relay_log_pos=4;
+ rli->relay_log.reset_bytes_written();
rli->log_pos_current=0;
if (!just_reset)
error = init_relay_log_pos(rli,0,0,0/*do not need data lock*/,errmsg);
-err:
+err:
+#ifndef DBUG_OFF
+ char buf[22];
+#endif
+ DBUG_PRINT("info",("log_space_total=%s",llstr(rli->log_space_total,buf)));
pthread_mutex_unlock(&rli->data_lock);
- return error;
+ DBUG_RETURN(error);
}
int terminate_slave_threads(MASTER_INFO* mi,int thread_mask,bool skip_lock)
@@ -953,8 +964,9 @@ void end_master_info(MASTER_INFO* mi)
int init_relay_log_info(RELAY_LOG_INFO* rli, const char* info_fname)
{
+ DBUG_ENTER("init_relay_log_info");
if (rli->inited)
- return 0;
+ DBUG_RETURN(0);
MY_STAT stat_area;
char fname[FN_REFLEN+128];
int info_fd;
@@ -970,6 +982,8 @@ int init_relay_log_info(RELAY_LOG_INFO* rli, const char* info_fname)
rli->log_pos_current=0;
rli->abort_pos_wait=0;
rli->skip_log_purge=0;
+ rli->log_space_limit = relay_log_space_limit;
+ rli->log_space_total = 0;
// TODO: make this work with multi-master
if (!opt_relay_logname)
{
@@ -1001,7 +1015,7 @@ int init_relay_log_info(RELAY_LOG_INFO* rli, const char* info_fname)
my_close(info_fd, MYF(0));
rli->info_fd=-1;
pthread_mutex_unlock(&rli->data_lock);
- return 1;
+ DBUG_RETURN(1);
}
if (init_relay_log_pos(rli,"",4,0/*no data mutex*/,&msg))
goto err;
@@ -1021,7 +1035,7 @@ int init_relay_log_info(RELAY_LOG_INFO* rli, const char* info_fname)
my_close(info_fd, MYF(0));
rli->info_fd=-1;
pthread_mutex_unlock(&rli->data_lock);
- return 1;
+ DBUG_RETURN(1);
}
rli->info_fd = info_fd;
@@ -1052,8 +1066,13 @@ int init_relay_log_info(RELAY_LOG_INFO* rli, const char* info_fname)
// before flush_relay_log_info
reinit_io_cache(&rli->info_file, WRITE_CACHE,0L,0,1);
error=test(flush_relay_log_info(rli));
+ if (count_relay_log_space(rli))
+ {
+ msg="Error counting relay log space";
+ goto err;
+ }
pthread_mutex_unlock(&rli->data_lock);
- return error;
+ DBUG_RETURN(error);
err:
sql_print_error(msg);
@@ -1061,9 +1080,66 @@ err:
my_close(info_fd, MYF(0));
rli->info_fd=-1;
pthread_mutex_unlock(&rli->data_lock);
- return 1;
+ DBUG_RETURN(1);
}
+static inline int add_relay_log(RELAY_LOG_INFO* rli,LOG_INFO* linfo)
+{
+ MY_STAT s;
+ DBUG_ENTER("add_relay_log");
+ if (!my_stat(linfo->log_file_name,&s,MYF(0)))
+ {
+ sql_print_error("log %s listed in the index, but failed to stat",
+ linfo->log_file_name);
+ DBUG_RETURN(1);
+ }
+ rli->log_space_total += s.st_size;
+#ifndef DBUG_OFF
+ char buf[22];
+#endif
+ DBUG_PRINT("info",("log_space_total: %s", llstr(rli->log_space_total,buf)));
+ DBUG_RETURN(0);
+}
+
+static bool wait_for_relay_log_space(RELAY_LOG_INFO* rli)
+{
+ bool slave_killed;
+ MASTER_INFO* mi = rli->mi;
+ const char* save_proc_info;
+ THD* thd = mi->io_thd;
+ DBUG_ENTER("wait_for_relay_log_space");
+ pthread_mutex_lock(&rli->log_space_lock);
+ save_proc_info = thd->proc_info;
+ thd->proc_info = "Waiting for relay log space to free";
+ while (rli->log_space_limit < rli->log_space_total &&
+ !(slave_killed=io_slave_killed(thd,mi)))
+ {
+ pthread_cond_wait(&rli->log_space_cond, &rli->log_space_lock);
+ }
+ thd->proc_info = save_proc_info;
+ pthread_mutex_unlock(&rli->log_space_lock);
+ DBUG_RETURN(slave_killed);
+}
+
+static int count_relay_log_space(RELAY_LOG_INFO* rli)
+{
+ LOG_INFO linfo;
+ DBUG_ENTER("count_relay_log_space");
+ rli->log_space_total = 0;
+ if (rli->relay_log.find_first_log(&linfo,""))
+ {
+ sql_print_error("Could not find first log while counting relay log space");
+ DBUG_RETURN(1);
+ }
+ if (add_relay_log(rli,&linfo))
+ DBUG_RETURN(1);
+ while (!rli->relay_log.find_next_log(&linfo))
+ {
+ if (add_relay_log(rli,&linfo))
+ DBUG_RETURN(1);
+ }
+ DBUG_RETURN(0);
+}
int init_master_info(MASTER_INFO* mi, const char* master_info_fname,
const char* slave_info_fname)
@@ -1242,6 +1318,7 @@ int show_master_info(THD* thd, MASTER_INFO* mi)
field_list.push_back(new Item_empty_string("Last_error", 20));
field_list.push_back(new Item_empty_string("Skip_counter", 12));
field_list.push_back(new Item_empty_string("Exec_master_log_pos", 12));
+ field_list.push_back(new Item_empty_string("Relay_log_space", 12));
if(send_fields(thd, field_list, 1))
DBUG_RETURN(-1);
@@ -1268,6 +1345,7 @@ int show_master_info(THD* thd, MASTER_INFO* mi)
net_store_data(packet, mi->rli.last_slave_error);
net_store_data(packet, mi->rli.slave_skip_counter);
net_store_data(packet, (longlong) mi->rli.master_log_pos);
+ net_store_data(packet, (longlong) mi->rli.log_space_total);
pthread_mutex_unlock(&mi->rli.data_lock);
pthread_mutex_unlock(&mi->data_lock);
@@ -1783,6 +1861,14 @@ from master");
goto err;
}
flush_master_info(mi);
+ if (mi->rli.log_space_limit && mi->rli.log_space_limit <
+ mi->rli.log_space_total)
+ if (wait_for_relay_log_space(&mi->rli))
+ {
+ sql_print_error("Slave I/O thread aborted while waiting for relay \
+log space");
+ goto err;
+ }
// TODO: check debugging abort code
#ifndef DBUG_OFF
if (abort_slave_event_count && !--events_till_abort)
@@ -1986,7 +2072,7 @@ static int process_io_create_file(MASTER_INFO* mi, Create_file_log_event* cev)
goto err;
}
- /* this dummy block is so we could insantiate Append_block_log_event
+ /* this dummy block is so we could instantiate Append_block_log_event
once and then modify it slightly instead of doing it multiple times
in the loop
*/
@@ -2012,6 +2098,7 @@ static int process_io_create_file(MASTER_INFO* mi, Create_file_log_event* cev)
relay log");
goto err;
}
+ mi->rli.relay_log.harvest_bytes_written(&mi->rli.log_space_total);
break;
}
if (unlikely(cev_not_written))
@@ -2026,6 +2113,7 @@ relay log");
goto err;
}
cev_not_written=0;
+ mi->rli.relay_log.harvest_bytes_written(&mi->rli.log_space_total);
}
else
{
@@ -2038,6 +2126,7 @@ relay log");
relay log");
goto err;
}
+ mi->rli.relay_log.harvest_bytes_written(&mi->rli.log_space_total) ;
}
}
}
@@ -2145,6 +2234,7 @@ static int queue_old_event(MASTER_INFO *mi, const char *buf,
DBUG_ASSERT(!tmp_buf);
return 1;
}
+ mi->rli.relay_log.harvest_bytes_written(&mi->rli.log_space_total);
}
delete ev;
if (likely(inc_pos))
@@ -2198,6 +2288,7 @@ int queue_event(MASTER_INFO* mi,const char* buf, ulong event_len)
{
if (likely(inc_pos))
mi->master_log_pos += event_len;
+ mi->rli.relay_log.harvest_bytes_written(&mi->rli.log_space_total);
}
if (unlikely(processed_stop_event))
mi->ignore_stop_event=1;
diff --git a/sql/slave.h b/sql/slave.h
index 7ae5da1a340..354fc46e99d 100644
--- a/sql/slave.h
+++ b/sql/slave.h
@@ -31,6 +31,7 @@ extern char* slave_load_tmpdir;
extern my_string master_info_file,relay_log_info_file;
extern my_string opt_relay_logname, opt_relaylog_index_name;
extern bool opt_skip_slave_start;
+extern ulong relay_log_space_limit;
struct st_master_info;
/*
@@ -153,6 +154,9 @@ typedef struct st_relay_log_info
bool log_pos_current;
bool abort_pos_wait;
bool skip_log_purge;
+ ulonglong log_space_limit,log_space_total;
+ pthread_mutex_t log_space_lock;
+ pthread_cond_t log_space_cond;
st_relay_log_info():info_fd(-1),cur_log_fd(-1),inited(0),
cur_log_init_count(0),
@@ -163,17 +167,21 @@ typedef struct st_relay_log_info
bzero(&info_file,sizeof(info_file));
pthread_mutex_init(&run_lock, MY_MUTEX_INIT_FAST);
pthread_mutex_init(&data_lock, MY_MUTEX_INIT_FAST);
+ pthread_mutex_init(&log_space_lock, MY_MUTEX_INIT_FAST);
pthread_cond_init(&data_cond, NULL);
pthread_cond_init(&start_cond, NULL);
pthread_cond_init(&stop_cond, NULL);
+ pthread_cond_init(&log_space_cond, NULL);
}
~st_relay_log_info()
{
pthread_mutex_destroy(&run_lock);
pthread_mutex_destroy(&data_lock);
+ pthread_mutex_destroy(&log_space_lock);
pthread_cond_destroy(&data_cond);
pthread_cond_destroy(&start_cond);
pthread_cond_destroy(&stop_cond);
+ pthread_cond_destroy(&log_space_cond);
}
inline void inc_pending(ulonglong val)
{
diff --git a/sql/sql_class.h b/sql/sql_class.h
index 289a2ab9255..d8824e80686 100644
--- a/sql/sql_class.h
+++ b/sql/sql_class.h
@@ -78,12 +78,29 @@ class MYSQL_LOG {
bool need_start_event;
pthread_cond_t update_cond;
bool no_auto_events; // for relay binlog
+ ulonglong bytes_written;
friend class Log_event;
public:
MYSQL_LOG();
~MYSQL_LOG();
pthread_mutex_t* get_log_lock() { return &LOCK_log; }
+ void reset_bytes_written()
+ {
+ bytes_written = 0;
+ }
+ void harvest_bytes_written(ulonglong* counter)
+ {
+#ifndef DBUG_OFF
+ char buf1[22],buf2[22];
+#endif
+ DBUG_ENTER("harvest_bytes_written");
+ (*counter)+=bytes_written;
+ DBUG_PRINT("info",("counter=%s,bytes_written=%s", llstr(*counter,buf1),
+ llstr(bytes_written,buf2)));
+ bytes_written=0;
+ DBUG_VOID_RETURN;
+ }
IO_CACHE* get_log_file() { return &log_file; }
void signal_update() { pthread_cond_broadcast(&update_cond);}
void wait_for_update(THD* thd);
diff --git a/sql/sql_repl.cc b/sql/sql_repl.cc
index 8216dec815a..398ff443ad4 100644
--- a/sql/sql_repl.cc
+++ b/sql/sql_repl.cc
@@ -751,7 +751,7 @@ int change_master(THD* thd, MASTER_INFO* mi)
need_relay_log_purge = 0;
mi->rli.skip_log_purge=1;
strnmov(mi->rli.relay_log_name,lex_mi->relay_log_name,
- sizeof(mi->rli.relay_log_name));
+ sizeof(mi->rli.relay_log_name)-1);
}
if (lex_mi->relay_log_pos)