Re: initdb failure in CVS - Mailing list pgsql-hackers
From | Andrew Dunstan |
---|---|
Subject | Re: initdb failure in CVS |
Date | |
Msg-id | 40994A10.7090802@dunslane.net Whole thread Raw |
In response to | initdb failure in CVS (Bruce Momjian <pgman@candle.pha.pa.us>) |
Responses |
Re: initdb failure in CVS
|
List | pgsql-hackers |
Bruce Momjian wrote: >I am seeing the following failure of initdb in CVS: > > The files belonging to this database system will be owned by user "postgres". > This user must also own the server process. > > The database cluster will be initialized with locale C. > > creating directory /u/pg/data ... ok > creating directory /u/pg/data/global ... ok > creating directory /u/pg/data/pg_xlog ... ok > creating directory /u/pg/data/pg_clog ... ok > creating directory /u/pg/data/base ... ok > creating directory /u/pg/data/base/1 ... ok > selecting default max_connections ... 100 > selecting default shared_buffers ... 1000 > creating configuration files ... ok > > creating template1 database in /u/pg/data/base/1 ... > > FATAL: invalid value for parameter "client_encoding": "" > > initdb: child process exited with exit code 1 > initdb: failed > initdb: removing data directory "/u/pg/data" > >The problem seems to be related to a commit made to initdb a few days >ago. > > revision 1.24 > date: 2004/05/05 16:09:31; author: tgl; state: Exp; lines: +23 -2 > Use a more portable technique for unsetting environment variables, > and unset PGCLIENTENCODING to prevent backend from dying if it's set > to something incompatible with the -E option. > >I don't have any encoding set in my system. > > > The change is based on this code from here (backend/commands/variable.c): /* * unsetenv() works fine, but is BSD, not POSIX, and is not available * under Solaris, among others. Apparently putenv() called as below * clears the process-specific environment variables. Other * reasonable arguments to putenv() (e.g. "TZ=", "TZ", "") result in a * core dump (under Linux anyway). - thomas 1998-01-26 */ if (tzbuf[0] == 'T') { strcpy(tzbuf, "="); if (putenv(tzbuf) != 0) elog(LOG, "could not clear TZ environment variable"); tzset(); } The Linux man page for putenv says this: Description for libc4, libc5, glibc: If the argument string is of the form name, and does not contain an ‘=’ character, then the variable name is removed from the environment. If putenv() has to allocate a new array environ, and the previous array was also allocated by putenv(), then it will be freed. In no case will the old storage asso- ciated to the environment variable itself be freed. The libc4 and libc5 and glibc 2.1.2 versions conform to SUSv2: the pointer string given to putenv() is used. In particular, this string becomes part of the environment; changing it later will change the environment. (Thus, it is an error is to call putenv() with an auto- matic variable as the argument, then return from the calling function while string is still part of the environment.) However, glibc 2.0-2.1.1 differs: a copy of the string is used. On the one hand this causes a memory leak, and on the other hand it violates SUSv2. This has been fixed in glibc2.1.2. The BSD4.4 version, like glibc 2.0, uses a copy. I suspect you have seen this latter effect, i.e. it in effect did putenv("PGCLIENTENCODING="); putenv("="); leaving you with an empty string as the env value rather than unsetting it. Did we actually find a current system where it broke with a straight putenv("LC_ALL")? cheers andrew
pgsql-hackers by date: