v1-0001-pg_dump-Fix-incorrect-parsing-of-object-types-in-.patch
application/octet-stream
Filename: v1-0001-pg_dump-Fix-incorrect-parsing-of-object-types-in-.patch
Type: application/octet-stream
Part: 0
Patch
Format: format-patch
Series: patch v1-0001
Subject: pg_dump: Fix incorrect parsing of object types in pg_dump --filter.
| File | + | − |
|---|---|---|
| src/bin/pg_dump/filter.c | 15 | 11 |
| src/bin/pg_dump/t/005_pg_dump_filterfile.pl | 10 | 4 |
From ed6f7a0586f79179d12365c258531c726b2cf556 Mon Sep 17 00:00:00 2001
From: Fujii Masao <fujii@postgresql.org>
Date: Sat, 2 Aug 2025 16:15:37 +0900
Subject: [PATCH v1] pg_dump: Fix incorrect parsing of object types in pg_dump
--filter.
Previously, pg_dump --filter could misinterpret invalid object types
in the filter file as valid ones. For example, the invalid object type
"table-data" (likely a typo for the valid "table_data") could be
mistakenly recognized as "table", causing pg_dump to succeed
when it should have failed.
This happened because pg_dump identified tokens as sequences of
ASCII alphabetic characters, treating non-alphabetic characters
(like hyphens) as token boundaries. As a result, "table-data" was
parsed as "table".
To fix this, pg_dump --filter now treats tokens as strings of
non-space characters separated by spaces or line endings,
ensuring invalid types like "table-data" are correctly rejected.
Back-patch to v17, where the --filter option was introduced.
---
src/bin/pg_dump/filter.c | 26 ++++++++++++---------
src/bin/pg_dump/t/005_pg_dump_filterfile.pl | 14 +++++++----
2 files changed, 25 insertions(+), 15 deletions(-)
diff --git a/src/bin/pg_dump/filter.c b/src/bin/pg_dump/filter.c
index 7214d514137..71b4bd9a73a 100644
--- a/src/bin/pg_dump/filter.c
+++ b/src/bin/pg_dump/filter.c
@@ -169,31 +169,35 @@ pg_log_filter_error(FilterStateData *fstate, const char *fmt,...)
}
/*
- * filter_get_keyword - read the next filter keyword from buffer
+ * filter_get_token - read the next filter token from buffer
*
- * Search for keywords (limited to ascii alphabetic characters) in
- * the passed in line buffer. Returns NULL when the buffer is empty or the first
- * char is not alpha. The char '_' is allowed, except as the first character.
+ * Search for tokens (strings of non-space characters bounded by
+ * space characters or end of line) in the passed in line buffer.
+ * Returns NULL when the buffer is empty or no token exists.
* The length of the found keyword is returned in the size parameter.
*/
static const char *
-filter_get_keyword(const char **line, int *size)
+filter_get_token(const char **line, int *size)
{
const char *ptr = *line;
const char *result = NULL;
- /* Set returned length preemptively in case no keyword is found */
+ /* Set returned length preemptively in case no token is found */
*size = 0;
- /* Skip initial whitespace */
+ /* Skip initial space characters */
while (isspace((unsigned char) *ptr))
ptr++;
- if (isalpha((unsigned char) *ptr))
+ /*
+ * Grab one token that's the string of non-space characters bounded by
+ * space characters or end of line.
+ */
+ if (*ptr != '\0' && !isspace((unsigned char) *ptr))
{
result = ptr++;
- while (isalpha((unsigned char) *ptr) || *ptr == '_')
+ while (*ptr != '\0' && !isspace((unsigned char) *ptr))
ptr++;
*size = ptr - result;
@@ -414,7 +418,7 @@ filter_read_item(FilterStateData *fstate,
* First we expect sequence of two keywords, {include|exclude}
* followed by the object type to operate on.
*/
- keyword = filter_get_keyword(&str, &size);
+ keyword = filter_get_token(&str, &size);
if (!keyword)
{
pg_log_filter_error(fstate,
@@ -433,7 +437,7 @@ filter_read_item(FilterStateData *fstate,
fstate->exit_nicely(1);
}
- keyword = filter_get_keyword(&str, &size);
+ keyword = filter_get_token(&str, &size);
if (!keyword)
{
pg_log_filter_error(fstate, _("missing filter object type"));
diff --git a/src/bin/pg_dump/t/005_pg_dump_filterfile.pl b/src/bin/pg_dump/t/005_pg_dump_filterfile.pl
index f05e8a20e05..d788406add4 100644
--- a/src/bin/pg_dump/t/005_pg_dump_filterfile.pl
+++ b/src/bin/pg_dump/t/005_pg_dump_filterfile.pl
@@ -418,10 +418,16 @@ command_fails_like(
qr/invalid filter command/,
"invalid syntax: incorrect filter command");
-# Test invalid object type
+# Test invalid object type.
+#
+# This test also verifies that tokens are correctly recognized as sequences of
+# non-space characters separated by spaces or line endings. If the parser
+# incorrectly treats non-space delimiters (like hyphens) as token boundaries,
+# "table-data" might be misread as the valid object type "table". To catch such
+# issues, "table-data" is used here as an intentionally invalid object type.
open $inputfile, '>', "$tempdir/inputfile.txt"
or die "unable to open filterfile for writing";
-print $inputfile "include xxx";
+print $inputfile "exclude table-data one";
close $inputfile;
command_fails_like(
@@ -432,8 +438,8 @@ command_fails_like(
'--filter' => "$tempdir/inputfile.txt",
'postgres'
],
- qr/unsupported filter object type: "xxx"/,
- "invalid syntax: invalid object type specified, should be table, schema, foreign_data or data"
+ qr/unsupported filter object type: "table-data"/,
+ "invalid syntax: invalid object type specified"
);
# Test missing object identifier pattern
--
2.50.1