diff options
author | Andrew Dunstan <andrew@dunslane.net> | 2007-09-12 20:49:27 +0000 |
---|---|---|
committer | Andrew Dunstan <andrew@dunslane.net> | 2007-09-12 20:49:27 +0000 |
commit | eb0a7735ba1ede6a35b80d73f6c371a8b1220552 (patch) | |
tree | b27786b01e95974689542ebe76a5daa8e2a3b9d3 /src/backend/commands/copy.c | |
parent | 22b613ebd9dc0b22820662127110ccc90e333bbe (diff) | |
download | postgresql-eb0a7735ba1ede6a35b80d73f6c371a8b1220552.tar.gz postgresql-eb0a7735ba1ede6a35b80d73f6c371a8b1220552.zip |
Perform post-escaping encoding validity checks on SQL literals and COPY input
so that invalidly encoded data cannot enter the database by these means.
Diffstat (limited to 'src/backend/commands/copy.c')
-rw-r--r-- | src/backend/commands/copy.c | 19 |
1 files changed, 17 insertions, 2 deletions
diff --git a/src/backend/commands/copy.c b/src/backend/commands/copy.c index d28a6ad11c2..fdfe5ea965f 100644 --- a/src/backend/commands/copy.c +++ b/src/backend/commands/copy.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.286 2007/09/07 20:59:26 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.287 2007/09/12 20:49:27 adunstan Exp $ * *------------------------------------------------------------------------- */ @@ -2685,6 +2685,7 @@ CopyReadAttributesText(CopyState cstate, int maxfields, char **fieldvals) char *start_ptr; char *end_ptr; int input_len; + bool saw_high_bit = false; /* Make sure space remains in fieldvals[] */ if (fieldno >= maxfields) @@ -2749,6 +2750,8 @@ CopyReadAttributesText(CopyState cstate, int maxfields, char **fieldvals) } } c = val & 0377; + if (IS_HIGHBIT_SET(c)) + saw_high_bit = true; } break; case 'x': @@ -2772,6 +2775,8 @@ CopyReadAttributesText(CopyState cstate, int maxfields, char **fieldvals) } } c = val & 0xff; + if (IS_HIGHBIT_SET(c)) + saw_high_bit = true; } } break; @@ -2799,7 +2804,7 @@ CopyReadAttributesText(CopyState cstate, int maxfields, char **fieldvals) * literally */ } - } + } /* Add c to output string */ *output_ptr++ = c; @@ -2808,6 +2813,16 @@ CopyReadAttributesText(CopyState cstate, int maxfields, char **fieldvals) /* Terminate attribute value in output area */ *output_ptr++ = '\0'; + /* If we de-escaped a char with the high bit set, make sure + * we still have valid data for the db encoding. Avoid calling strlen + * here for the sake of efficiency. + */ + if (saw_high_bit) + { + char *fld = fieldvals[fieldno]; + pg_verifymbstr(fld, output_ptr - (fld + 1), false); + } + /* Check whether raw input matched null marker */ input_len = end_ptr - start_ptr; if (input_len == cstate->null_print_len && |