aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xconfigure39
-rw-r--r--configure.in12
-rw-r--r--doc/src/sgml/charset.sgml131
-rw-r--r--doc/src/sgml/datatype.sgml10
-rw-r--r--doc/src/sgml/installation.sgml13
-rw-r--r--doc/src/sgml/ref/initdb.sgml54
-rw-r--r--doc/src/sgml/release.sgml3
-rw-r--r--doc/src/sgml/runtime.sgml98
-rw-r--r--src/backend/access/transam/xlog.c22
-rw-r--r--src/backend/main/main.c36
-rw-r--r--src/backend/utils/adt/cash.c28
-rw-r--r--src/backend/utils/adt/formatting.c12
-rw-r--r--src/backend/utils/adt/pg_locale.c223
-rw-r--r--src/backend/utils/adt/selfuncs.c87
-rw-r--r--src/backend/utils/adt/varlena.c48
-rw-r--r--src/backend/utils/misc/guc.c23
-rw-r--r--src/bin/initdb/initdb.sh103
-rw-r--r--src/include/pg_config.h.in5
-rw-r--r--src/include/utils/pg_locale.h64
19 files changed, 543 insertions, 468 deletions
diff --git a/configure b/configure
index 17e1db1e3e8..01c0a9d9467 100755
--- a/configure
+++ b/configure
@@ -845,7 +845,6 @@ if test -n "$ac_init_help"; then
Optional Features:
--disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no)
--enable-FEATURE[=ARG] include FEATURE [ARG=yes]
- --enable-locale enable locale support
--enable-recode enable character set recode support
--enable-multibyte enable multibyte character support
--enable-nls[=LANGUAGES] enable Native Language Support
@@ -1571,44 +1570,6 @@ fi;
#
-# Locale (--enable-locale)
-#
-echo "$as_me:$LINENO: checking whether to build with locale support" >&5
-echo $ECHO_N "checking whether to build with locale support... $ECHO_C" >&6
-
-
-# Check whether --enable-locale or --disable-locale was given.
-if test "${enable_locale+set}" = set; then
- enableval="$enable_locale"
-
- case $enableval in
- yes)
-
-cat >>confdefs.h <<\_ACEOF
-#define USE_LOCALE 1
-_ACEOF
-
- ;;
- no)
- :
- ;;
- *)
- { { echo "$as_me:$LINENO: error: no argument expected for --enable-locale option" >&5
-echo "$as_me: error: no argument expected for --enable-locale option" >&2;}
- { (exit 1); exit 1; }; }
- ;;
- esac
-
-else
- enable_locale=no
-
-fi;
-
-echo "$as_me:$LINENO: result: $enable_locale" >&5
-echo "${ECHO_T}$enable_locale" >&6
-
-
-#
# Character set recode (--enable-recode)
#
echo "$as_me:$LINENO: checking whether to build with recode support" >&5
diff --git a/configure.in b/configure.in
index 1d5a3703f9c..7fbf76e32b4 100644
--- a/configure.in
+++ b/configure.in
@@ -1,5 +1,5 @@
dnl Process this file with autoconf to produce a configure script.
-dnl $Header: /cvsroot/pgsql/configure.in,v 1.174 2002/04/01 01:11:00 tgl Exp $
+dnl $Header: /cvsroot/pgsql/configure.in,v 1.175 2002/04/03 05:39:27 petere Exp $
dnl Developers, please strive to achieve this order:
dnl
@@ -141,16 +141,6 @@ PGAC_ARG_REQ(with, libs, [ --with-libs=DIRS alternative spelling of
#
-# Locale (--enable-locale)
-#
-AC_MSG_CHECKING([whether to build with locale support])
-PGAC_ARG_BOOL(enable, locale, no, [ --enable-locale enable locale support],
- [AC_DEFINE([USE_LOCALE], 1,
- [Set to 1 if you want LOCALE support (--enable-locale)])])
-AC_MSG_RESULT([$enable_locale])
-
-
-#
# Character set recode (--enable-recode)
#
AC_MSG_CHECKING([whether to build with recode support])
diff --git a/doc/src/sgml/charset.sgml b/doc/src/sgml/charset.sgml
index 29cc7e528ef..a19940ce9a6 100644
--- a/doc/src/sgml/charset.sgml
+++ b/doc/src/sgml/charset.sgml
@@ -1,4 +1,4 @@
-<!-- $Header: /cvsroot/pgsql/doc/src/sgml/charset.sgml,v 2.23 2002/03/22 19:20:05 petere Exp $ -->
+<!-- $Header: /cvsroot/pgsql/doc/src/sgml/charset.sgml,v 2.24 2002/04/03 05:39:27 petere Exp $ -->
<chapter id="charset">
<title>Localization</>
@@ -63,35 +63,24 @@
<sect2>
<title>Overview</>
- <para>
- Locale support is not built into <productname>PostgreSQL</> by
- default; to enable it, supply the <option>--enable-locale</> option
- to the <filename>configure</> script:
-<informalexample>
+ <para>
+ Locale support is automatically initialized when a database
+ cluster is created using <command>initdb</command>.
+ <command>initdb</command> will initialize the database cluster
+ with the locale setting of its execution environment; so if your
+ system is already set to use the locale that you want in your
+ database cluster then there is nothing else you need to do. If
+ you want to use a different locale (or you are not sure which
+ locale your system is set to), you can tell
+ <command>initdb</command> exactly which locale you want with the
+ option <option>--locale</option>. For example:
<screen>
-<prompt>$ </><userinput>./configure --enable-locale</>
+<prompt>$ </><userinput>initdb --locale=sv_SE</>
</screen>
-</informalexample>
- Locale support only affects the server; all clients are compatible
- with servers with or without locale support.
- </para>
-
- <para>
- To enable messages translated to the user's preferred language,
- the <option>--enable-nls</option> option must be used. This
- option is independent of the other locale support.
</para>
<para>
- The information about which particular cultural rules to use is
- determined by standard environment variables. If you are getting
- localized behavior from other programs you probably have them set
- up already. The simplest way to set the localization information
- is the <envar>LANG</> variable, for example:
-<programlisting>
-export LANG=sv_SE
-</programlisting>
- This sets the locale to Swedish (<literal>sv</>) as spoken in
+ This example sets the locale to Swedish (<literal>sv</>) as spoken in
Sweden (<literal>SE</>). Other possibilities might be
<literal>en_US</> (U.S. English) and <literal>fr_CA</> (Canada,
French). If more than one character set can be useful for a locale
@@ -103,9 +92,9 @@ export LANG=sv_SE
<para>
Occasionally it is useful to mix rules from several locales, e.g.,
- use U.S. collation rules but Spanish messages. To do that a set of
- environment variables exist that override the default of
- <envar>LANG</> for a particular category:
+ use U.S. collation rules but Spanish messages. To support that, a
+ set of locale subcategories exist that control only a certain
+ aspect of the localization rules.
<informaltable>
<tgroup cols="2">
@@ -138,49 +127,79 @@ export LANG=sv_SE
</tgroup>
</informaltable>
- Additionally, all of these specific variables and the
- <envar>LANG</> variable can be overridden with the
- <envar>LC_ALL</> environment variable.
+ The category names translate into names of
+ <command>initdb</command> options to override the locale choice
+ for a specific category. For instance, to set the locale to
+ French Canadian, but use U.S. rules for formatting currency, use
+ <literal>initdb --locale=fr_CA --lc-monetary=en_US</literal>.
</para>
- <note>
- <para>
- Some message localization libraries also look at the environment
- variable <envar>LANGUAGE</envar> which overrides all other locale
- settings for the purpose of setting the language of messages. If
- in doubt, please refer to the documentation of your operating
- system, in particular the
- <citerefentry><refentrytitle>gettext</><manvolnum>3</></> manual
- page, for more information.
- </para>
- </note>
-
<para>
If you want the system to behave as if it had no locale support,
- use the special locale <literal>C</> or <literal>POSIX</>, or
- simply unset all locale-related variables.
+ use the special locale <literal>C</> or <literal>POSIX</>.
+ </para>
+
+ <para>
+ The nature of some locale categories is that their value has to be
+ fixed for the lifetime of a database cluster. That is, once
+ <command>initdb</command> has run, you cannot change them anymore.
+ <literal>LC_COLLATE</literal> and <literal>LC_CTYPE</literal> are
+ those categories. They affect the sort order of indexes, so they
+ must be kept fixed, or indexes on text columns will become corrupt.
+ <productname>PostgreSQL</productname> enforces this by recording
+ the values of <envar>LC_COLLATE</> and <envar>LC_CTYPE</> that are
+ seen by <command>initdb</>. The server automatically adopts
+ those two values when it is started.
+ </para>
+
+ <para>
+ The other locale categories can be changed as desired whenever the
+ server is started by setting the run-time configuration variables
+ that have the same name as the locale categories (see <xref
+ linkend="runtime-config"> for details). The defaults that are
+ chosen by <command>initdb</command> are actually only written into
+ the configuration file <filename>postgresql.conf</filename> to
+ serve as defaults when the server is started. If you delete the
+ assignments from <filename>postgresql.conf</filename> then the
+ server will inherit the settings from the execution environment.
</para>
<para>
Note that the locale behavior of the server is determined by the
environment variables seen by the server, not by the environment
- of any client. Therefore, be careful to set these variables
+ of any client. Therefore, be careful to configure the correct locale settings
before starting the server. A consequence of this is that if
client and server are set up to different locales, messages may
appear in different languages depending on where they originated.
</para>
+ <note>
+ <para>
+ When we speak of inheriting the locale from the execution
+ environment, this means the following on most operating systems:
+ For a given locale category, say the collation, the following
+ environment variables are consulted in this order until one is
+ found to be set: <envar>LC_ALL</envar>, <envar>LC_COLLATE</envar>
+ (the variable corresponding to the respective category),
+ <envar>LANG</envar>. If none of these environment variables are
+ set then the locale defaults to <literal>C</literal>.
+ </para>
+
+ <para>
+ Some message localization libraries also look at the environment
+ variable <envar>LANGUAGE</envar> which overrides all other locale
+ settings for the purpose of setting the language of messages. If
+ in doubt, please refer to the documentation of your operating
+ system, in particular the
+ <citerefentry><refentrytitle>gettext</><manvolnum>3</></> manual
+ page, for more information.
+ </para>
+ </note>
+
<para>
- The <envar>LC_COLLATE</> and <envar>LC_CTYPE</> variables affect the
- sort order of indexes. Therefore, these values must be kept fixed
- for any particular database cluster, or indexes on text columns will
- become corrupt. <productname>PostgreSQL</productname> enforces this
- by recording the values of <envar>LC_COLLATE</> and <envar>LC_CTYPE</>
- that are seen by <application>initdb</>. The server automatically adopts
- those two values when it is started; only the other <envar>LC_</>
- categories can be set from the environment at server start-up.
- In short, only one collation order can be used in a database cluster,
- and it is chosen at <application>initdb</> time.
+ To enable messages translated to the user's preferred language,
+ the <option>--enable-nls</option> option must be used. This
+ option is independent of the other locale support.
</para>
</sect2>
diff --git a/doc/src/sgml/datatype.sgml b/doc/src/sgml/datatype.sgml
index a792d52e424..1dbf460cf4c 100644
--- a/doc/src/sgml/datatype.sgml
+++ b/doc/src/sgml/datatype.sgml
@@ -1,5 +1,5 @@
<!--
-$Header: /cvsroot/pgsql/doc/src/sgml/datatype.sgml,v 1.86 2002/03/22 19:20:07 petere Exp $
+$Header: /cvsroot/pgsql/doc/src/sgml/datatype.sgml,v 1.87 2002/04/03 05:39:27 petere Exp $
-->
<chapter id="datatype">
@@ -724,11 +724,9 @@ CREATE TABLE <replaceable class="parameter">tablename</replaceable> (<replaceabl
</note>
<para>
- The <type>money</type> type stores U.S.-style currency with fixed
- decimal point representation. If
- <productname>PostgreSQL</productname> is compiled with locale
- support then the <type>money</type> type uses locale-specific
- output formatting.
+ The <type>money</type> type stores a currency amount with fixed
+ decimal point representation. The output format is
+ locale-specific.
</para>
<para>
diff --git a/doc/src/sgml/installation.sgml b/doc/src/sgml/installation.sgml
index c8aa0dd0c95..e5f9de741af 100644
--- a/doc/src/sgml/installation.sgml
+++ b/doc/src/sgml/installation.sgml
@@ -1,4 +1,4 @@
-<!-- $Header: /cvsroot/pgsql/doc/src/sgml/installation.sgml,v 1.74 2002/01/20 05:45:18 tgl Exp $ -->
+<!-- $Header: /cvsroot/pgsql/doc/src/sgml/installation.sgml,v 1.75 2002/04/03 05:39:28 petere Exp $ -->
<chapter id="installation">
<title><![%standalone-include[<productname>PostgreSQL</>]]>
@@ -532,17 +532,6 @@ su - postgres
</varlistentry>
<varlistentry>
- <term><option>--enable-locale</option></term>
- <listitem>
- <para>
- Enables locale support. There is a performance penalty
- associated with locale support, but if you are not in an
- English-speaking environment you will most likely need this.
- </para>
- </listitem>
- </varlistentry>
-
- <varlistentry>
<term><option>--enable-recode</option></term>
<listitem>
<para>
diff --git a/doc/src/sgml/ref/initdb.sgml b/doc/src/sgml/ref/initdb.sgml
index 3bbe44aeee8..8ac524e3dc8 100644
--- a/doc/src/sgml/ref/initdb.sgml
+++ b/doc/src/sgml/ref/initdb.sgml
@@ -1,5 +1,5 @@
<!--
-$Header: /cvsroot/pgsql/doc/src/sgml/ref/initdb.sgml,v 1.19 2001/12/08 03:24:37 thomas Exp $
+$Header: /cvsroot/pgsql/doc/src/sgml/ref/initdb.sgml,v 1.20 2002/04/03 05:39:29 petere Exp $
PostgreSQL documentation
-->
@@ -38,6 +38,13 @@ PostgreSQL documentation
<arg>-E </arg>
<replaceable>encoding</replaceable>
</group>
+ <arg>--locale <replaceable>locale</replaceable></arg>
+ <arg>--lc-collate <replaceable>locale</replaceable></arg>
+ <arg>--lc-ctype <replaceable>locale</replaceable></arg>
+ <arg>--lc-messages <replaceable>locale</replaceable></arg>
+ <arg>--lc-monetary <replaceable>locale</replaceable></arg>
+ <arg>--lc-numeric <replaceable>locale</replaceable></arg>
+ <arg>--lc-time <replaceable>locale</replaceable></arg>
<arg>-L <replaceable>directory</replaceable></arg>
<group><arg>--noclean</arg><arg>-n</arg></group>
<group><arg>--debug</arg><arg>-d</arg></group>
@@ -67,6 +74,25 @@ PostgreSQL documentation
</para>
<para>
+ <command>initdb</command> initializes the database cluster's
+ default locale and character set encoding. Some locale categories
+ are fixed for the lifetime of the cluster, so it is important to
+ make the right choice when running <command>initdb</command>.
+ Other locale categories can be changed later when the server is
+ started. <command>initdb</command> will write those locale
+ settings into the <filename>postgresql.conf</filename>
+ configuration file so they are the default, but they can be changed
+ by editing that file. To set the locale that
+ <command>initdb</command> uses, see the description of the
+ <option>--locale</option> option. The character set encoding can
+ be set separately for each database as it is created.
+ <command>initdb</command> determines the encoding for the
+ <literal>template1</literal> database, which will serve as the
+ default for all other databases. To alter the default encoding use
+ the <option>--encoding</option> option.
+ </para>
+
+ <para>
<command>initdb</command> must be run as the user that will own the
server process, because the server needs to have access to the
files and directories that <command>initdb</command> creates.
@@ -150,6 +176,32 @@ PostgreSQL documentation
</listitem>
</varlistentry>
+ <varlistentry>
+ <term>--locale=<replaceable>locale</replaceable></term>
+ <listitem>
+ <para>
+ Sets the default locale for the database cluster. If this
+ option is not specified, the locale is inherited from the
+ environment that <command>initdb</command> runs in.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>--lc-collate=<replaceable>locale</replaceable></term>
+ <term>--lc-ctype=<replaceable>locale</replaceable></term>
+ <term>--lc-messages=<replaceable>locale</replaceable></term>
+ <term>--lc-monetary=<replaceable>locale</replaceable></term>
+ <term>--lc-numeric=<replaceable>locale</replaceable></term>
+ <term>--lc-time=<replaceable>locale</replaceable></term>
+
+ <listitem>
+ <para>
+ Like <option>--locale</option>, but only sets the locale in
+ the specified category.
+ </para>
+ </listitem>
+ </varlistentry>
</variablelist>
</para>
diff --git a/doc/src/sgml/release.sgml b/doc/src/sgml/release.sgml
index c3e52dd948b..dfb96e4ff8e 100644
--- a/doc/src/sgml/release.sgml
+++ b/doc/src/sgml/release.sgml
@@ -1,5 +1,5 @@
<!--
-$Header: /cvsroot/pgsql/doc/src/sgml/release.sgml,v 1.129 2002/04/01 04:35:37 tgl Exp $
+$Header: /cvsroot/pgsql/doc/src/sgml/release.sgml,v 1.130 2002/04/03 05:39:28 petere Exp $
-->
<appendix id="release">
@@ -24,6 +24,7 @@ CDATA means the content is "SGML-free", so you can write without
worries about funny characters.
-->
<literallayout><![CDATA[
+Locale support is now built by default; choice of locale is set by initdb and/or at run-time
ALTER TABLE ALTER COLUMN SET/DROP NOT NULL
EXPLAIN output comes out as a query result, not a NOTICE message
DOMAINs (types that are constrained versions of base types)
diff --git a/doc/src/sgml/runtime.sgml b/doc/src/sgml/runtime.sgml
index 43b6931fe18..2b0a4ad6349 100644
--- a/doc/src/sgml/runtime.sgml
+++ b/doc/src/sgml/runtime.sgml
@@ -1,5 +1,5 @@
<!--
-$Header: /cvsroot/pgsql/doc/src/sgml/runtime.sgml,v 1.111 2002/04/01 03:34:24 tgl Exp $
+$Header: /cvsroot/pgsql/doc/src/sgml/runtime.sgml,v 1.112 2002/04/03 05:39:29 petere Exp $
-->
<Chapter Id="runtime">
@@ -135,8 +135,14 @@ postgres$ <userinput>initdb -D /usr/local/pgsql/data</userinput>
</para>
<para>
+ <indexterm><primary>locale</></>
<indexterm><primary>LC_COLLATE</></>
- One surprise you might encounter while running
+ <command>initdb</command> also initializes the default locale for
+ the database cluster. Normally, it will just take the locale
+ settings in the environment and apply them to the initialized
+ database. It is possible to specify a different locale for the
+ database; more information about that can be found in <xref
+ linkend="locale">. One surprise you might encounter while running
<command>initdb</command> is a notice similar to this:
<screen>
WARNING: Initializing database with en_US collation order.
@@ -145,18 +151,17 @@ WARNING: Initializing database with en_US collation order.
such queries, you may wish to set LC_COLLATE to "C" and
re-initdb. For more information see the Administrator's Guide.
</screen>
- This is intended to warn you that the currently selected locale will
- cause indexes to be sorted in an order that prevents them from being
- used for LIKE and regular-expression searches. If you need good
- performance in such searches, you should set your current locale to
- <literal>C</> and re-run <command>initdb</command>. On most systems,
- setting the current locale is done by changing the value of the
- environment variable <literal>LC_ALL</literal> or
- <literal>LANG</literal>. The sort order used within a particular
- database cluster is set by <command>initdb</command> and cannot be
- changed later, short of dumping all data, rerunning
- <command>initdb</command>, and reloading the data. So it's important
- to make this choice correctly the first time.
+ This is intended to warn you that the currently selected locale
+ will cause indexes to be sorted in an order that prevents them from
+ being used for LIKE and regular-expression searches. If you need
+ good performance in such searches, you should set your current
+ locale to <literal>C</> and re-run <command>initdb</command>, e.g.,
+ by running <literal>initdb --lc-collate=C</literal>. The sort
+ order used within a particular database cluster is set by
+ <command>initdb</command> and cannot be changed later, short of
+ dumping all data, rerunning <command>initdb</command>, and
+ reloading the data. So it's important to make this choice correctly
+ the first time.
</para>
</sect1>
@@ -1317,6 +1322,71 @@ dynamic_library_path = '/usr/local/lib/postgresql:/home/my_project/lib:$libdir'
</varlistentry>
<varlistentry>
+ <term><varname>LC_MESSAGES</varname> (<type>string</type>)</term>
+ <listitem>
+ <para>
+ Sets the language in which messages are displayed. Acceptable
+ values are system-dependent; see <xref linkend="locale"> for
+ more information. If this variable is set to the empty string
+ (which is the default) then the value is inherited from the
+ execution environment of the server in a system-dependent way.
+ </para>
+
+ <para>
+ On some systems, this locale category does not exist. Setting
+ this variable will still work, but there will be no effect.
+ Also, there is a chance that no translated messages for the
+ desired language exist. In that case you will continue to see
+ the English messages.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><varname>LC_MONETARY</varname> (<type>string</type>)</term>
+ <listitem>
+ <para>
+ Sets the locale to use for formatting monetary amounts.
+ Acceptable values are system-dependent; see <xref
+ linkend="locale"> for more information. If this variable is
+ set to the empty string (which is the default) then the value
+ is inherited from the execution environment of the server in a
+ system-dependent way.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><varname>LC_NUMERIC</varname> (<type>string</type>)</term>
+ <listitem>
+ <para>
+ Sets the locale to use for formatting numbers, for example
+ with the <function>to_char()</function> family of
+ functions. Acceptable values are system-dependent; see <xref
+ linkend="locale"> for more information. If this variable is
+ set to the empty string (which is the default) then the value
+ is inherited from the execution environment of the server in a
+ system-dependent way.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term><varname>LC_TIME</varname> (<type>string</type>)</term>
+ <listitem>
+ <para>
+ Sets the locale to use for formatting date and time values,
+ for example with the <function>to_char()</function> family of
+ functions. Acceptable values are system-dependent; see <xref
+ linkend="locale"> for more information. If this variable is
+ set to the empty string (which is the default) then the value
+ is inherited from the execution environment of the server in a
+ system-dependent way.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
<term><varname>MAX_CONNECTIONS</varname> (<type>integer</type>)</term>
<listitem>
<para>
diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index 7e29f6cd026..c148f3d4e4d 100644
--- a/src/backend/access/transam/xlog.c
+++ b/src/backend/access/transam/xlog.c
@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
- * $Header: /cvsroot/pgsql/src/backend/access/transam/xlog.c,v 1.90 2002/03/15 19:20:30 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/access/transam/xlog.c,v 1.91 2002/04/03 05:39:29 petere Exp $
*
*-------------------------------------------------------------------------
*/
@@ -22,9 +22,7 @@
#include <sys/time.h>
#include <sys/types.h>
#include <dirent.h>
-#ifdef USE_LOCALE
#include <locale.h>
-#endif
#include "access/clog.h"
#include "access/transam.h"
@@ -2081,10 +2079,7 @@ WriteControlFile(void)
{
int fd;
char buffer[BLCKSZ]; /* need not be aligned */
-
-#ifdef USE_LOCALE
char *localeptr;
-#endif
/*
* Initialize version and compatibility-check fields
@@ -2093,7 +2088,6 @@ WriteControlFile(void)
ControlFile->catalog_version_no = CATALOG_VERSION_NO;
ControlFile->blcksz = BLCKSZ;
ControlFile->relseg_size = RELSEG_SIZE;
-#ifdef USE_LOCALE
localeptr = setlocale(LC_COLLATE, NULL);
if (!localeptr)
elog(PANIC, "invalid LC_COLLATE setting");
@@ -2115,10 +2109,6 @@ WriteControlFile(void)
"\n\tsuch queries, you may wish to set LC_COLLATE to \"C\" and"
"\n\tre-initdb. For more information see the Administrator's Guide.",
ControlFile->lc_collate);
-#else /* not USE_LOCALE */
- strcpy(ControlFile->lc_collate, "C");
- strcpy(ControlFile->lc_ctype, "C");
-#endif /* not USE_LOCALE */
/* Contents are protected with a CRC */
INIT_CRC64(ControlFile->crc);
@@ -2232,7 +2222,6 @@ ReadControlFile(void)
"\tbut the backend was compiled with RELSEG_SIZE %d.\n"
"\tIt looks like you need to initdb.",
ControlFile->relseg_size, RELSEG_SIZE);
-#ifdef USE_LOCALE
if (setlocale(LC_COLLATE, ControlFile->lc_collate) == NULL)
elog(PANIC,
"The database cluster was initialized with LC_COLLATE '%s',\n"
@@ -2245,15 +2234,6 @@ ReadControlFile(void)
"\twhich is not recognized by setlocale().\n"
"\tIt looks like you need to initdb.",
ControlFile->lc_ctype);
-#else /* not USE_LOCALE */
- if (strcmp(ControlFile->lc_collate, "C") != 0 ||
- strcmp(ControlFile->lc_ctype, "C") != 0)
- elog(PANIC,
- "The database cluster was initialized with LC_COLLATE '%s' and\n"
- "\tLC_CTYPE '%s', but the server was compiled without locale support.\n"
- "\tIt looks like you need to initdb or recompile.",
- ControlFile->lc_collate, ControlFile->lc_ctype);
-#endif /* not USE_LOCALE */
}
void
diff --git a/src/backend/main/main.c b/src/backend/main/main.c
index b1be0781412..9c79e7b78d9 100644
--- a/src/backend/main/main.c
+++ b/src/backend/main/main.c
@@ -13,7 +13,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/main/main.c,v 1.49 2001/11/05 17:46:25 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/main/main.c,v 1.50 2002/04/03 05:39:29 petere Exp $
*
*-------------------------------------------------------------------------
*/
@@ -21,9 +21,7 @@
#include <pwd.h>
#include <unistd.h>
-#if defined(USE_LOCALE) || defined(ENABLE_NLS)
#include <locale.h>
-#endif
#if defined(__alpha) && defined(__osf__)
#include <sys/sysinfo.h>
@@ -122,11 +120,25 @@ main(int argc, char *argv[])
new_argv[i] = strdup(argv[i]);
new_argv[argc] = NULL;
- /* Initialize NLS settings so we can give localized error messages */
-#ifdef ENABLE_NLS
+ /*
+ * Set up locale information from environment. Note that CTYPE
+ * and COLLATE will be overridden later from pg_control if we are
+ * in an already-initialized database. We set them here so that
+ * they will be available to fill pg_control during initdb. The
+ * other ones will get reset later in ResetAllOptions, but we set
+ * them here to get already localized behavior during startup
+ * (e.g., error messages).
+ */
+ setlocale(LC_COLLATE, "");
+ setlocale(LC_CTYPE, "");
#ifdef LC_MESSAGES
setlocale(LC_MESSAGES, "");
#endif
+ setlocale(LC_MONETARY, "");
+ setlocale(LC_NUMERIC, "");
+ setlocale(LC_TIME, "");
+
+#ifdef ENABLE_NLS
bindtextdomain("postgres", LOCALEDIR);
textdomain("postgres");
#endif
@@ -179,20 +191,6 @@ main(int argc, char *argv[])
}
/*
- * Set up locale information from environment, in only the categories
- * needed by Postgres; leave other categories set to default "C".
- * (Note that CTYPE and COLLATE will be overridden later from
- * pg_control if we are in an already-initialized database. We set
- * them here so that they will be available to fill pg_control during
- * initdb.)
- */
-#ifdef USE_LOCALE
- setlocale(LC_CTYPE, "");
- setlocale(LC_COLLATE, "");
- setlocale(LC_MONETARY, "");
-#endif
-
- /*
* Now dispatch to one of PostmasterMain, PostgresMain, or
* BootstrapMain depending on the program name (and possibly first
* argument) we were called with. The lack of consistency here is
diff --git a/src/backend/utils/adt/cash.c b/src/backend/utils/adt/cash.c
index c2af4a64fa9..4a8ddcf19b6 100644
--- a/src/backend/utils/adt/cash.c
+++ b/src/backend/utils/adt/cash.c
@@ -9,7 +9,7 @@
* workings can be found in the book "Software Solutions in C" by
* Dale Schumacher, Academic Press, ISBN: 0-12-632360-7.
*
- * $Header: /cvsroot/pgsql/src/backend/utils/adt/cash.c,v 1.52 2002/02/19 22:19:34 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/cash.c,v 1.53 2002/04/03 05:39:29 petere Exp $
*/
#include "postgres.h"
@@ -17,9 +17,7 @@
#include <limits.h>
#include <ctype.h>
#include <math.h>
-#ifdef USE_LOCALE
#include <locale.h>
-#endif
#include "miscadmin.h"
#include "utils/builtins.h"
@@ -83,11 +81,7 @@ cash_in(PG_FUNCTION_ARGS)
psymbol,
*nsymbol;
-#ifdef USE_LOCALE
struct lconv *lconvert = PGLC_localeconv();
-#endif
-
-#ifdef USE_LOCALE
/*
* frac_digits will be CHAR_MAX in some locales, notably C. However,
@@ -108,14 +102,6 @@ cash_in(PG_FUNCTION_ARGS)
csymbol = ((*lconvert->currency_symbol != '\0') ? lconvert->currency_symbol : "$");
psymbol = ((*lconvert->positive_sign != '\0') ? *lconvert->positive_sign : '+');
nsymbol = ((*lconvert->negative_sign != '\0') ? lconvert->negative_sign : "-");
-#else
- fpoint = 2;
- dsymbol = '.';
- ssymbol = ',';
- csymbol = "$";
- psymbol = '+';
- nsymbol = "-";
-#endif
#ifdef CASHDEBUG
printf("cashin- precision '%d'; decimal '%c'; thousands '%c'; currency '%s'; positive '%c'; negative '%s'\n",
@@ -241,11 +227,8 @@ cash_out(PG_FUNCTION_ARGS)
*nsymbol;
char convention;
-#ifdef USE_LOCALE
struct lconv *lconvert = PGLC_localeconv();
-#endif
-#ifdef USE_LOCALE
/* see comments about frac_digits in cash_in() */
points = lconvert->frac_digits;
if (points < 0 || points > 10)
@@ -264,15 +247,6 @@ cash_out(PG_FUNCTION_ARGS)
dsymbol = ((*lconvert->mon_decimal_point != '\0') ? *lconvert->mon_decimal_point : '.');
csymbol = ((*lconvert->currency_symbol != '\0') ? lconvert->currency_symbol : "$");
nsymbol = ((*lconvert->negative_sign != '\0') ? lconvert->negative_sign : "-");
-#else
- points = 2;
- mon_group = 3;
- comma = ',';
- convention = 0;
- dsymbol = '.';
- csymbol = "$";
- nsymbol = "-";
-#endif
point_pos = LAST_DIGIT - points;
diff --git a/src/backend/utils/adt/formatting.c b/src/backend/utils/adt/formatting.c
index 199630e0cc4..231bad2ca6d 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.51 2002/03/06 06:10:12 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/formatting.c,v 1.52 2002/04/03 05:39:29 petere Exp $
*
*
* Portions Copyright (c) 1999-2000, PostgreSQL Global Development Group
@@ -72,9 +72,7 @@
#include <ctype.h>
#include <sys/time.h>
#include <unistd.h>
-#ifdef USE_LOCALE
#include <locale.h>
-#endif
#include <math.h>
#include <float.h>
@@ -3380,9 +3378,6 @@ int_to_roman(int number)
static void
NUM_prepare_locale(NUMProc *Np)
{
-
-#ifdef USE_LOCALE
-
if (Np->Num->need_locale)
{
@@ -3436,8 +3431,6 @@ NUM_prepare_locale(NUMProc *Np)
}
else
{
-#endif
-
/*
* Default values
*/
@@ -3446,10 +3439,7 @@ NUM_prepare_locale(NUMProc *Np)
Np->decimal = ".";
Np->L_thousands_sep = ",";
Np->L_currency_symbol = " ";
-
-#ifdef USE_LOCALE
}
-#endif
}
/* ----------
diff --git a/src/backend/utils/adt/pg_locale.c b/src/backend/utils/adt/pg_locale.c
index 2c86ff5bcf1..c5c8d312d3f 100644
--- a/src/backend/utils/adt/pg_locale.c
+++ b/src/backend/utils/adt/pg_locale.c
@@ -1,173 +1,144 @@
-/* -----------------------------------------------------------------------
- * pg_locale.c
+/*-----------------------------------------------------------------------
*
- * The PostgreSQL locale utils.
+ * PostgreSQL locale utilities
*
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/pg_locale.c,v 1.16 2002/04/03 05:39:31 petere Exp $
*
- * $Header: /cvsroot/pgsql/src/backend/utils/adt/pg_locale.c,v 1.15 2002/03/06 06:10:14 momjian Exp $
+ * Portions Copyright (c) 2002, PostgreSQL Global Development Group
*
- * Portions Copyright (c) 1999-2000, PostgreSQL Global Development Group
- *
- * Karel Zak
- *
- * -----------------------------------------------------------------------
+ *-----------------------------------------------------------------------
*/
#include "postgres.h"
-
-#ifdef USE_LOCALE
-
-#include <locale.h>
-
#include "utils/pg_locale.h"
-
-/* #define DEBUG_LOCALE_UTILS */
+#include <locale.h>
-static bool CurrentLocaleConvValid = false;
-static struct lconv CurrentLocaleConv;
+/* GUC storage area */
+char * locale_messages;
+char * locale_monetary;
+char * locale_numeric;
+char * locale_time;
-static void PGLC_setlocale(PG_LocaleCategories *lc);
+/* GUC parse hooks */
-/*------
- * Frees memory used in PG_LocaleCategories -- this memory is
- * allocated in PGLC_current().
- *------
- */
-void
-PGLC_free_categories(PG_LocaleCategories *lc)
+bool locale_messages_check(const char *proposed)
{
- if (lc->lc_ctype)
- pfree(lc->lc_ctype);
- if (lc->lc_numeric)
- pfree(lc->lc_numeric);
- if (lc->lc_time)
- pfree(lc->lc_time);
- if (lc->lc_collate)
- pfree(lc->lc_collate);
- if (lc->lc_monetary);
- pfree(lc->lc_monetary);
#ifdef LC_MESSAGES
- if (lc->lc_messages)
- pfree(lc->lc_messages);
+ return chklocale(LC_MESSAGES, proposed);
+#else
+ /* We return true here so LC_MESSAGES can be set in the
+ configuration file on every system. */
+ return true;
#endif
}
-/*------
- * Return in PG_LocaleCategories the current locale settings.
- *
- * NB: strings are allocated in the current memory context!
- *------
- */
-void
-PGLC_current(PG_LocaleCategories *lc)
+bool locale_monetary_check(const char *proposed)
{
- lc->lang = getenv("LANG");
+ return chklocale(LC_MONETARY, proposed);
+}
- lc->lc_ctype = pstrdup(setlocale(LC_CTYPE, NULL));
- lc->lc_numeric = pstrdup(setlocale(LC_NUMERIC, NULL));
- lc->lc_time = pstrdup(setlocale(LC_TIME, NULL));
- lc->lc_collate = pstrdup(setlocale(LC_COLLATE, NULL));
- lc->lc_monetary = pstrdup(setlocale(LC_MONETARY, NULL));
-#ifdef LC_MESSAGES
- lc->lc_messages = pstrdup(setlocale(LC_MESSAGES, NULL));
-#endif
+bool locale_numeric_check(const char *proposed)
+{
+ return chklocale(LC_NUMERIC, proposed);
}
+bool locale_time_check(const char *proposed)
+{
+ return chklocale(LC_TIME, proposed);
+}
-#ifdef DEBUG_LOCALE_UTILS
+/* GUC assign hooks */
-/*------
- * Print a PG_LocaleCategories struct as DEBUG
- *------
- */
-static void
-PGLC_debug_lc(PG_LocaleCategories *lc)
+void locale_messages_assign(const char *value)
{
#ifdef LC_MESSAGES
- elog(LOG, "CURRENT LOCALE ENVIRONMENT:\n\nLANG: \t%s\nLC_CTYPE:\t%s\nLC_NUMERIC:\t%s\nLC_TIME:\t%s\nLC_COLLATE:\t%s\nLC_MONETARY:\t%s\nLC_MESSAGES:\t%s\n",
- lc->lang,
- lc->lc_ctype,
- lc->lc_numeric,
- lc->lc_time,
- lc->lc_collate,
- lc->lc_monetary,
- lc->lc_messages);
-#else
- elog(LOG, "CURRENT LOCALE ENVIRONMENT:\n\nLANG: \t%s\nLC_CTYPE:\t%s\nLC_NUMERIC:\t%s\nLC_TIME:\t%s\nLC_COLLATE:\t%s\nLC_MONETARY:\t%s\n",
- lc->lang,
- lc->lc_ctype,
- lc->lc_numeric,
- lc->lc_time,
- lc->lc_collate,
- lc->lc_monetary);
+ setlocale(LC_MESSAGES, value);
#endif
}
-#endif
-/*------
- * Set locales via a PG_LocaleCategories struct
- *
- * NB: it would be very dangerous to set the locale values to any random
- * choice of locale, since that could cause indexes to become corrupt, etc.
- * Therefore this routine is NOT exported from this module. It should be
- * used only to restore previous locale settings during PGLC_localeconv.
- *------
+void locale_monetary_assign(const char *value)
+{
+ setlocale(LC_MONETARY, value);
+}
+
+void locale_numeric_assign(const char *value)
+{
+ setlocale(LC_NUMERIC, value);
+}
+
+void locale_time_assign(const char *value)
+{
+ setlocale(LC_TIME, value);
+}
+
+
+/*
+ * Returns true if the proposed string represents a valid locale of
+ * the given category. This is probably pretty slow, but it's not
+ * called in critical places.
*/
-static void
-PGLC_setlocale(PG_LocaleCategories *lc)
+bool
+chklocale(int category, const char *proposed)
{
- if (!setlocale(LC_COLLATE, lc->lc_collate))
- elog(WARNING, "pg_setlocale(): 'LC_COLLATE=%s' cannot be honored.",
- lc->lc_collate);
+ char *save;
- if (!setlocale(LC_CTYPE, lc->lc_ctype))
- elog(WARNING, "pg_setlocale(): 'LC_CTYPE=%s' cannot be honored.",
- lc->lc_ctype);
+ save = setlocale(category, NULL);
+ if (!save)
+ return false;
- if (!setlocale(LC_NUMERIC, lc->lc_numeric))
- elog(WARNING, "pg_setlocale(): 'LC_NUMERIC=%s' cannot be honored.",
- lc->lc_numeric);
+ if (!setlocale(category, proposed))
+ return false;
- if (!setlocale(LC_TIME, lc->lc_time))
- elog(WARNING, "pg_setlocale(): 'LC_TIME=%s' cannot be honored.",
- lc->lc_time);
+ setlocale(category, save);
+ return true;
+}
- if (!setlocale(LC_MONETARY, lc->lc_monetary))
- elog(WARNING, "pg_setlocale(): 'LC_MONETARY=%s' cannot be honored.",
- lc->lc_monetary);
-#ifdef LC_MESSAGES
- if (!setlocale(LC_MESSAGES, lc->lc_messages))
- elog(WARNING, "pg_setlocale(): 'LC_MESSAGES=%s' cannot be honored.",
- lc->lc_messages);
-#endif
+/*
+ * We'd like to cache whether LC_COLLATE is C (or POSIX), so we can
+ * optimize a few code paths in various places.
+ */
+bool
+lc_collate_is_c(void)
+{
+ /* Cache result so we only have to compute it once */
+ static int result = -1;
+ char *localeptr;
+
+ if (result >= 0)
+ return (bool) result;
+ localeptr = setlocale(LC_COLLATE, NULL);
+ if (!localeptr)
+ elog(PANIC, "Invalid LC_COLLATE setting");
+
+ if (strcmp(localeptr, "C") == 0)
+ result = true;
+ else if (strcmp(localeptr, "POSIX") == 0)
+ result = true;
+ else
+ result = false;
+ return (bool) result;
}
-/*------
- * Return the POSIX lconv struct (contains number/money formatting information)
- * with locale information for all categories. Note that returned lconv
- * does not depend on currently active category settings, but on external
- * environment variables for locale.
- *------
+
+
+/*
+ * Return the POSIX lconv struct (contains number/money formatting
+ * information) with locale information for all categories.
*/
struct lconv *
PGLC_localeconv(void)
{
- PG_LocaleCategories lc;
struct lconv *extlconv;
+ static bool CurrentLocaleConvValid = false;
+ static struct lconv CurrentLocaleConv;
/* Did we do it already? */
if (CurrentLocaleConvValid)
return &CurrentLocaleConv;
- /* Save current locale setting to lc */
- PGLC_current(&lc);
-
- /* Set all locale categories based on postmaster's environment vars */
- setlocale(LC_ALL, "");
-
/* Get formatting information for the external environment */
extlconv = localeconv();
@@ -187,14 +158,6 @@ PGLC_localeconv(void)
CurrentLocaleConv.negative_sign = strdup(extlconv->negative_sign);
CurrentLocaleConv.positive_sign = strdup(extlconv->positive_sign);
- /* Restore Postgres' internal locale settings */
- PGLC_setlocale(&lc);
-
- /* Deallocate category settings allocated in PGLC_current() */
- PGLC_free_categories(&lc);
-
CurrentLocaleConvValid = true;
return &CurrentLocaleConv;
}
-
-#endif /* USE_LOCALE */
diff --git a/src/backend/utils/adt/selfuncs.c b/src/backend/utils/adt/selfuncs.c
index f5fb2adf2eb..e8e71dec25a 100644
--- a/src/backend/utils/adt/selfuncs.c
+++ b/src/backend/utils/adt/selfuncs.c
@@ -15,7 +15,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/utils/adt/selfuncs.c,v 1.106 2002/03/08 04:29:01 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/selfuncs.c,v 1.107 2002/04/03 05:39:31 petere Exp $
*
*-------------------------------------------------------------------------
*/
@@ -70,9 +70,7 @@
#include <ctype.h>
#include <math.h>
-#ifdef USE_LOCALE
#include <locale.h>
-#endif
#include "access/heapam.h"
#include "catalog/catname.h"
@@ -95,6 +93,7 @@
#include "utils/datum.h"
#include "utils/int8.h"
#include "utils/lsyscache.h"
+#include "utils/pg_locale.h"
#include "utils/selfuncs.h"
#include "utils/syscache.h"
@@ -2240,19 +2239,16 @@ convert_one_string_to_scalar(unsigned char *value, int rangelo, int rangehi)
/*
* Convert a string-type Datum into a palloc'd, null-terminated string.
*
- * If USE_LOCALE is defined, we must pass the string through strxfrm()
+ * When using a non-C locale, we must pass the string through strxfrm()
* before continuing, so as to generate correct locale-specific results.
*/
static unsigned char *
convert_string_datum(Datum value, Oid typid)
{
char *val;
-
-#ifdef USE_LOCALE
char *xfrmstr;
size_t xfrmsize;
size_t xfrmlen;
-#endif
switch (typid)
{
@@ -2290,21 +2286,22 @@ convert_string_datum(Datum value, Oid typid)
return NULL;
}
-#ifdef USE_LOCALE
- /* Guess that transformed string is not much bigger than original */
- xfrmsize = strlen(val) + 32; /* arbitrary pad value here... */
- xfrmstr = (char *) palloc(xfrmsize);
- xfrmlen = strxfrm(xfrmstr, val, xfrmsize);
- if (xfrmlen >= xfrmsize)
+ if (!lc_collate_is_c())
{
- /* Oops, didn't make it */
- pfree(xfrmstr);
- xfrmstr = (char *) palloc(xfrmlen + 1);
- xfrmlen = strxfrm(xfrmstr, val, xfrmlen + 1);
+ /* Guess that transformed string is not much bigger than original */
+ xfrmsize = strlen(val) + 32; /* arbitrary pad value here... */
+ xfrmstr = (char *) palloc(xfrmsize);
+ xfrmlen = strxfrm(xfrmstr, val, xfrmsize);
+ if (xfrmlen >= xfrmsize)
+ {
+ /* Oops, didn't make it */
+ pfree(xfrmstr);
+ xfrmstr = (char *) palloc(xfrmlen + 1);
+ xfrmlen = strxfrm(xfrmstr, val, xfrmlen + 1);
+ }
+ pfree(val);
+ val = xfrmstr;
}
- pfree(val);
- val = xfrmstr;
-#endif
return (unsigned char *) val;
}
@@ -3147,44 +3144,28 @@ pattern_selectivity(char *patt, Pattern_Type ptype)
return result;
}
+
/*
- * Test whether the database's LOCALE setting is safe for LIKE/regexp index
- * optimization. The key requirement here is that given a prefix string,
- * say "foo", we must be able to generate another string "fop" that is
- * greater than all strings "foobar" starting with "foo". Unfortunately,
- * many non-C locales have bizarre collation rules in which "fop" > "foo"
- * is not sufficient to ensure "fop" > "foobar". Until we can come up
- * with a more bulletproof way of generating the upper-bound string,
- * disable the optimization in locales where it is not known to be safe.
+ * We want test whether the database's LC_COLLATE setting is safe for
+ * LIKE/regexp index optimization.
+ *
+ * The key requirement here is that given a prefix string, say "foo",
+ * we must be able to generate another string "fop" that is greater
+ * than all strings "foobar" starting with "foo". Unfortunately, a
+ * non-C locale may have arbitrary collation rules in which "fop" >
+ * "foo" is not sufficient to ensure "fop" > "foobar". Until we can
+ * come up with a more bulletproof way of generating the upper-bound
+ * string, the optimization is disabled in all non-C locales.
+ *
+ * (In theory, locales other than C may be LIKE-safe so this function
+ * could be different from lc_collate_is_c(), but in a different
+ * theory, non-C locales are completely unpredicable so it's unlikely
+ * to happen.)
*/
bool
locale_is_like_safe(void)
{
-#ifdef USE_LOCALE
- /* Cache result so we only have to compute it once */
- static int result = -1;
- char *localeptr;
-
- if (result >= 0)
- return (bool) result;
- localeptr = setlocale(LC_COLLATE, NULL);
- if (!localeptr)
- elog(PANIC, "Invalid LC_COLLATE setting");
-
- /*
- * Currently we accept only "C" and "POSIX" (do any systems still
- * return "POSIX"?). Which other locales allow safe optimization?
- */
- if (strcmp(localeptr, "C") == 0)
- result = true;
- else if (strcmp(localeptr, "POSIX") == 0)
- result = true;
- else
- result = false;
- return (bool) result;
-#else /* not USE_LOCALE */
- return true; /* We must be in C locale, which is OK */
-#endif /* USE_LOCALE */
+ return lc_collate_is_c();
}
/*
diff --git a/src/backend/utils/adt/varlena.c b/src/backend/utils/adt/varlena.c
index 5afaf398879..0cd38a76bee 100644
--- a/src/backend/utils/adt/varlena.c
+++ b/src/backend/utils/adt/varlena.c
@@ -8,7 +8,7 @@
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/backend/utils/adt/varlena.c,v 1.81 2002/04/01 03:34:26 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/adt/varlena.c,v 1.82 2002/04/03 05:39:32 petere Exp $
*
*-------------------------------------------------------------------------
*/
@@ -19,6 +19,7 @@
#include "mb/pg_wchar.h"
#include "miscadmin.h"
#include "utils/builtins.h"
+#include "utils/pg_locale.h"
static int text_cmp(text *arg1, text *arg2);
@@ -493,29 +494,36 @@ varstr_cmp(char *arg1, int len1, char *arg2, int len2)
char *a1p,
*a2p;
-#ifdef USE_LOCALE
- a1p = (char *) palloc(len1 + 1);
- a2p = (char *) palloc(len2 + 1);
-
- memcpy(a1p, arg1, len1);
- *(a1p + len1) = '\0';
- memcpy(a2p, arg2, len2);
- *(a2p + len2) = '\0';
-
- result = strcoll(a1p, a2p);
+ /*
+ * Unfortunately, there is no strncoll(), so in the non-C locale
+ * case we have to do some memory copying. This turns out to be
+ * significantly slower, so we optimize the case were LC_COLLATE
+ * is C.
+ */
+ if (!lc_collate_is_c())
+ {
+ a1p = (char *) palloc(len1 + 1);
+ a2p = (char *) palloc(len2 + 1);
- pfree(a1p);
- pfree(a2p);
+ memcpy(a1p, arg1, len1);
+ *(a1p + len1) = '\0';
+ memcpy(a2p, arg2, len2);
+ *(a2p + len2) = '\0';
-#else
+ result = strcoll(a1p, a2p);
- a1p = arg1;
- a2p = arg2;
+ pfree(a1p);
+ pfree(a2p);
+ }
+ else
+ {
+ a1p = arg1;
+ a2p = arg2;
- result = strncmp(a1p, a2p, Min(len1, len2));
- if ((result == 0) && (len1 != len2))
- result = (len1 < len2) ? -1 : 1;
-#endif
+ result = strncmp(a1p, a2p, Min(len1, len2));
+ if ((result == 0) && (len1 != len2))
+ result = (len1 < len2) ? -1 : 1;
+ }
return result;
}
diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c
index 9c35f0949aa..8abf451b630 100644
--- a/src/backend/utils/misc/guc.c
+++ b/src/backend/utils/misc/guc.c
@@ -4,7 +4,7 @@
* Support for grand unified configuration scheme, including SET
* command, configuration file, and command line options.
*
- * $Header: /cvsroot/pgsql/src/backend/utils/misc/guc.c,v 1.64 2002/04/01 03:34:26 tgl Exp $
+ * $Header: /cvsroot/pgsql/src/backend/utils/misc/guc.c,v 1.65 2002/04/03 05:39:32 petere Exp $
*
* Copyright 2000 by PostgreSQL Global Development Group
* Written by Peter Eisentraut <peter_e@gmx.net>.
@@ -41,6 +41,7 @@
#include "utils/builtins.h"
#include "utils/datetime.h"
#include "utils/elog.h"
+#include "utils/pg_locale.h"
#include "pgstat.h"
@@ -586,6 +587,26 @@ static struct config_string
},
{
+ "lc_messages", PGC_POSTMASTER, PGC_S_DEFAULT, &locale_messages,
+ "", locale_messages_check, locale_messages_assign
+ },
+
+ {
+ "lc_monetary", PGC_POSTMASTER, PGC_S_DEFAULT, &locale_monetary,
+ "", locale_monetary_check, locale_monetary_assign
+ },
+
+ {
+ "lc_numeric", PGC_POSTMASTER, PGC_S_DEFAULT, &locale_numeric,
+ "", locale_numeric_check, locale_numeric_assign
+ },
+
+ {
+ "lc_time", PGC_POSTMASTER, PGC_S_DEFAULT, &locale_time,
+ "", locale_time_check, locale_time_assign
+ },
+
+ {
"server_min_messages", PGC_USERSET, PGC_S_DEFAULT, &server_min_messages_str,
server_min_messages_str_default, check_server_min_messages,
assign_server_min_messages
diff --git a/src/bin/initdb/initdb.sh b/src/bin/initdb/initdb.sh
index 2bb413844f1..e028ac1b10e 100644
--- a/src/bin/initdb/initdb.sh
+++ b/src/bin/initdb/initdb.sh
@@ -27,7 +27,7 @@
# Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
# Portions Copyright (c) 1994, Regents of the University of California
#
-# $Header: /cvsroot/pgsql/src/bin/initdb/Attic/initdb.sh,v 1.145 2002/03/02 21:39:34 momjian Exp $
+# $Header: /cvsroot/pgsql/src/bin/initdb/Attic/initdb.sh,v 1.146 2002/04/03 05:39:32 petere Exp $
#
#-------------------------------------------------------------------------
@@ -51,6 +51,26 @@ exit_nicely(){
exit 1
}
+pg_getlocale(){
+ arg=$1
+ unset ret
+
+ for var in "PGLC_$arg" PGLOCALE LC_ALL "LC_$arg" LANG; do
+ varset=`eval echo '${'"$var"'+set}'`
+ varval=`eval echo '$'"$var"`
+ if test "$varset" = set; then
+ ret=$varval
+ break
+ fi
+ done
+
+ if test "${ret+set}" != set; then
+ ret=C
+ fi
+
+ echo "$ret"
+}
+
CMDNAME=`basename $0`
@@ -251,11 +271,61 @@ do
-E*)
MULTIBYTE=`echo $1 | sed 's/^-E//'`
;;
+# Locale flags
+ --locale)
+ PGLOCALE="$2"
+ shift;;
+ --locale=*)
+ PGLOCALE=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --no-locale)
+ PGLOCALE=C
+ ;;
+
+ --lc-collate)
+ PGLC_COLLATE=$2
+ shift;;
+ --lc-collate=*)
+ PGLC_COLLATE=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --lc-ctype)
+ PGLC_CTYPE=$2
+ shift;;
+ --lc-ctype=*)
+ PGLC_CTYPE=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --lc-messages)
+ PGLC_MESSAGES=$2
+ shift;;
+ --lc-messages=*)
+ PGLC_MESSAGES=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --lc-monetary)
+ PGLC_MONETARY=$2
+ shift;;
+ --lc-monetary=*)
+ PGLC_MONETARY=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --lc-numeric)
+ PGLC_NUMERIC=$2
+ shift;;
+ --lc-numeric=*)
+ PGLC_NUMERIC=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+ --lc-time)
+ PGLC_TIME=$2
+ shift;;
+ --lc-time=*)
+ PGLC_TIME=`echo $1 | sed 's/^[^=]*=//'`
+ ;;
+
-*)
echo "$CMDNAME: invalid option: $1"
echo "Try '$CMDNAME --help' for more information."
exit 1
;;
+
+# Non-option argument specifies data directory
*)
PGDATA=$1
;;
@@ -275,6 +345,13 @@ if [ "$usage" ]; then
if [ -n "$MULTIBYTE" ] ; then
echo " -E, --encoding ENCODING Set default encoding for new databases"
fi
+ echo " --locale LOCALE Initialize database cluster with given locale"
+ echo " --lc-collate, --lc-ctype, --lc-messages LOCALE"
+ echo " --lc-monetary, --lc-numeric, --lc-time LOCALE"
+ echo " Initialize database cluster with given locale"
+ echo " in the respective category"
+ echo " (default taken from environment)"
+ echo " --no-locale Equivalent to --locale=C"
echo " -U, --username NAME Database superuser name"
echo "Less commonly used options: "
echo " -L DIRECTORY Where to find the input files"
@@ -469,7 +546,15 @@ echo "$short_version" > "$PGDATA/PG_VERSION" || exit_nicely
cat "$POSTGRES_BKI" \
| sed -e "s/POSTGRES/$POSTGRES_SUPERUSERNAME/g" \
-e "s/ENCODING/$MULTIBYTEID/g" \
-| "$PGPATH"/postgres -boot -x1 $PGSQL_OPT $BACKEND_TALK_ARG template1 \
+|
+(
+ LC_COLLATE=`pg_getlocale COLLATE`
+ LC_CTYPE=`pg_getlocale CTYPE`
+ export LC_COLLATE
+ export LC_CTYPE
+ unset LC_ALL
+ "$PGPATH"/postgres -boot -x1 $PGSQL_OPT $BACKEND_TALK_ARG template1
+) \
|| exit_nicely
# Make the per-database PGVERSION for template1 only after init'ing it
@@ -485,7 +570,19 @@ $ECHO_N "creating configuration files... "$ECHO_C
cp "$PG_HBA_SAMPLE" "$PGDATA"/pg_hba.conf || exit_nicely
cp "$PG_IDENT_SAMPLE" "$PGDATA"/pg_ident.conf || exit_nicely
-cp "$POSTGRESQL_CONF_SAMPLE" "$PGDATA"/postgresql.conf || exit_nicely
+(
+ cat "$POSTGRESQL_CONF_SAMPLE"
+ echo
+ echo
+ echo "#"
+ echo "# Locale settings"
+ echo "#"
+ echo "# (initialized by initdb -- may be changed)"
+ for cat in MESSAGES MONETARY NUMERIC TIME; do
+ echo "LC_$cat = '`pg_getlocale $cat`'"
+ done
+) > "$PGDATA"/postgresql.conf || exit_nicely
+
chmod 0600 "$PGDATA"/pg_hba.conf "$PGDATA"/pg_ident.conf \
"$PGDATA"/postgresql.conf
diff --git a/src/include/pg_config.h.in b/src/include/pg_config.h.in
index 8a509e3d89a..cd27d28fa3c 100644
--- a/src/include/pg_config.h.in
+++ b/src/include/pg_config.h.in
@@ -8,7 +8,7 @@
* or in pg_config.h afterwards. Of course, if you edit pg_config.h, then your
* changes will be overwritten the next time you run configure.
*
- * $Id: pg_config.h.in,v 1.19 2002/03/29 17:32:55 petere Exp $
+ * $Id: pg_config.h.in,v 1.20 2002/04/03 05:39:33 petere Exp $
*/
#ifndef PG_CONFIG_H
@@ -33,9 +33,6 @@
/* A canonical string containing the version number, platform, and C compiler */
#undef PG_VERSION_STR
-/* Set to 1 if you want LOCALE support (--enable-locale) */
-#undef USE_LOCALE
-
/* Set to 1 if you want cyrillic recode (--enable-recode) */
#undef CYR_RECODE
diff --git a/src/include/utils/pg_locale.h b/src/include/utils/pg_locale.h
index 03330682b75..b5056e6ca80 100644
--- a/src/include/utils/pg_locale.h
+++ b/src/include/utils/pg_locale.h
@@ -1,56 +1,42 @@
-/* -----------------------------------------------------------------------
- * pg_locale.h
+/*-----------------------------------------------------------------------
*
- * The PostgreSQL locale utils.
+ * PostgreSQL locale utilities
*
+ * $Header: /cvsroot/pgsql/src/include/utils/pg_locale.h,v 1.12 2002/04/03 05:39:33 petere Exp $
*
- * $Id: pg_locale.h,v 1.11 2001/11/05 17:46:36 momjian Exp $
+ * Copyright (c) 2002, PostgreSQL Global Development Group
*
- * Portions Copyright (c) 1999-2000, PostgreSQL Global Development Group
- *
- * Karel Zak - Zakkr
- *
- * -----------------------------------------------------------------------
+ *-----------------------------------------------------------------------
*/
#ifndef _PG_LOCALE_
#define _PG_LOCALE_
-#ifdef USE_LOCALE
+#include "postgres.h"
+#include <locale.h>
-/*------
- * POSIX locale categories and environment variable LANG
- *------
- */
-typedef struct PG_LocaleCategories
-{
- char *lang,
- *lc_ctype,
- *lc_numeric,
- *lc_time,
- *lc_collate,
- *lc_monetary,
- *lc_messages;
-} PG_LocaleCategories;
+extern char * locale_messages;
+extern char * locale_monetary;
+extern char * locale_numeric;
+extern char * locale_time;
-/*
- * Save locale category settings into PG memory
- */
-extern void PGLC_current(PG_LocaleCategories *lc);
+bool locale_messages_check(const char *proposed);
+bool locale_monetary_check(const char *proposed);
+bool locale_numeric_check(const char *proposed);
+bool locale_time_check(const char *proposed);
+
+void locale_messages_assign(const char *value);
+void locale_monetary_assign(const char *value);
+void locale_numeric_assign(const char *value);
+void locale_time_assign(const char *value);
+
+bool chklocale(int category, const char *proposed);
+bool lc_collate_is_c(void);
/*
- * Free memory allocated in PGLC_current()
- */
-extern void PGLC_free_categories(PG_LocaleCategories *lc);
-
-/*------
- * Return the POSIX lconv struct (contains number/money formatting information)
- * with locale information for all categories. Note that returned lconv
- * does not depend on currently active category settings, but on external
- * environment variables for locale.
- *------
+ * Return the POSIX lconv struct (contains number/money formatting
+ * information) with locale information for all categories.
*/
extern struct lconv *PGLC_localeconv(void);
-#endif /* USE_LOCALE */
#endif /* _PG_LOCALE_ */