Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit 16adaf1

Browse files
committed
Swap the order of testing for control characters and for column delimiter in
CopyAttributeOutText(), so that control characters are converted to the C-style escape sequences even if they happen to be equal to the column delimiter (as is true by default for tab, for example). Oversight in my previous patch to restore pre-8.3 behavior of COPY OUT escaping. Per report from Tomas Szepe.
1 parent f5f1355 commit 16adaf1

File tree

1 file changed

+21
-15
lines changed

1 file changed

+21
-15
lines changed

src/backend/commands/copy.c

+21-15
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
*
99
*
1010
* IDENTIFICATION
11-
* $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.290 2007/12/03 00:03:05 tgl Exp $
11+
* $PostgreSQL: pgsql/src/backend/commands/copy.c,v 1.291 2007/12/27 16:45:22 tgl Exp $
1212
*
1313
*-------------------------------------------------------------------------
1414
*/
@@ -3094,13 +3094,7 @@ CopyAttributeOutText(CopyState cstate, char *string)
30943094
start = ptr;
30953095
while ((c = *ptr) != '\0')
30963096
{
3097-
if (c == '\\' || c == delimc)
3098-
{
3099-
DUMPSOFAR();
3100-
CopySendChar(cstate, '\\');
3101-
start = ptr++; /* we include char in next run */
3102-
}
3103-
else if ((unsigned char) c < (unsigned char) 0x20)
3097+
if ((unsigned char) c < (unsigned char) 0x20)
31043098
{
31053099
/*
31063100
* \r and \n must be escaped, the others are traditional.
@@ -3130,6 +3124,9 @@ CopyAttributeOutText(CopyState cstate, char *string)
31303124
c = 'v';
31313125
break;
31323126
default:
3127+
/* If it's the delimiter, must backslash it */
3128+
if (c == delimc)
3129+
break;
31333130
/* All ASCII control chars are length 1 */
31343131
ptr++;
31353132
continue; /* fall to end of loop */
@@ -3140,6 +3137,12 @@ CopyAttributeOutText(CopyState cstate, char *string)
31403137
CopySendChar(cstate, c);
31413138
start = ++ptr; /* do not include char in next run */
31423139
}
3140+
else if (c == '\\' || c == delimc)
3141+
{
3142+
DUMPSOFAR();
3143+
CopySendChar(cstate, '\\');
3144+
start = ptr++; /* we include char in next run */
3145+
}
31433146
else if (IS_HIGHBIT_SET(c))
31443147
ptr += pg_encoding_mblen(cstate->client_encoding, ptr);
31453148
else
@@ -3151,13 +3154,7 @@ CopyAttributeOutText(CopyState cstate, char *string)
31513154
start = ptr;
31523155
while ((c = *ptr) != '\0')
31533156
{
3154-
if (c == '\\' || c == delimc)
3155-
{
3156-
DUMPSOFAR();
3157-
CopySendChar(cstate, '\\');
3158-
start = ptr++; /* we include char in next run */
3159-
}
3160-
else if ((unsigned char) c < (unsigned char) 0x20)
3157+
if ((unsigned char) c < (unsigned char) 0x20)
31613158
{
31623159
/*
31633160
* \r and \n must be escaped, the others are traditional.
@@ -3187,6 +3184,9 @@ CopyAttributeOutText(CopyState cstate, char *string)
31873184
c = 'v';
31883185
break;
31893186
default:
3187+
/* If it's the delimiter, must backslash it */
3188+
if (c == delimc)
3189+
break;
31903190
/* All ASCII control chars are length 1 */
31913191
ptr++;
31923192
continue; /* fall to end of loop */
@@ -3197,6 +3197,12 @@ CopyAttributeOutText(CopyState cstate, char *string)
31973197
CopySendChar(cstate, c);
31983198
start = ++ptr; /* do not include char in next run */
31993199
}
3200+
else if (c == '\\' || c == delimc)
3201+
{
3202+
DUMPSOFAR();
3203+
CopySendChar(cstate, '\\');
3204+
start = ptr++; /* we include char in next run */
3205+
}
32003206
else
32013207
ptr++;
32023208
}

0 commit comments

Comments
 (0)