redis-cli --rdb: fix broken fsync/ftruncate for stdout (#9135)
A change in redis 6.2 caused redis-cli --rdb that's directed to stdout to fail because fsync fails. This commit avoids doing ftruncate (fails with a warning) and fsync (fails with an error) when the output file is `-`, and adds the missing documentation that `-` means stdout. Co-authored-by: Oran Agra <oran@redislabs.com> Co-authored-by: Wang Yuan <wangyuancode@163.com> (cherry picked from commit 74fe15b3602ed7c003b5c53e45e31f7aa6d4a86f)
This commit is contained in:
parent
adc4748248
commit
2186c2e945
@ -1896,6 +1896,7 @@ static void usage(void) {
|
|||||||
" --lru-test <keys> Simulate a cache workload with an 80-20 distribution.\n"
|
" --lru-test <keys> Simulate a cache workload with an 80-20 distribution.\n"
|
||||||
" --replica Simulate a replica showing commands received from the master.\n"
|
" --replica Simulate a replica showing commands received from the master.\n"
|
||||||
" --rdb <filename> Transfer an RDB dump from remote server to local file.\n"
|
" --rdb <filename> Transfer an RDB dump from remote server to local file.\n"
|
||||||
|
" Use filename of \"-\" to write to stdout.\n"
|
||||||
" --pipe Transfer raw Redis protocol from stdin to server.\n"
|
" --pipe Transfer raw Redis protocol from stdin to server.\n"
|
||||||
" --pipe-timeout <n> In --pipe mode, abort with error if after sending all data.\n"
|
" --pipe-timeout <n> In --pipe mode, abort with error if after sending all data.\n"
|
||||||
" no reply is received within <n> seconds.\n"
|
" no reply is received within <n> seconds.\n"
|
||||||
@ -7154,8 +7155,9 @@ static void getRDB(clusterManagerNode *node) {
|
|||||||
payload, filename);
|
payload, filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int write_to_stdout = !strcmp(filename,"-");
|
||||||
/* Write to file. */
|
/* Write to file. */
|
||||||
if (!strcmp(filename,"-")) {
|
if (write_to_stdout) {
|
||||||
fd = STDOUT_FILENO;
|
fd = STDOUT_FILENO;
|
||||||
} else {
|
} else {
|
||||||
fd = open(filename, O_CREAT|O_WRONLY, 0644);
|
fd = open(filename, O_CREAT|O_WRONLY, 0644);
|
||||||
@ -7197,7 +7199,7 @@ static void getRDB(clusterManagerNode *node) {
|
|||||||
}
|
}
|
||||||
if (usemark) {
|
if (usemark) {
|
||||||
payload = ULLONG_MAX - payload - RDB_EOF_MARK_SIZE;
|
payload = ULLONG_MAX - payload - RDB_EOF_MARK_SIZE;
|
||||||
if (ftruncate(fd, payload) == -1)
|
if (!write_to_stdout && ftruncate(fd, payload) == -1)
|
||||||
fprintf(stderr,"ftruncate failed: %s.\n", strerror(errno));
|
fprintf(stderr,"ftruncate failed: %s.\n", strerror(errno));
|
||||||
fprintf(stderr,"Transfer finished with success after %llu bytes\n", payload);
|
fprintf(stderr,"Transfer finished with success after %llu bytes\n", payload);
|
||||||
} else {
|
} else {
|
||||||
@ -7206,7 +7208,7 @@ static void getRDB(clusterManagerNode *node) {
|
|||||||
redisFree(s); /* Close the connection ASAP as fsync() may take time. */
|
redisFree(s); /* Close the connection ASAP as fsync() may take time. */
|
||||||
if (node)
|
if (node)
|
||||||
node->context = NULL;
|
node->context = NULL;
|
||||||
if (fsync(fd) == -1) {
|
if (!write_to_stdout && fsync(fd) == -1) {
|
||||||
fprintf(stderr,"Fail to fsync '%s': %s\n", filename, strerror(errno));
|
fprintf(stderr,"Fail to fsync '%s': %s\n", filename, strerror(errno));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user