aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorTom Lane <tgl@sss.pgh.pa.us>2005-03-26 00:42:21 +0000
committerTom Lane <tgl@sss.pgh.pa.us>2005-03-26 00:42:21 +0000
commit12fa5c57acd845096247c7e0d9a78c61d169598f (patch)
tree5b17a08f68f6e7d999702b96da47181119364658 /src
parent3e65431bc1a722c5d7e1a7598f3b18f9b3224ace (diff)
downloadpostgresql-12fa5c57acd845096247c7e0d9a78c61d169598f.tar.gz
postgresql-12fa5c57acd845096247c7e0d9a78c61d169598f.zip
Prevent to_char(interval) from dumping core on month-related formats
when a zero-month interval is given. Per discussion with Karel.
Diffstat (limited to 'src')
-rw-r--r--src/backend/utils/adt/formatting.c32
1 files changed, 24 insertions, 8 deletions
diff --git a/src/backend/utils/adt/formatting.c b/src/backend/utils/adt/formatting.c
index 727d0f86dfa..9066776862f 100644
--- a/src/backend/utils/adt/formatting.c
+++ b/src/backend/utils/adt/formatting.c
@@ -1,7 +1,7 @@
/* -----------------------------------------------------------------------
* formatting.c
*
- * $Header: /cvsroot/pgsql/src/backend/utils/adt/formatting.c,v 1.69 2003/09/29 00:05:25 petere Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/formatting.c,v 1.69.2.1 2005/03/26 00:42:21 tgl Exp $
*
*
* Portions Copyright (c) 1999-2003, PostgreSQL Global Development Group
@@ -2038,6 +2038,7 @@ static int
dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
{
char buff[DCH_CACHE_SIZE],
+ workbuff[32],
*p_inout;
int i,
len;
@@ -2160,14 +2161,18 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
}
break;
case DCH_MONTH:
- strcpy(inout, months_full[tm->tm_mon - 1]);
- sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, str_toupper(inout));
+ if (!tm->tm_mon)
+ return -1;
+ strcpy(workbuff, months_full[tm->tm_mon - 1]);
+ sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, str_toupper(workbuff));
if (S_FM(suf))
return strlen(p_inout) - 1;
else
return 8;
case DCH_Month:
+ if (!tm->tm_mon)
+ return -1;
sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, months_full[tm->tm_mon - 1]);
if (S_FM(suf))
return strlen(p_inout) - 1;
@@ -2175,6 +2180,8 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
return 8;
case DCH_month:
+ if (!tm->tm_mon)
+ return -1;
sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, months_full[tm->tm_mon - 1]);
*inout = tolower((unsigned char) *inout);
if (S_FM(suf))
@@ -2183,15 +2190,21 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
return 8;
case DCH_MON:
+ if (!tm->tm_mon)
+ return -1;
strcpy(inout, months[tm->tm_mon - 1]);
inout = str_toupper(inout);
return 2;
case DCH_Mon:
+ if (!tm->tm_mon)
+ return -1;
strcpy(inout, months[tm->tm_mon - 1]);
return 2;
case DCH_mon:
+ if (!tm->tm_mon)
+ return -1;
strcpy(inout, months[tm->tm_mon - 1]);
*inout = tolower((unsigned char) *inout);
return 2;
@@ -2206,7 +2219,6 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
return strlen(p_inout) - 1;
else
return 1;
-
}
else if (flag == FROM_CHAR)
{
@@ -2223,8 +2235,8 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
}
break;
case DCH_DAY:
- strcpy(inout, days[tm->tm_wday]);
- sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, str_toupper(inout));
+ strcpy(workbuff, days[tm->tm_wday]);
+ sprintf(inout, "%*s", S_FM(suf) ? 0 : -9, str_toupper(workbuff));
if (S_FM(suf))
return strlen(p_inout) - 1;
else
@@ -2366,7 +2378,6 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
return strlen(p_inout) - 1;
else
return 1;
-
}
else if (flag == FROM_CHAR)
{
@@ -2385,6 +2396,8 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
case DCH_Q:
if (flag == TO_CHAR)
{
+ if (!tm->tm_mon)
+ return -1;
sprintf(inout, "%d", (tm->tm_mon - 1) / 3 + 1);
if (S_THth(suf))
{
@@ -2392,7 +2405,6 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
return 2;
}
return 0;
-
}
else if (flag == FROM_CHAR)
{
@@ -2560,6 +2572,8 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
case DCH_RM:
if (flag == TO_CHAR)
{
+ if (!tm->tm_mon)
+ return -1;
sprintf(inout, "%*s", S_FM(suf) ? 0 : -4,
rm_months_upper[12 - tm->tm_mon]);
if (S_FM(suf))
@@ -2581,6 +2595,8 @@ dch_date(int arg, char *inout, int suf, int flag, FormatNode *node, void *data)
case DCH_rm:
if (flag == TO_CHAR)
{
+ if (!tm->tm_mon)
+ return -1;
sprintf(inout, "%*s", S_FM(suf) ? 0 : -4,
rm_months_lower[12 - tm->tm_mon]);
if (S_FM(suf))