Skip to content

Commit 9174364

Browse files
committedNov 25, 2010
WL#3127 slave side TCP address binding
- Extend CHANGE MASTER with MASTER_BIND='interface' - Extend SHOW SLAVE STATUS with a new column Master_Bind - Add testcase
1 parent 813b6be commit 9174364

11 files changed

+206
-22
lines changed
 

‎mysql-test/extra/rpl_tests/rpl_change_master.test

+33
Original file line numberDiff line numberDiff line change
@@ -292,5 +292,38 @@ if (`SELECT "$ignore_new_value" <> "$ignore_crash_value" || $connect_new_value <
292292
-- die
293293
}
294294

295+
#
296+
# WL#3127 slave side TCP address binding
297+
# - CHANGE MASTER ... MASTER_BIND='interface'
298+
# - SHOW SLAVE STATUS has new column Master_Bind
299+
#
300+
301+
let $check_ipv6_just_check=1;
302+
source include/check_ipv6.inc;
303+
let $check_ipv6_just_check=0;
304+
305+
# Test valid IPv4 address
306+
let $master_bind='127.0.0.1';
307+
--source extra/rpl_tests/rpl_change_master_bind.inc
308+
309+
# Test invalid IPv4 address
310+
let $master_bind='1.1.1.1';
311+
let $master_bind_error_expected=2003;
312+
--source extra/rpl_tests/rpl_change_master_bind.inc
313+
let $master_bind_error_expected=0;
314+
315+
# Test valid IPv6 address
316+
let $master_bind='::1';
317+
if (!$check_ipv6_supported)
318+
{
319+
# No IPv6 support, fallback to IPv4
320+
let $master_bind='127.0.0.1';
321+
}
322+
--source extra/rpl_tests/rpl_change_master_bind.inc
323+
324+
# Test with no bind address(check that reset works)
325+
let $master_bind='';
326+
--source extra/rpl_tests/rpl_change_master_bind.inc
327+
295328
-- source include/master-slave-reset.inc
296329
-- source include/master-slave-end.inc
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
#
2+
# Test CHANGE MASTER MASTER_BIND=xxx
3+
#
4+
# Parameters:
5+
# $master_bind - the address to use for MASTER_BIND
6+
# $master_bind_error_expected - expect an error when using the specified
7+
# master_bind address
8+
#
9+
#
10+
11+
# Stop the slave
12+
connection slave;
13+
source include/stop_slave.inc;
14+
15+
# Create table and insert one record with the bind address on master
16+
connection master;
17+
create table t1(n int, b varchar(256));
18+
--replace_result $master_bind <master_bind>
19+
eval insert into t1 values(1, $master_bind);
20+
21+
# Configure slave to connect to master with then give bind address
22+
connection slave;
23+
--replace_result $master_bind <master_bind>
24+
eval change master to master_bind=$master_bind;
25+
start slave;
26+
27+
# Check that SHOW SLAVE STATUS has Master_bind column set to $master_bind
28+
let $master_bind_value= query_get_value(SHOW SLAVE STATUS, Master_Bind, 1);
29+
if (`select '$master_bind_value' != $master_bind`)
30+
{
31+
source include/show_rpl_debug_info.inc;
32+
echo 'master_bind_value: $master_bind_value' != 'master_bind: $master_bind';
33+
die Master_bind in SHOW SLAVE STAUS not showing configured value;
34+
}
35+
36+
if ($master_bind_error_expected)
37+
{
38+
# The given master bind address is not valid
39+
# and replication should fail
40+
let $slave_io_errno= $master_bind_error_expected;
41+
source include/wait_for_slave_io_error.inc;
42+
echo got expected error $master_bind_error_expected;
43+
source include/stop_slave.inc;
44+
45+
# Reset the master_bind to that cleanup can run
46+
eval change master to master_bind='';
47+
start slave;
48+
49+
}
50+
51+
source include/wait_for_slave_to_start.inc;
52+
53+
connection master;
54+
sync_slave_with_master;
55+
56+
connection slave;
57+
let $master_bind_repl= query_get_value(select b from t1, b, 1);
58+
if (`select '$master_bind_repl' != $master_bind`)
59+
{
60+
select * from t1;
61+
source include/show_rpl_debug_info.inc;
62+
echo 'master_bind_repl: $master_bind_repl' != 'master_bind: $master_bind';
63+
die The replicated value to show replication working was not correct;
64+
}
65+
66+
# Clean up
67+
connection master;
68+
drop table t1;
69+
sync_slave_with_master;

‎mysql-test/include/check_ipv6.inc

+12-2
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,20 @@
1-
# Check if ipv6 is available. If not, server is crashing (see BUG#48915).
1+
# Check if ipv6 is available.
2+
#
3+
# Parameters:
4+
# $check_ipv6_just_check - don't skip the test if IPv6 is unsupported,
5+
# just set the variable $check_ipv6_supported
6+
#
27
--disable_query_log
38
--disable_abort_on_error
9+
let $check_ipv6_supported=1;
410
connect (checkcon123456789,::1,root,,test);
511
if($mysql_errno)
612
{
7-
skip wrong IP;
13+
let $check_ipv6_supported=0;
14+
if(!$check_ipv6_just_check)
15+
{
16+
skip No IPv6 support;
17+
}
818
}
919
connection default;
1020
disconnect checkcon123456789;

‎mysql-test/suite/rpl/r/rpl_change_master.result

+28
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,34 @@ CHANGE MASTER TO master_connect_retry= 200, IGNORE_SERVER_IDS= (100, 200, 300, 4
7777
### start slave server
7878
include/start_slave.inc
7979
Eexpected values: "100, 200, 300, 400, 500" == "100, 200, 300, 400, 500" or 200 == 200
80+
include/stop_slave.inc
81+
create table t1(n int, b varchar(256));
82+
insert into t1 values(1, <master_bind>);
83+
change master to master_bind=<master_bind>;
84+
start slave;
85+
drop table t1;
86+
include/stop_slave.inc
87+
create table t1(n int, b varchar(256));
88+
insert into t1 values(1, <master_bind>);
89+
change master to master_bind=<master_bind>;
90+
start slave;
91+
got expected error 2003
92+
include/stop_slave.inc
93+
change master to master_bind='';
94+
start slave;
95+
drop table t1;
96+
include/stop_slave.inc
97+
create table t1(n int, b varchar(256));
98+
insert into t1 values(1, <master_bind>);
99+
change master to master_bind=<master_bind>;
100+
start slave;
101+
drop table t1;
102+
include/stop_slave.inc
103+
create table t1(n int, b varchar(256));
104+
insert into t1 values(1, <master_bind>);
105+
change master to master_bind=<master_bind>;
106+
start slave;
107+
drop table t1;
80108
stop slave;
81109
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
82110
reset master;

‎mysql-test/suite/rpl/r/rpl_change_master_crash_safe.result

+28
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,34 @@ CHANGE MASTER TO master_connect_retry= 200, IGNORE_SERVER_IDS= (100, 200, 300, 4
7777
### start slave server
7878
include/start_slave.inc
7979
Eexpected values: "100, 200, 300, 400, 500" == "100, 200, 300, 400, 500" or 200 == 200
80+
include/stop_slave.inc
81+
create table t1(n int, b varchar(256));
82+
insert into t1 values(1, <master_bind>);
83+
change master to master_bind=<master_bind>;
84+
start slave;
85+
drop table t1;
86+
include/stop_slave.inc
87+
create table t1(n int, b varchar(256));
88+
insert into t1 values(1, <master_bind>);
89+
change master to master_bind=<master_bind>;
90+
start slave;
91+
got expected error 2003
92+
include/stop_slave.inc
93+
change master to master_bind='';
94+
start slave;
95+
drop table t1;
96+
include/stop_slave.inc
97+
create table t1(n int, b varchar(256));
98+
insert into t1 values(1, <master_bind>);
99+
change master to master_bind=<master_bind>;
100+
start slave;
101+
drop table t1;
102+
include/stop_slave.inc
103+
create table t1(n int, b varchar(256));
104+
insert into t1 values(1, <master_bind>);
105+
change master to master_bind=<master_bind>;
106+
start slave;
107+
drop table t1;
80108
stop slave;
81109
drop table if exists t1,t2,t3,t4,t5,t6,t7,t8,t9;
82110
reset master;

‎sql/lex.h

+1
Original file line numberDiff line numberDiff line change
@@ -316,6 +316,7 @@ static SYMBOL symbols[] = {
316316
{ "LOOP", SYM(LOOP_SYM)},
317317
{ "LOW_PRIORITY", SYM(LOW_PRIORITY)},
318318
{ "MASTER", SYM(MASTER_SYM)},
319+
{ "MASTER_BIND", SYM(MASTER_BIND_SYM)},
319320
{ "MASTER_CONNECT_RETRY", SYM(MASTER_CONNECT_RETRY_SYM)},
320321
{ "MASTER_DELAY", SYM(MASTER_DELAY_SYM)},
321322
{ "MASTER_HOST", SYM(MASTER_HOST_SYM)},

‎sql/rpl_mi.cc

+3-14
Original file line numberDiff line numberDiff line change
@@ -89,7 +89,7 @@ Master_info::Master_info(PSI_mutex_key *param_key_info_run_lock,
8989
clock_diff_with_master(0), heartbeat_period(0),
9090
received_heartbeats(0), master_id(0), retry_count(master_retry_count)
9191
{
92-
host[0] = 0; user[0] = 0; password[0] = 0;
92+
host[0] = 0; user[0] = 0; password[0] = 0; bind_addr[0] = 0;
9393
ssl_ca[0]= 0; ssl_capath[0]= 0; ssl_cert[0]= 0;
9494
ssl_cipher[0]= 0; ssl_key[0]= 0;
9595
master_uuid[0]= 0;
@@ -371,13 +371,7 @@ bool Master_info::read_info(Rpl_info_handler *from)
371371
*/
372372
if (lines >= LINE_FOR_MASTER_BIND)
373373
{
374-
/*
375-
This is a placeholder for the bind option.
376-
Please, update this after WL#3126 and
377-
WL#3127.
378-
*/
379-
char fake_bind[2];
380-
if (from->get_info(fake_bind, sizeof(fake_bind), ""))
374+
if (from->get_info(bind_addr, sizeof(bind_addr), ""))
381375
DBUG_RETURN(TRUE);
382376
}
383377

@@ -447,12 +441,7 @@ bool Master_info::write_info(Rpl_info_handler *to, bool force)
447441
to->set_info(ssl_key) ||
448442
to->set_info(ssl_verify_server_cert) ||
449443
to->set_info(heartbeat_period) ||
450-
/*
451-
This is a placeholder for the bind option.
452-
Please, update this after WL#3126 and
453-
WL#3127.
454-
*/
455-
to->set_info("") ||
444+
to->set_info(bind_addr) ||
456445
to->set_info(ignore_server_ids) ||
457446
to->set_info(master_uuid) ||
458447
to->set_info(retry_count))

‎sql/rpl_mi.h

+1
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,7 @@ class Master_info : public Rpl_info
7272

7373
/* the variables below are needed because we can change masters on the fly */
7474
char host[HOSTNAME_LENGTH+1];
75+
char bind_addr[HOSTNAME_LENGTH+1];
7576
char user[USERNAME_LENGTH+1];
7677
char password[MAX_PASSWORD_LENGTH+1];
7778
my_bool ssl; // enables use of SSL connection if true

‎sql/rpl_slave.cc

+25-5
Original file line numberDiff line numberDiff line change
@@ -1912,6 +1912,8 @@ bool show_master_info(THD* thd, Master_info* mi)
19121912
field_list.push_back(new Item_empty_string("Slave_SQL_Running_State", 20));
19131913
field_list.push_back(new Item_return_int("Master_Retry_Count", 10,
19141914
MYSQL_TYPE_LONGLONG));
1915+
field_list.push_back(new Item_empty_string("Master_Bind",
1916+
sizeof(mi->bind_addr)));
19151917

19161918
if (protocol->send_result_set_metadata(&field_list,
19171919
Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF))
@@ -2100,6 +2102,8 @@ bool show_master_info(THD* thd, Master_info* mi)
21002102
protocol->store(slave_sql_running_state, &my_charset_bin);
21012103
// Master_Retry_Count
21022104
protocol->store((ulonglong) mi->retry_count);
2105+
// Master_Bind
2106+
protocol->store(mi->bind_addr, &my_charset_bin);
21032107

21042108
mysql_mutex_unlock(&mi->rli->err_lock);
21052109
mysql_mutex_unlock(&mi->err_lock);
@@ -4462,6 +4466,12 @@ static int connect_to_master(THD* thd, MYSQL* mysql, Master_info* mi,
44624466
mysql_options(mysql, MYSQL_OPT_CONNECT_TIMEOUT, (char *) &slave_net_timeout);
44634467
mysql_options(mysql, MYSQL_OPT_READ_TIMEOUT, (char *) &slave_net_timeout);
44644468

4469+
if (mi->bind_addr[0])
4470+
{
4471+
DBUG_PRINT("info",("bind_addr: %s", mi->bind_addr));
4472+
mysql_options(mysql, MYSQL_OPT_BIND, mi->bind_addr);
4473+
}
4474+
44654475
#ifdef HAVE_OPENSSL
44664476
if (mi->ssl)
44674477
{
@@ -4588,6 +4598,12 @@ MYSQL *rpl_connect_master(MYSQL *mysql)
45884598
mysql_options(mysql, MYSQL_OPT_CONNECT_TIMEOUT, (char *) &slave_net_timeout);
45894599
mysql_options(mysql, MYSQL_OPT_READ_TIMEOUT, (char *) &slave_net_timeout);
45904600

4601+
if (mi->bind_addr[0])
4602+
{
4603+
DBUG_PRINT("info",("bind_addr: %s", mi->bind_addr));
4604+
mysql_options(mysql, MYSQL_OPT_BIND, mi->bind_addr);
4605+
}
4606+
45914607
#ifdef HAVE_OPENSSL
45924608
if (mi->ssl)
45934609
{
@@ -5521,7 +5537,7 @@ bool change_master(THD* thd, Master_info* mi)
55215537
bool need_relay_log_purge= 1;
55225538
char *var_master_log_name= NULL, *var_group_master_log_name= NULL;
55235539
bool ret= FALSE;
5524-
char saved_host[HOSTNAME_LENGTH + 1];
5540+
char saved_host[HOSTNAME_LENGTH + 1], saved_bind_addr[HOSTNAME_LENGTH + 1];
55255541
uint saved_port= 0;
55265542
char saved_log_name[FN_REFLEN];
55275543
my_off_t saved_log_pos= 0;
@@ -5570,6 +5586,7 @@ bool change_master(THD* thd, Master_info* mi)
55705586
Before processing the command, save the previous state.
55715587
*/
55725588
strmake(saved_host, mi->host, HOSTNAME_LENGTH);
5589+
strmake(saved_bind_addr, mi->bind_addr, HOSTNAME_LENGTH);
55735590
saved_port= mi->port;
55745591
strmake(saved_log_name, mi->get_master_log_name(), FN_REFLEN - 1);
55755592
saved_log_pos= mi->get_master_log_pos();
@@ -5603,6 +5620,8 @@ bool change_master(THD* thd, Master_info* mi)
56035620

56045621
if (lex_mi->host)
56055622
strmake(mi->host, lex_mi->host, sizeof(mi->host)-1);
5623+
if (lex_mi->bind_addr)
5624+
strmake(mi->bind_addr, lex_mi->bind_addr, sizeof(mi->bind_addr)-1);
56065625
if (lex_mi->user)
56075626
strmake(mi->user, lex_mi->user, sizeof(mi->user)-1);
56085627
if (lex_mi->password)
@@ -5785,11 +5804,12 @@ bool change_master(THD* thd, Master_info* mi)
57855804

57865805
sql_print_information("'CHANGE MASTER TO executed'. "
57875806
"Previous state master_host='%s', master_port='%u', master_log_file='%s', "
5788-
"master_log_pos='%ld'. "
5807+
"master_log_pos='%ld', master_bind='%s'. "
57895808
"New state master_host='%s', master_port='%u', master_log_file='%s', "
5790-
"master_log_pos='%ld'.", saved_host, saved_port, saved_log_name,
5791-
(ulong) saved_log_pos, mi->host, mi->port, mi->get_master_log_name(),
5792-
(ulong) mi->get_master_log_pos());
5809+
"master_log_pos='%ld', master_bind='%s'.",
5810+
saved_host, saved_port, saved_log_name, (ulong) saved_log_pos,
5811+
saved_bind_addr, mi->host, mi->port, mi->get_master_log_name(),
5812+
(ulong) mi->get_master_log_pos(), mi->bind_addr);
57935813

57945814
/*
57955815
If we don't write new coordinates to disk now, then old will remain in

‎sql/sql_lex.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -205,7 +205,7 @@ typedef struct st_lex_server_options
205205
*/
206206
typedef struct st_lex_master_info
207207
{
208-
char *host, *user, *password, *log_file_name;
208+
char *host, *user, *password, *log_file_name, *bind_addr;
209209
uint port, connect_retry;
210210
float heartbeat_period;
211211
int sql_delay;

‎sql/sql_yacc.yy

+5
Original file line numberDiff line numberDiff line change
@@ -1072,6 +1072,7 @@ bool my_yyoverflow(short **a, YYSTYPE **b, ulong *yystacksize);
10721072
%token LOOP_SYM
10731073
%token LOW_PRIORITY
10741074
%token LT /* OPERATOR */
1075+
%token MASTER_BIND_SYM
10751076
%token MASTER_CONNECT_RETRY_SYM
10761077
%token MASTER_DELAY_SYM
10771078
%token MASTER_HOST_SYM
@@ -1894,6 +1895,10 @@ master_def:
18941895
{
18951896
Lex->mi.host = $3.str;
18961897
}
1898+
| MASTER_BIND_SYM EQ TEXT_STRING_sys
1899+
{
1900+
Lex->mi.bind_addr = $3.str;
1901+
}
18971902
| MASTER_USER_SYM EQ TEXT_STRING_sys
18981903
{
18991904
Lex->mi.user = $3.str;

0 commit comments

Comments
 (0)