11/* -----------------------------------------------------------------------
22 * formatting.c
33 *
4- * $PostgreSQL: pgsql/src/backend/utils/adt/formatting.c,v 1.144 2008/06/26 16:06 :37teodor Exp $
4+ * $PostgreSQL: pgsql/src/backend/utils/adt/formatting.c,v 1.145 2008/07/12 00:44 :37tgl Exp $
55 *
66 *
77 * Portions Copyright (c) 1999-2008, PostgreSQL Global Development Group
@@ -945,13 +945,6 @@ static NUMCacheEntry *NUM_cache_search(char *str);
945945static NUMCacheEntry * NUM_cache_getnew (char * str );
946946static void NUM_cache_remove (NUMCacheEntry * ent );
947947
948- #ifdef USE_WIDE_UPPER_LOWER
949- /* externs are in oracle_compat.c */
950- extern char * wstring_upper (char * str );
951- extern char * wstring_lower (char * str );
952- extern wchar_t * texttowcs (const text * txt );
953- extern text * wcstotext (const wchar_t * str ,int ncodes );
954- #endif
955948
956949/* ----------
957950 * Fast sequential search, use index for data selection which
@@ -1431,14 +1424,14 @@ str_numth(char *dest, char *num, int type)
14311424 * by LC_CTYPE.
14321425 */
14331426
1434- /* ----------
1427+ /*
14351428 * wide-character-aware lower function
1429+ *
14361430 * We pass the number of bytes so we can pass varlena and char*
1437- * to this function.
1438- * ----------
1431+ * to this function. The result is a palloc'd, null-terminated string.
14391432 */
14401433char *
1441- str_tolower (char * buff ,size_t nbytes )
1434+ str_tolower (const char * buff ,size_t nbytes )
14421435{
14431436char * result ;
14441437
@@ -1479,14 +1472,14 @@ str_tolower(char *buff, size_t nbytes)
14791472return result ;
14801473}
14811474
1482- /* ----------
1475+ /*
14831476 * wide-character-aware upper function
1477+ *
14841478 * We pass the number of bytes so we can pass varlena and char*
1485- * to this function.
1486- * ----------
1479+ * to this function. The result is a palloc'd, null-terminated string.
14871480 */
14881481char *
1489- str_toupper (char * buff ,size_t nbytes )
1482+ str_toupper (const char * buff ,size_t nbytes )
14901483{
14911484char * result ;
14921485
@@ -1527,14 +1520,14 @@ str_toupper(char *buff, size_t nbytes)
15271520return result ;
15281521}
15291522
1530- /* ----------
1523+ /*
15311524 * wide-character-aware initcap function
1525+ *
15321526 * We pass the number of bytes so we can pass varlena and char*
1533- * to this function.
1534- * ----------
1527+ * to this function. The result is a palloc'd, null-terminated string.
15351528 */
15361529char *
1537- str_initcap (char * buff ,size_t nbytes )
1530+ str_initcap (const char * buff ,size_t nbytes )
15381531{
15391532char * result ;
15401533bool wasalnum = false;
@@ -1588,6 +1581,27 @@ str_initcap(char *buff, size_t nbytes)
15881581return result ;
15891582}
15901583
1584+ /* convenience routines for when the input is null-terminated */
1585+
1586+ static char *
1587+ str_tolower_z (const char * buff )
1588+ {
1589+ return str_tolower (buff ,strlen (buff ));
1590+ }
1591+
1592+ static char *
1593+ str_toupper_z (const char * buff )
1594+ {
1595+ return str_toupper (buff ,strlen (buff ));
1596+ }
1597+
1598+ static char *
1599+ str_initcap_z (const char * buff )
1600+ {
1601+ return str_initcap (buff ,strlen (buff ));
1602+ }
1603+
1604+
15911605/* ----------
15921606 * Sequential search with to upper/lower conversion
15931607 * ----------
@@ -1791,8 +1805,7 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
17911805FormatNode * n ;
17921806char * s ;
17931807struct pg_tm * tm = & in -> tm ;
1794- char buff [DCH_CACHE_SIZE ],
1795- workbuff [32 ];
1808+ char buff [DCH_CACHE_SIZE ];
17961809int i ;
17971810
17981811/* cache localized days and months */
@@ -1895,9 +1908,9 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
18951908INVALID_FOR_INTERVAL ;
18961909if (tmtcTzn (in ))
18971910{
1898- char * p = pstrdup (tmtcTzn (in ));
1911+ char * p = str_tolower_z (tmtcTzn (in ));
18991912
1900- strcpy (s ,str_tolower ( p , strlen ( p )) );
1913+ strcpy (s ,p );
19011914pfree (p );
19021915s += strlen (s );
19031916}
@@ -1939,23 +1952,18 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
19391952if (!tm -> tm_mon )
19401953break ;
19411954if (S_TM (n -> suffix ))
1942- strcpy (s ,str_toupper (localized_full_months [tm -> tm_mon - 1 ],
1943- strlen (localized_full_months [tm -> tm_mon - 1 ])));
1955+ strcpy (s ,str_toupper_z (localized_full_months [tm -> tm_mon - 1 ]));
19441956else
1945- {
1946- strcpy (workbuff ,months_full [tm -> tm_mon - 1 ]);
19471957sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,
1948- str_toupper (workbuff ,strlen (workbuff )));
1949- }
1958+ str_toupper_z (months_full [tm -> tm_mon - 1 ]));
19501959s += strlen (s );
19511960break ;
19521961case DCH_Month :
19531962INVALID_FOR_INTERVAL ;
19541963if (!tm -> tm_mon )
19551964break ;
19561965if (S_TM (n -> suffix ))
1957- strcpy (s ,str_initcap (localized_full_months [tm -> tm_mon - 1 ],
1958- strlen (localized_full_months [tm -> tm_mon - 1 ])));
1966+ strcpy (s ,str_initcap_z (localized_full_months [tm -> tm_mon - 1 ]));
19591967else
19601968sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,months_full [tm -> tm_mon - 1 ]);
19611969s += strlen (s );
@@ -1965,8 +1973,7 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
19651973if (!tm -> tm_mon )
19661974break ;
19671975if (S_TM (n -> suffix ))
1968- strcpy (s ,str_tolower (localized_full_months [tm -> tm_mon - 1 ],
1969- strlen (localized_full_months [tm -> tm_mon - 1 ])));
1976+ strcpy (s ,str_tolower_z (localized_full_months [tm -> tm_mon - 1 ]));
19701977else
19711978{
19721979sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,months_full [tm -> tm_mon - 1 ]);
@@ -1979,20 +1986,17 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
19791986if (!tm -> tm_mon )
19801987break ;
19811988if (S_TM (n -> suffix ))
1982- strcpy (s ,str_toupper (localized_abbrev_months [tm -> tm_mon - 1 ],
1983- strlen (localized_abbrev_months [tm -> tm_mon - 1 ])));
1989+ strcpy (s ,str_toupper_z (localized_abbrev_months [tm -> tm_mon - 1 ]));
19841990else
1985- strcpy (s ,str_toupper (months [tm -> tm_mon - 1 ],
1986- strlen (months [tm -> tm_mon - 1 ])));
1991+ strcpy (s ,str_toupper_z (months [tm -> tm_mon - 1 ]));
19871992s += strlen (s );
19881993break ;
19891994case DCH_Mon :
19901995INVALID_FOR_INTERVAL ;
19911996if (!tm -> tm_mon )
19921997break ;
19931998if (S_TM (n -> suffix ))
1994- strcpy (s ,str_initcap (localized_abbrev_months [tm -> tm_mon - 1 ],
1995- strlen (localized_abbrev_months [tm -> tm_mon - 1 ])));
1999+ strcpy (s ,str_initcap_z (localized_abbrev_months [tm -> tm_mon - 1 ]));
19962000else
19972001strcpy (s ,months [tm -> tm_mon - 1 ]);
19982002s += strlen (s );
@@ -2002,8 +2006,7 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
20022006if (!tm -> tm_mon )
20032007break ;
20042008if (S_TM (n -> suffix ))
2005- strcpy (s ,str_tolower (localized_abbrev_months [tm -> tm_mon - 1 ],
2006- strlen (localized_abbrev_months [tm -> tm_mon - 1 ])));
2009+ strcpy (s ,str_tolower_z (localized_abbrev_months [tm -> tm_mon - 1 ]));
20072010else
20082011{
20092012strcpy (s ,months [tm -> tm_mon - 1 ]);
@@ -2020,30 +2023,24 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
20202023case DCH_DAY :
20212024INVALID_FOR_INTERVAL ;
20222025if (S_TM (n -> suffix ))
2023- strcpy (s ,str_toupper (localized_full_days [tm -> tm_wday ],
2024- strlen (localized_full_days [tm -> tm_wday ])));
2026+ strcpy (s ,str_toupper_z (localized_full_days [tm -> tm_wday ]));
20252027else
2026- {
2027- strcpy (workbuff ,days [tm -> tm_wday ]);
20282028sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,
2029- str_toupper (workbuff ,strlen (workbuff )));
2030- }
2029+ str_toupper_z (days [tm -> tm_wday ]));
20312030s += strlen (s );
20322031break ;
20332032case DCH_Day :
20342033INVALID_FOR_INTERVAL ;
20352034if (S_TM (n -> suffix ))
2036- strcpy (s ,str_initcap (localized_full_days [tm -> tm_wday ],
2037- strlen (localized_full_days [tm -> tm_wday ])));
2035+ strcpy (s ,str_initcap_z (localized_full_days [tm -> tm_wday ]));
20382036else
20392037sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,days [tm -> tm_wday ]);
20402038s += strlen (s );
20412039break ;
20422040case DCH_day :
20432041INVALID_FOR_INTERVAL ;
20442042if (S_TM (n -> suffix ))
2045- strcpy (s ,str_tolower (localized_full_days [tm -> tm_wday ],
2046- strlen (localized_full_days [tm -> tm_wday ])));
2043+ strcpy (s ,str_tolower_z (localized_full_days [tm -> tm_wday ]));
20472044else
20482045{
20492046sprintf (s ,"%*s" ,S_FM (n -> suffix ) ?0 :-9 ,days [tm -> tm_wday ]);
@@ -2054,27 +2051,23 @@ DCH_to_char(FormatNode *node, bool is_interval, TmToChar *in, char *out)
20542051case DCH_DY :
20552052INVALID_FOR_INTERVAL ;
20562053if (S_TM (n -> suffix ))
2057- strcpy (s ,str_toupper (localized_abbrev_days [tm -> tm_wday ],
2058- strlen (localized_abbrev_days [tm -> tm_wday ])));
2054+ strcpy (s ,str_toupper_z (localized_abbrev_days [tm -> tm_wday ]));
20592055else
2060- strcpy (s ,str_toupper (days_short [tm -> tm_wday ],
2061- strlen (days_short [tm -> tm_wday ])));
2056+ strcpy (s ,str_toupper_z (days_short [tm -> tm_wday ]));
20622057s += strlen (s );
20632058break ;
20642059case DCH_Dy :
20652060INVALID_FOR_INTERVAL ;
20662061if (S_TM (n -> suffix ))
2067- strcpy (s ,str_initcap (localized_abbrev_days [tm -> tm_wday ],
2068- strlen (localized_abbrev_days [tm -> tm_wday ])));
2062+ strcpy (s ,str_initcap_z (localized_abbrev_days [tm -> tm_wday ]));
20692063else
20702064strcpy (s ,days_short [tm -> tm_wday ]);
20712065s += strlen (s );
20722066break ;
20732067case DCH_dy :
20742068INVALID_FOR_INTERVAL ;
20752069if (S_TM (n -> suffix ))
2076- strcpy (s ,str_tolower (localized_abbrev_days [tm -> tm_wday ],
2077- strlen (localized_abbrev_days [tm -> tm_wday ])));
2070+ strcpy (s ,str_tolower_z (localized_abbrev_days [tm -> tm_wday ]));
20782071else
20792072{
20802073strcpy (s ,days_short [tm -> tm_wday ]);
@@ -4339,14 +4332,12 @@ NUM_processor(FormatNode *node, NUMDesc *Num, char *inout, char *number,
43394332case NUM_rn :
43404333if (IS_FILLMODE (Np -> Num ))
43414334{
4342- strcpy (Np -> inout_p ,str_tolower (Np -> number_p ,
4343- strlen (Np -> number_p )));
4335+ strcpy (Np -> inout_p ,str_tolower_z (Np -> number_p ));
43444336Np -> inout_p += strlen (Np -> inout_p )- 1 ;
43454337}
43464338else
43474339{
4348- sprintf (Np -> inout_p ,"%15s" ,str_tolower (Np -> number_p ,
4349- strlen (Np -> number_p )));
4340+ sprintf (Np -> inout_p ,"%15s" ,str_tolower_z (Np -> number_p ));
43504341Np -> inout_p += strlen (Np -> inout_p )- 1 ;
43514342}
43524343break ;