Fix "pgpool reset" command not working if watchdog is enabled.
authorTatsuo Ishii <ishii@sraoss.co.jp>
Mon, 10 Jun 2024 02:23:47 +0000 (11:23 +0900)
committerTatsuo Ishii <ishii@sraoss.co.jp>
Mon, 10 Jun 2024 04:30:10 +0000 (13:30 +0900)
[pgpool-hackers: 4465] abnormal behavior about PGPOOL RESET. and proposal a patch file.
reported that "pgpool reset" command fails if watchdog is enabled.

test=# PGPOOL RESET client_idle_limit;
SET
ERROR: Pgpool node id file �y/pgpool_node_id does not exist
DETAIL: If watchdog is enable, pgpool_node_id file is required
message type 0x5a arrived from server while idle
message type 0x43 arrived from server while idle
message type 0x5a arrived from server while idle

SetPgpoolNodeId() tried to obtain the path to the node id file by
using global variable config_file_dir and failed because it points to
an automatic variable in ParseConfigFile().

To fix this, change the config_file_dir from a pointer to an array and
save the path string into config_file_dir in ParseConfigFile().

Also regression test is added to 004.watchdog.

Bug reported and problem analysis by keiseo.

Back patch to V4.2 in which the node id file was introduced.

src/config/pool_config.l
src/include/pool_config.h
src/test/regression/tests/004.watchdog/test.sh

index 3be304beaf4e181e900bb8c92963f91b6d5c2539..2eef2ed116d43bb83ae57bac385398672aae7fd4 100644 (file)
@@ -45,7 +45,7 @@ int yylex(void);
 POOL_CONFIG g_pool_config;     /* configuration values */
 POOL_CONFIG *pool_config = &g_pool_config;     /* for legacy reason pointer to the above struct */
 static unsigned Lineno;
-char   *config_file_dir = NULL; /* directory path of config file pgpool.conf */
+char   config_file_dir[POOLMAXPATHLEN + 1];    /* directory path of config file pgpool.conf */
 
 typedef enum {
   POOL_KEY = 1,
@@ -354,7 +354,7 @@ ParseConfigFile(const char *config_file, const char *calling_file,
                /* get directory path of config file pgpool.conf */
                strlcpy(buf, config_file, sizeof(buf));
                get_parent_directory(buf);
-               config_file_dir = buf;
+               strlcpy(config_file_dir, buf, sizeof(config_file_dir));
        }
 
 
index a2a3f0414db9366df7894f4dd1f8bd2d79402b0f..7782d50c428943fe7e1c15a5f9bf247ecd2fc067 100644 (file)
@@ -6,7 +6,7 @@
  * pgpool: a language independent connection pool server for PostgreSQL
  * written by Tatsuo Ishii
  *
- * Copyright (c) 2003-2023     PgPool Global Development Group
+ * Copyright (c) 2003-2024     PgPool Global Development Group
  *
  * Permission to use, copy, modify, and distribute this software and
  * its documentation for any purpose and without fee is hereby
@@ -644,7 +644,7 @@ typedef struct
 }                      POOL_CONFIG;
 
 extern POOL_CONFIG * pool_config;
-extern char *config_file_dir; /* directory path of config file pgpool.conf */
+extern char config_file_dir[]; /* directory path of config file pgpool.conf */
 
 typedef enum
 {
index 71490857d03df45a00a5dfba7f5c8a2246891317..21c90cf43120ef8b65f4ec04dc872111e02bc978 100755 (executable)
@@ -4,6 +4,7 @@
 source $TESTLIBS
 LEADER_DIR=leader
 STANDBY_DIR=standby
+PSQL=$PGBIN/psql
 success_count=0
 
 rm -fr $LEADER_DIR
@@ -76,6 +77,18 @@ do
        sleep 2
 done
 
+# at this point the watchdog leader and stabdby are working.
+# check to see if "pgpool reset" command works.
+echo "Check pgpool reset command..."
+for i in 11000 11100
+do
+    echo "Check pgpool reset command on port $i..."
+    $PSQL -p $i -c "pgpool reset client_idle_limit" test
+    if [ $? = 0 ];then
+       success_count=$(( success_count + 1 ))
+    fi
+done
+
 # step 2 stop leader pgpool and see if standby take over
 $PGPOOL_INSTALL_DIR/bin/pgpool -f $LEADER_DIR/etc/pgpool.conf -m f stop
 
@@ -112,9 +125,9 @@ $PGPOOL_INSTALL_DIR/bin/pgpool -f $STANDBY_DIR/etc/pgpool.conf -m f stop
 cd leader
 ./shutdownall
 
-echo "$success_count out of 4 successful";
+echo "$success_count out of 6 successful";
 
-if test $success_count -eq 4
+if test $success_count -eq 6
 then
     exit 0
 fi