newlocale(3) with base == (locale_t)0

RVP <[email protected]> Thu, 26 Mar 2026 11:16:01 +0000 (UTC)
Newsgroups gmane.os.netbsd.devel.userlevel
Message-ID <[email protected]>
Can someone tell me if NetBSD is non-conforming here, or should only the
newlocale(3) man-page be updated?

SUSv5 says for newlocale(3):

 	If the base argument is (locale_t)0, a new locale object shall
 	be created[...]
 	If a completely new locale object is created, the data for all
 	sections not requested by category_mask shall be taken from the
 	POSIX locale.

and that is what happens on Linux (Debian 13.4.0) and FreeBSD (15.0-RELEASE).
However, the Tribblix 0m39 newlocale(3) says:

 	To create a new locale, the argument base should be passed the
 	special argument (locale_t)0. This will use a copy of the current
 	global locale as a starting point.

So, the base is the _current_ locale, not POSIX, when base == (locale_t)0.
NetBSD has the same behaviour, but, this isn't documented.

Test code follows:

---START---
#ifdef __linux__
#define _GNU_SOURCE
#endif
#include <langinfo.h>
#include <stdio.h>
#include <stdlib.h>
#ifdef __FreeBSD__
#include <xlocale.h>
#else
#include <locale.h>
#endif

int
main(void)
{
 	locale_t nl;

 	/*
 	 * es_ES -> es_ES
 	 */

 	setlocale(LC_ALL, "es_ES.UTF-8");	/* must have locale files */
 	printf("%s\n", localeconv()->decimal_point);	/* , */
 	printf("%f\n", strtod("0,987654", NULL));	/* 0,987654 */

 	/*
 	 * C -> es_ES
 	 */

 	/* use LC_NUMERIC_MASK on NetBSD & Tribblix 0m39 */
 	nl = newlocale(LC_CTYPE_MASK, "C", (locale_t)0);
 	printf("%s\n", nl_langinfo_l(RADIXCHAR, nl));	/* . or , (nbsd, tribblix) */
 	printf("%f\n", strtod_l("0.987654", NULL, nl));	/* expect: 0,987654 */
 	freelocale(nl);

 	return 0;
}
---END---

-RVP