summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLorna Luo <lornaluo@amazon.com>2023-03-13 17:27:28 -0400
committerSergei Golubchik <vuvova@gmail.com>2023-04-03 14:36:11 +0200
commitda73db2382d6cfaaa74fe5c37e7df18aa2d44238 (patch)
treebe14bccd2254dc85091614f1812b20e2eb49e18d
parent0a6343909fcf8b193a1b517b3a16eabd4ae89a83 (diff)
downloadmariadb-git-da73db2382d6cfaaa74fe5c37e7df18aa2d44238.tar.gz
Make 'move_file' command more reliable in mysqltest
The tests innodb.import_tablespace_race, innodn.restart, and innodb.innodb-wl5522 move the tablespace file between the data directory and the tmp directory specified by global environment variables. However this is risky because it's not unusual that the set tmp directory (often under /tmp) is mounted on another disk partition or device, and 'move_file' command may fail with "Errcode: 18 'Invalid cross-device link.'" To stabilize mysqltest in the described scenario, and prevent such behavior in the future, let make_file() check both from file path and to file path and make sure they are either both under MYSQLTEST_VARDIR or MYSQL_TMP_DIR. All new code of the whole pull request, including one or several files that are either new files or modified ones, are contributed under the BSD-new license. I am contributing on behalf of my employer Amazon Web Services, Inc.
-rw-r--r--client/mysqltest.cc16
1 files changed, 14 insertions, 2 deletions
diff --git a/client/mysqltest.cc b/client/mysqltest.cc
index 214b7542374..6330d4f881d 100644
--- a/client/mysqltest.cc
+++ b/client/mysqltest.cc
@@ -3814,9 +3814,21 @@ void do_move_file(struct st_command *command)
sizeof(move_file_args)/sizeof(struct command_arg),
' ');
- if (bad_path(ds_to_file.str))
- DBUG_VOID_RETURN;
+ size_t from_plen = strlen(ds_from_file.str);
+ size_t to_plen = strlen(ds_to_file.str);
+ const char *vardir= getenv("MYSQLTEST_VARDIR");
+ const char *tmpdir= getenv("MYSQL_TMP_DIR");
+ if (!((is_sub_path(ds_from_file.str, from_plen, vardir) &&
+ is_sub_path(ds_to_file.str, to_plen, vardir)) ||
+ (is_sub_path(ds_from_file.str, from_plen, tmpdir) &&
+ is_sub_path(ds_to_file.str, to_plen, tmpdir)))) {
+ report_or_die("Paths '%s' and '%s' are not both under MYSQLTEST_VARDIR '%s'"
+ "or both under MYSQL_TMP_DIR '%s'",
+ ds_from_file, ds_to_file, vardir, tmpdir);
+ DBUG_VOID_RETURN;
+ }
+
DBUG_PRINT("info", ("Move %s to %s", ds_from_file.str, ds_to_file.str));
error= (my_rename(ds_from_file.str, ds_to_file.str,
MYF(disable_warnings ? 0 : MY_WME)) != 0);