From: Yugo Nagata
- This option specifies the network device name for sending heartbeat signals. - You can use multiple devices. - The number at the end of the parameter name is referred as "device number", + This option specifies the destination of heartbeat signals bu IP address or hostname. + You can use multiple destination. + The number at the end of the parameter name is referred as "destination number", and it starts from 0. - If you want to set mutiple destination (heartbeat_destiationN) for one device, - specify the device name repeatedly using different numbers. This works only heartbeat mode.
@@ -4220,12 +4218,15 @@ Configuration about virtual IP interface control
- This option specifies the destination of heartbeat signals which is sent from the device specified by - heartbeat_deviceX. Use IP address or hostname. - The number at the end of the parameter name is referred as "device number", + This option specifies the port number of destination of heartbeat signals + which is specified by heartbeat_destinationX. + This is usually the same value as wd_heartbeat_port + You must use another value if the port number is unusable on a certain host or + there are more than two pgpool-IIs in a host. + The number at the end of the parameter name is referred as "destination number", and it starts from 0. This works only heartbeat mode.
@@ -4234,23 +4235,23 @@ Configuration about virtual IP interface control- This option specifies the port number of destination of heartbeat signals which is sent from the device specified by - heartbeat_deviceX. - This is usually the same value of wd_heartbeat_port - You must set another value if the port number is unusable or there are more than two pgpool-IIs in a host. - The number at the end of the parameter name is referred as "device number", + This option specifies the network device name for sending heartbeat signals to + destination specified by heartbeat_destinationX. + You can use the same device for different distinations. + The number at the end of the parameter name is referred as "destination number", and it starts from 0. This works only heartbeat mode. + In addition, this works only when pgpool-II has root privilege and are running on Linux, + because this uses SO_BINDTODEVICE socket option.
You need to restart pgpool-II if you change this value.
- ãã¼ããã¼ãã®éåä¿¡ã«ç¨ãããããã¯ã¼ã¯ããã¤ã¹åãæå®ãã¾ãã - è¤æ°ã®ããã¤ã¹ãè¨å®å¯è½ã§ãã - æ°å¤ã®é¨åã¯ããã¤ã¹ã®çªå·ã§ãã - ããã¤ã¹æ¯ã« 0 ããã®é£çªã«ãã¾ãã - ï¼ã¤ã®ããã¤ã¹ã«è¤æ°ã®ãã¼ããã¼ãéä¿¡å ï¼heartbeat_destiationNï¼ãè¨å®ããå ´åã¯ãéè¤ããããã¤ã¹åãç°ãªãçªå·ã§æå®ãã¦ãã ããã + ãã¼ããã¼ãä¿¡å·ã®éãå ãããã¹ãåã IP ã§æå®ãã¾ãã + è¤æ°ã®éãå ãæå®å¯è½ã§ãã + æ°å¤ã®é¨åã¯éãå ã®çªå·ã§ãã0 ããã®é£çªã«ãã¾ãã ãã¼ããã¼ãã¢ã¼ãã®å ´åã®ã¿æå¹ã§ãã
@@ -4335,12 +4333,13 @@ pgpool-II ãçãã¦ã㦠PostgreSQL ã¨ç¹ãã£ã¦ããå ´åã§ãã
- heartbeat_deviceXã«æå®ããããã¤ã¹ããéããã¼ããã¼ãä¿¡å·ã®å®å ãããã¹ãåã IP ã§æå®ãã¾ãã - æ°å¤ã®é¨åã¯ããã¤ã¹ã®çªå·ã§ãã - ããã¤ã¹æ¯ã« 0 ããã®é£çªã«ãã¾ãã + heartbeat_destinationXã«æå®ãããã¼ããã¼ãä¿¡å·ã®éãå ã®ãã¼ãçªå·ãæå®ãã¾ãã + é常㯠wd_heartbeat_port ã¨åãå¤ãæå®ãã¾ãã + ãã®ãã¼ãçªå·ã使ç¨ã§ããªããã¹ãããåããã¹ãã§è¤æ°ã® pgpool-II ãåä½ãããå ´åã«ã¯ãç°ãªãå¤ãæå®ããå¿ è¦ãããã¾ãã + æ°å¤ã®é¨åã¯éãå ã®çªå·ã§ãã0 ããã®é£çªã«ãã¾ãã ãã¼ããã¼ãã¢ã¼ãã®å ´åã®ã¿æå¹ã§ãã
@@ -4348,15 +4347,14 @@ pgpool-II ãçãã¦ã㦠PostgreSQL ã¨ç¹ãã£ã¦ããå ´åã§ãã
- heartbeat_deviceXã«æå®ããããã¤ã¹ããéããã¼ããã¼ãä¿¡å·ã®å®å ã®ãã¼ãçªå·ãæå®ãã¾ãã - é常㯠wd_heartbeat_port ã¨åãå¤ãæå®ãã¾ãã - ãã®ãã¼ãçªå·ã使ç¨ã§ããªããã¹ãããåããã¹ãã§è¤æ°ã® pgpool-II ãåä½ãããå ´åã«ã¯ãç°ãªãå¤ãæå®ããå¿ è¦ãããã¾ãã - æ°å¤ã®é¨åã¯ããã¤ã¹ã®çªå·ã§ãã - ããã¤ã¹æ¯ã« 0 ããã®é£çªã«ãã¾ãã + heartbeat_destinationXã«æå®ããéãå ã¨ã®ãã¼ããã¼ãã®éåä¿¡ã«ç¨ãããããã¯ã¼ã¯ããã¤ã¹åãæå®ãã¾ãã + æ°å¤ã®é¨åã¯éãå ã®çªå·ã§ããããã¤ã¹æ¯ã« 0 ããã®é£çªã«ãã¾ãã + è¤æ°ã®ç°ãªãéãå ã«åãããã¤ã¹ãè¨å®ãããã¨ãå¯è½ã§ãã ãã¼ããã¼ãã¢ã¼ãã®å ´åã®ã¿æå¹ã§ãã + ã¾ããSO_BINDTODEVICE ã½ã±ãããªãã·ã§ã³ã使ç¨ãã¦ãããããpgpool-II ã Linux ã§ root 権éã§èµ·åãã¦ããå ´åã®ã¿æå¹ã§ãã
ãã®ãã©ã¡ã¼ã¿ã夿´ããæã«ã¯ pgpool-II ãåèµ·åãã¦ãã ããã diff --git a/pgpool.conf.sample b/pgpool.conf.sample index 86244baa7..a50092f6e 100644 --- a/pgpool.conf.sample +++ b/pgpool.conf.sample @@ -517,22 +517,25 @@ wd_heartbeat_keepalive = 2 wd_heartbeat_deadtime = 30 # Deadtime interval for heartbeat signal (sec) # (change requires restart) -heartbeat_device0 = 'eth0' - # Name of NIC device 0 using for - # sending/receiving heartbeat signal - # (change requires restart) -heartbeat_destination_ip0 = 'host0_ip1' - # Destination host name or IP address - # for sending heartbeat signal using NIC device 0. +heartbeat_destination = 'host0_ip1' + # Host name or IP address of destination 0 + # for sending heartbeat signal. # (change requires restart) heartbeat_destination_port0 = 9694 - # Destination port number for sending heartbeat - # signal to destination 0. Usually this is the - # same of wd_heartbeat_port. + # Port number of destination 0 for sending + # heartbeat signal. Usually this is the + # same as wd_heartbeat_port. # (change requires restart) -#heartbeat_device1 = 'eth1' +heartbeat_device0 = 'eth0' + # Name of NIC device using for + # sending/receiving heartbeat signal + # to/from destination 0. + # This works only when pgpool has root privilege. + # (change requires restart) + #heartbeat_destination_ip1 = 'host0_ip2' #heartbeat_destination_port1 = 9694 +#heartbeat_device1 = 'eth1' # -- query mode -- diff --git a/pgpool.conf.sample-master-slave b/pgpool.conf.sample-master-slave index a83baaa0a..e4b975500 100644 --- a/pgpool.conf.sample-master-slave +++ b/pgpool.conf.sample-master-slave @@ -517,22 +517,25 @@ wd_heartbeat_keepalive = 2 wd_heartbeat_deadtime = 30 # Deadtime interval for heartbeat signal (sec) # (change requires restart) -heartbeat_device0 = 'eth0' - # Name of NIC device 0 using for - # sending/receiving heartbeat signal - # (change requires restart) -heartbeat_destination0 = 'host0_ip1' - # Destination host name or IP address - # for sending heartbeat signal using NIC device 0. +heartbeat_destination = 'host0_ip1' + # Host name or IP address of destination 0 + # for sending heartbeat signal. # (change requires restart) heartbeat_destination_port0 = 9694 - # Destination port number for sending heartbeat - # signal to destination 0. Usually this is the - # same of wd_heartbeat_port. + # Port number of destination 0 for sending + # heartbeat signal. Usually this is the + # same as wd_heartbeat_port. # (change requires restart) -#heartbeat_device1 = 'eth1' -#heartbeat_destination1 = 'host0_ip2' +heartbeat_device0 = 'eth0' + # Name of NIC device using for + # sending/receiving heartbeat signal + # to/from destination 0. + # This works only when pgpool has root privilege. + # (change requires restart) + +#heartbeat_destination_ip1 = 'host0_ip2' #heartbeat_destination_port1 = 9694 +#heartbeat_device1 = 'eth1' # -- query mode -- diff --git a/pgpool.conf.sample-replication b/pgpool.conf.sample-replication index 9d5fb6fd6..114a8114a 100644 --- a/pgpool.conf.sample-replication +++ b/pgpool.conf.sample-replication @@ -516,22 +516,25 @@ wd_heartbeat_keepalive = 2 wd_heartbeat_deadtime = 30 # Deadtime interval for heartbeat signal (sec) # (change requires restart) -heartbeat_device0 = 'eth0' - # Name of NIC device 0 using for - # sending/receiving heartbeat signal - # (change requires restart) -heartbeat_destination0 = 'host0_ip1' - # Destination host name or IP address - # for sending heartbeat signal using NIC device 0. +heartbeat_destination = 'host0_ip1' + # Host name or IP address of destination 0 + # for sending heartbeat signal. # (change requires restart) heartbeat_destination_port0 = 9694 - # Destination port number for sending heartbeat - # signal to destination 0. Usually this is the - # same of wd_heartbeat_port. + # Port number of destination 0 for sending + # heartbeat signal. Usually this is the + # same as wd_heartbeat_port. # (change requires restart) -#heartbeat_device1 = 'eth1' -#heartbeat_destination1 = 'host0_ip2' +heartbeat_device0 = 'eth0' + # Name of NIC device using for + # sending/receiving heartbeat signal + # to/from destination 0. + # This works only when pgpool has root privilege. + # (change requires restart) + +#heartbeat_destination_ip1 = 'host0_ip2' #heartbeat_destination_port1 = 9694 +#heartbeat_device1 = 'eth1' # -- query mode -- diff --git a/pgpool.conf.sample-stream b/pgpool.conf.sample-stream index a8e8ddb27..8d74931af 100644 --- a/pgpool.conf.sample-stream +++ b/pgpool.conf.sample-stream @@ -516,22 +516,25 @@ wd_heartbeat_keepalive = 2 wd_heartbeat_deadtime = 30 # Deadtime interval for heartbeat signal (sec) # (change requires restart) -heartbeat_device0 = 'eth0' - # Name of NIC device 0 using for - # sending/receiving heartbeat signal - # (change requires restart) -heartbeat_destination0 = 'host0_ip1' - # Destination host name or IP address - # for sending heartbeat signal using NIC device 0. +heartbeat_destination = 'host0_ip1' + # Host name or IP address of destination 0 + # for sending heartbeat signal. # (change requires restart) heartbeat_destination_port0 = 9694 - # Destination port number for sending heartbeat - # signal to destination 0. Usually this is the - # same of wd_heartbeat_port. + # Port number of destination 0 for sending + # heartbeat signal. Usually this is the + # same as wd_heartbeat_port. # (change requires restart) -#heartbeat_device1 = 'eth1' -#heartbeat_destination1 = 'host0_ip2' +heartbeat_device0 = 'eth0' + # Name of NIC device using for + # sending/receiving heartbeat signal + # to/from destination 0. + # This works only when pgpool has root privilege. + # (change requires restart) + +#heartbeat_destination_ip1 = 'host0_ip2' #heartbeat_destination_port1 = 9694 +#heartbeat_device1 = 'eth1' # -- query mode -- diff --git a/pool_config.c b/pool_config.c index d98b3dad5..b2101a081 100644 --- a/pool_config.c +++ b/pool_config.c @@ -3944,10 +3944,7 @@ int pool_get_config(char *confpath, POOL_CONFIG_CONTEXT context) return(-1); } if (context == INIT_CONFIG || (context == RELOAD_CONFIG )) - { strlcpy(WD_HB_IF(slot).if_name, str, WD_MAX_IF_NAME_LEN); - pool_config->num_hb_if = slot + 1; - } } /* this must be prior to hertbeat_destination */ @@ -3966,7 +3963,10 @@ int pool_get_config(char *confpath, POOL_CONFIG_CONTEXT context) } if (context == INIT_CONFIG || (context == RELOAD_CONFIG )) + { WD_HB_IF(slot).dest_port = atoi(yytext); + pool_config->num_hb_if = slot + 1; + } } else if (!strncmp(key, "heartbeat_destination", 21) && CHECK_CONTEXT(INIT_CONFIG|RELOAD_CONFIG, context) && diff --git a/pool_config.l b/pool_config.l index 556c41e3e..2026f2c1f 100644 --- a/pool_config.l +++ b/pool_config.l @@ -2397,10 +2397,7 @@ int pool_get_config(char *confpath, POOL_CONFIG_CONTEXT context) return(-1); } if (context == INIT_CONFIG || (context == RELOAD_CONFIG )) - { strlcpy(WD_HB_IF(slot).if_name, str, WD_MAX_IF_NAME_LEN); - pool_config->num_hb_if = slot + 1; - } } /* this must be prior to hertbeat_destination */ @@ -2419,7 +2416,10 @@ int pool_get_config(char *confpath, POOL_CONFIG_CONTEXT context) } if (context == INIT_CONFIG || (context == RELOAD_CONFIG )) + { WD_HB_IF(slot).dest_port = atoi(yytext); + pool_config->num_hb_if = slot + 1; + } } else if (!strncmp(key, "heartbeat_destination", 21) && CHECK_CONTEXT(INIT_CONFIG|RELOAD_CONFIG, context) && diff --git a/watchdog/wd_heartbeat.c b/watchdog/wd_heartbeat.c index bee5ce616..d9034c273 100644 --- a/watchdog/wd_heartbeat.c +++ b/watchdog/wd_heartbeat.c @@ -57,6 +57,7 @@ static RETSIGTYPE hb_receiver_exit(int sig); static int hton_wd_hb_packet(WdHbPacket * to, WdHbPacket * from); static int ntoh_wd_hb_packet(WdHbPacket * to, WdHbPacket * from); static int packet_to_string_hb(WdHbPacket pkt, char *str, int maxlen); +static bool is_usable_bindtodevice(void); /* create socket for sending heartbeat */ int @@ -83,8 +84,8 @@ wd_create_hb_send_socket(WdHbIf hb_if) close(sock); return -1; } -/* -#if defined(SO_BINDTODEVICE) + + if (is_usable_bindtodevice()) { struct ifreq i; strlcpy(i.ifr_name, hb_if.if_name, sizeof(i.ifr_name)); @@ -98,8 +99,9 @@ wd_create_hb_send_socket(WdHbIf hb_if) } pool_log("wd_create_hb_send_socket: bind send socket to device: %s", i.ifr_name); } -#endif -*/ + else + pool_log("wd_create_hb_send_socket: couldn't bind send socket to device: %s", hb_if.if_name); + #if defined(SO_REUSEPORT) { int one = 1; @@ -155,8 +157,8 @@ wd_create_hb_recv_socket(WdHbIf hb_if) close(sock); return -1; } -/* -#if defined(SO_BINDTODEVICE) + + if (is_usable_bindtodevice()) { struct ifreq i; strlcpy(i.ifr_name, hb_if.if_name, sizeof(i.ifr_name)); @@ -170,8 +172,8 @@ wd_create_hb_recv_socket(WdHbIf hb_if) } pool_log("wd_create_hb_recv_socket: bind receive socket to device: %s", i.ifr_name); } -#endif -*/ + else + pool_log("wd_create_hb_recv_socket: couldn't bind receive socket to device: %s", hb_if.if_name); #if defined(SO_REUSEPORT) { @@ -212,10 +214,7 @@ wd_create_hb_recv_socket(WdHbIf hb_if) if (fcntl(sock, F_SETFD, FD_CLOEXEC) < 0) { pool_error("wd_create_hb_recv_socket: setting close-on-exec flag failed. reason: %s", - strerror(errno)); - close(sock); - return -1; - } + strerror(errno)); close(sock); return -1; } return sock; } @@ -294,7 +293,8 @@ wd_hb_recv(int sock, WdHbPacket * pkt) } /* fork heartbeat receiver child */ -pid_t wd_hb_receiver(int fork_wait_time, WdHbIf hb_if) +pid_t +wd_hb_receiver(int fork_wait_time, WdHbIf hb_if) { int sock; pid_t pid = 0; @@ -397,7 +397,8 @@ pid_t wd_hb_receiver(int fork_wait_time, WdHbIf hb_if) } /* fork heartbeat sender child */ -pid_t wd_hb_sender(int fork_wait_time, WdHbIf hb_if) +pid_t +wd_hb_sender(int fork_wait_time, WdHbIf hb_if) { int sock; pid_t pid = 0; @@ -541,7 +542,8 @@ ntoh_wd_hb_packet(WdHbPacket * to, WdHbPacket * from) } /* convert packet to string and return length of the string */ -static int packet_to_string_hb(WdHbPacket pkt, char *str, int maxlen) +static int +packet_to_string_hb(WdHbPacket pkt, char *str, int maxlen) { int len; len = snprintf(str, maxlen, "status=%d tv_sec=%ld tv_usec=%ld from=%s", @@ -549,3 +551,22 @@ static int packet_to_string_hb(WdHbPacket pkt, char *str, int maxlen) return len; } + +static bool +is_usable_bindtodevice(void) +{ +#if defined(SO_BINDTODEVICE) + if (geteuid() != 0) + { + pool_log("is_usable_bindtodevice: setsockopt(SO_BINDTODEVICE) requies root privilege"); + return false; + } + else + { + return true; + } +#else + pool_log("is_usable_bindtodevice: couldn't setsockopt(SO_BINDTODEVICE) in this platform"); + return false; +#endif +}