Skip to content

Commit 3c45ca2

Browse files
committed
Handle Linux extra locale categories
Linux has six locale categories that aren't in the POSIX standard. This commit enables their use. For example there is meta data about a locale, and information about how telephone numbers are formatted for it. On non-Linux boxes, you can now request them as well, but you will get stub values, as if the locale were C.
1 parent c23c19c commit 3c45ca2

File tree

10 files changed

+681
-16
lines changed

10 files changed

+681
-16
lines changed

ext/I18N-Langinfo/Langinfo.pm

+153
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,46 @@ our @EXPORT_OK = qw(
6868
T_FMT_AMPM
6969
YESEXPR
7070
YESSTR
71+
_NL_ADDRESS_POSTAL_FMT
72+
_NL_ADDRESS_COUNTRY_NAME
73+
_NL_ADDRESS_COUNTRY_POST
74+
_NL_ADDRESS_COUNTRY_AB2
75+
_NL_ADDRESS_COUNTRY_AB3
76+
_NL_ADDRESS_COUNTRY_CAR
77+
_NL_ADDRESS_COUNTRY_NUM
78+
_NL_ADDRESS_COUNTRY_ISBN
79+
_NL_ADDRESS_LANG_NAME
80+
_NL_ADDRESS_LANG_AB
81+
_NL_ADDRESS_LANG_TERM
82+
_NL_ADDRESS_LANG_LIB
83+
_NL_IDENTIFICATION_TITLE
84+
_NL_IDENTIFICATION_SOURCE
85+
_NL_IDENTIFICATION_ADDRESS
86+
_NL_IDENTIFICATION_CONTACT
87+
_NL_IDENTIFICATION_EMAIL
88+
_NL_IDENTIFICATION_TEL
89+
_NL_IDENTIFICATION_FAX
90+
_NL_IDENTIFICATION_LANGUAGE
91+
_NL_IDENTIFICATION_TERRITORY
92+
_NL_IDENTIFICATION_AUDIENCE
93+
_NL_IDENTIFICATION_APPLICATION
94+
_NL_IDENTIFICATION_ABBREVIATION
95+
_NL_IDENTIFICATION_REVISION
96+
_NL_IDENTIFICATION_DATE
97+
_NL_IDENTIFICATION_CATEGORY
98+
_NL_MEASUREMENT_MEASUREMENT
99+
_NL_NAME_NAME_FMT
100+
_NL_NAME_NAME_GEN
101+
_NL_NAME_NAME_MR
102+
_NL_NAME_NAME_MRS
103+
_NL_NAME_NAME_MISS
104+
_NL_NAME_NAME_MS
105+
_NL_PAPER_HEIGHT
106+
_NL_PAPER_WIDTH
107+
_NL_TELEPHONE_TEL_INT_FMT
108+
_NL_TELEPHONE_TEL_DOM_FMT
109+
_NL_TELEPHONE_INT_SELECT
110+
_NL_TELEPHONE_INT_PREFIX
71111
);
72112

73113
our $VERSION = '0.23';
@@ -209,6 +249,114 @@ For the eras based on typically some ruler, such as the Japanese Emperor
209249
210250
=back
211251
252+
In addition, Linux boxes have extra items, as follows. (When called from
253+
other platform types, these return a stub value, of not much use.)
254+
255+
=over
256+
257+
=item C<_NL_ADDRESS_POSTAL_FMT>
258+
259+
=item C<_NL_ADDRESS_COUNTRY_NAME>
260+
261+
=item C<_NL_ADDRESS_COUNTRY_POST>
262+
263+
=item C<_NL_ADDRESS_COUNTRY_AB2>
264+
265+
=item C<_NL_ADDRESS_COUNTRY_AB3>
266+
267+
=item C<_NL_ADDRESS_COUNTRY_CAR>
268+
269+
=item C<_NL_ADDRESS_COUNTRY_NUM>
270+
271+
=item C<_NL_ADDRESS_COUNTRY_ISBN>
272+
273+
=item C<_NL_ADDRESS_LANG_NAME>
274+
275+
=item C<_NL_ADDRESS_LANG_AB>
276+
277+
=item C<_NL_ADDRESS_LANG_TERM>
278+
279+
=item C<_NL_ADDRESS_LANG_LIB>
280+
281+
On Linux boxes, these return information about the country for the current
282+
locale. Further information is found in F<langinfo.h>
283+
284+
=item C<_NL_IDENTIFICATION_TITLE>
285+
286+
=item C<_NL_IDENTIFICATION_SOURCE>
287+
288+
=item C<_NL_IDENTIFICATION_ADDRESS>
289+
290+
=item C<_NL_IDENTIFICATION_CONTACT>
291+
292+
=item C<_NL_IDENTIFICATION_EMAIL>
293+
294+
=item C<_NL_IDENTIFICATION_TEL>
295+
296+
=item C<_NL_IDENTIFICATION_FAX>
297+
298+
=item C<_NL_IDENTIFICATION_LANGUAGE>
299+
300+
=item C<_NL_IDENTIFICATION_TERRITORY>
301+
302+
=item C<_NL_IDENTIFICATION_AUDIENCE>
303+
304+
=item C<_NL_IDENTIFICATION_APPLICATION>
305+
306+
=item C<_NL_IDENTIFICATION_ABBREVIATION>
307+
308+
=item C<_NL_IDENTIFICATION_REVISION>
309+
310+
=item C<_NL_IDENTIFICATION_DATE>
311+
312+
=item C<_NL_IDENTIFICATION_CATEGORY>
313+
314+
On Linux boxes, these return meta information about the current locale,
315+
such as how to get in touch with its maintainers.
316+
Further information is found in F<langinfo.h>
317+
318+
=item C<_NL_MEASUREMENT_MEASUREMENT>
319+
320+
On Linux boxes, it returns 1 if the metric system of measurement prevails in
321+
the locale; or 2 if US customary units prevail.
322+
323+
=item C<_NL_NAME_NAME_FMT>
324+
325+
=item C<_NL_NAME_NAME_GEN>
326+
327+
=item C<_NL_NAME_NAME_MR>
328+
329+
=item C<_NL_NAME_NAME_MRS>
330+
331+
=item C<_NL_NAME_NAME_MISS>
332+
333+
=item C<_NL_NAME_NAME_MS>
334+
335+
On Linux boxes, these return information about how names are formatted and
336+
the personal salutations used in the current locale. Further information
337+
is found in L<locale(7)> and F<langinfo.h>
338+
339+
=item C<_NL_PAPER_HEIGHT>
340+
341+
=item C<_NL_PAPER_WIDTH>
342+
343+
On Linux boxes, these return the standard size of sheets of paper (in
344+
millimeters) in the current locale.
345+
346+
=item C<_NL_TELEPHONE_TEL_INT_FMT>
347+
348+
=item C<_NL_TELEPHONE_TEL_DOM_FMT>
349+
350+
=item C<_NL_TELEPHONE_INT_SELECT>
351+
352+
=item C<_NL_TELEPHONE_INT_PREFIX>
353+
354+
On Linux boxes, these return information about how telephone numbers are
355+
formatted (both domestically and international calling) in the current locale.
356+
Further information is found in F<langinfo.h>
357+
358+
=back
359+
212360
=head2 For systems without C<nl_langinfo>
213361
214362
This module originally was just a wrapper for the libc C<nl_langinfo>
@@ -275,6 +423,11 @@ L<https://github.com/Perl/perl5/issues>.
275423
These are derived by using C<strftime()>, and not all versions of that function
276424
know about them. C<""> is returned for these on such systems.
277425
426+
=item All C<_NL_I<foo>> items
427+
428+
These return the same values as they do on boxes that don't have the
429+
appropriate underlying locale categories.
430+
278431
=back
279432
280433
See your L<nl_langinfo(3)> for more information about the available

ext/I18N-Langinfo/Langinfo.xs

+1-9
Original file line numberDiff line numberDiff line change
@@ -26,15 +26,7 @@ langinfo(code)
2626
int code
2727
PROTOTYPE: _
2828
CODE:
29-
#ifdef HAS_NL_LANGINFO
30-
if (code < 0) {
31-
SETERRNO(EINVAL, LIB_INVARG);
32-
RETVAL = &PL_sv_undef;
33-
} else
34-
#endif
35-
{
36-
RETVAL = sv_langinfo(code);
37-
}
29+
RETVAL = sv_langinfo(code);
3830

3931
OUTPUT:
4032
RETVAL

ext/I18N-Langinfo/Makefile.PL

+43-2
Original file line numberDiff line numberDiff line change
@@ -14,15 +14,56 @@ WriteMakefile(
1414
my @names = 'CODESET'; # CODESET isn't an enum in old glibc's langinfo.h
1515
push @names, # This lot are always enums in old langinfo.h:
1616
{name=>$_, type=>"IV",
17-
macro=>["#if defined($_) || (defined(__GNU_LIBRARY__) && defined(_NL_ITEM))\n",
17+
macro=>["#if defined($_) || (defined(_NL_ITEM))\n",
1818
"#endif\n"]}
1919
foreach qw (ABDAY_1 ABDAY_2 ABDAY_3 ABDAY_4 ABDAY_5 ABDAY_6 ABDAY_7
2020
ABMON_1 ABMON_10 ABMON_11 ABMON_12 ABMON_2 ABMON_3 ABMON_4
2121
ABMON_5 ABMON_6 ABMON_7 ABMON_8 ABMON_9 ALT_DIGITS AM_STR
2222
DAY_1 DAY_2 DAY_3 DAY_4 DAY_5 DAY_6 DAY_7 D_FMT D_T_FMT ERA
2323
ERA_D_FMT ERA_D_T_FMT ERA_T_FMT MON_1 MON_10 MON_11 MON_12
2424
MON_2 MON_3 MON_4 MON_5 MON_6 MON_7 MON_8 MON_9 NOEXPR NOSTR
25-
PM_STR T_FMT T_FMT_AMPM YESEXPR YESSTR);
25+
PM_STR T_FMT T_FMT_AMPM YESEXPR YESSTR
26+
_NL_ADDRESS_POSTAL_FMT
27+
_NL_ADDRESS_COUNTRY_NAME
28+
_NL_ADDRESS_COUNTRY_POST
29+
_NL_ADDRESS_COUNTRY_AB2
30+
_NL_ADDRESS_COUNTRY_AB3
31+
_NL_ADDRESS_COUNTRY_CAR
32+
_NL_ADDRESS_COUNTRY_NUM
33+
_NL_ADDRESS_COUNTRY_ISBN
34+
_NL_ADDRESS_LANG_NAME
35+
_NL_ADDRESS_LANG_AB
36+
_NL_ADDRESS_LANG_TERM
37+
_NL_ADDRESS_LANG_LIB
38+
_NL_IDENTIFICATION_TITLE
39+
_NL_IDENTIFICATION_SOURCE
40+
_NL_IDENTIFICATION_ADDRESS
41+
_NL_IDENTIFICATION_CONTACT
42+
_NL_IDENTIFICATION_EMAIL
43+
_NL_IDENTIFICATION_TEL
44+
_NL_IDENTIFICATION_FAX
45+
_NL_IDENTIFICATION_LANGUAGE
46+
_NL_IDENTIFICATION_TERRITORY
47+
_NL_IDENTIFICATION_AUDIENCE
48+
_NL_IDENTIFICATION_APPLICATION
49+
_NL_IDENTIFICATION_ABBREVIATION
50+
_NL_IDENTIFICATION_REVISION
51+
_NL_IDENTIFICATION_DATE
52+
_NL_IDENTIFICATION_CATEGORY
53+
_NL_MEASUREMENT_MEASUREMENT
54+
_NL_NAME_NAME_FMT
55+
_NL_NAME_NAME_GEN
56+
_NL_NAME_NAME_MR
57+
_NL_NAME_NAME_MRS
58+
_NL_NAME_NAME_MISS
59+
_NL_NAME_NAME_MS
60+
_NL_PAPER_HEIGHT
61+
_NL_PAPER_WIDTH
62+
_NL_TELEPHONE_TEL_INT_FMT
63+
_NL_TELEPHONE_TEL_DOM_FMT
64+
_NL_TELEPHONE_INT_SELECT
65+
_NL_TELEPHONE_INT_PREFIX
66+
);
2667
push @names, # This lot are only enums for __SVR4_I386_ABI_L1__:
2768
{name=>$_, type=>"IV",
2869
macro=>["#if defined($_) || (defined(__GNU_LIBRARY__) && defined(_NL_ITEM) && defined(__SVR4_I386_ABI_L1__))\n",

ext/I18N-Langinfo/t/Langinfo.t

+52-1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,13 @@ my %want = ( RADIXCHAR => qr/ ^ \. $ /x,
2222
# these. In the C locale, there is nothing after the first
2323
# character.
2424
CRNCYSTR => qr/ ^ [+-.]? $ /x,
25+
26+
_NL_ADDRESS_COUNTRY_NUM => qr/^ 0 $/x,
27+
_NL_IDENTIFICATION_TERRITORY => qr/ ^ ISO $/x,
28+
_NL_MEASUREMENT_MEASUREMENT => qr/ ^ [01] $/x,
29+
_NL_PAPER_HEIGHT => qr/^ \d+ $/x,
30+
_NL_NAME_NAME_GEN => qr/ .* /x,
31+
_NL_TELEPHONE_INT_SELECT => qr/ .* /x,
2532
);
2633

2734
# Abbreviated and full are swapped in many locales in early netbsd. Skip
@@ -145,7 +152,51 @@ sub check_utf8_validity($$$) {
145152
my @want = sort keys %want;
146153
my @illegal_utf8;
147154

148-
use_ok('I18N::Langinfo', 'langinfo', @constants, 'CRNCYSTR');
155+
my %extra_items = (
156+
_NL_ADDRESS_POSTAL_FMT => 'LC_ADDRESS',
157+
_NL_ADDRESS_COUNTRY_NAME => 'LC_ADDRESS',
158+
_NL_ADDRESS_COUNTRY_POST => 'LC_ADDRESS',
159+
_NL_ADDRESS_COUNTRY_AB2 => 'LC_ADDRESS',
160+
_NL_ADDRESS_COUNTRY_AB3 => 'LC_ADDRESS',
161+
_NL_ADDRESS_COUNTRY_CAR => 'LC_ADDRESS',
162+
_NL_ADDRESS_COUNTRY_NUM => 'LC_ADDRESS',
163+
_NL_ADDRESS_COUNTRY_ISBN => 'LC_ADDRESS',
164+
_NL_ADDRESS_LANG_NAME => 'LC_ADDRESS',
165+
_NL_ADDRESS_LANG_AB => 'LC_ADDRESS',
166+
_NL_ADDRESS_LANG_TERM => 'LC_ADDRESS',
167+
_NL_ADDRESS_LANG_LIB => 'LC_ADDRESS',
168+
_NL_IDENTIFICATION_TITLE => 'LC_IDENTIFICATION',
169+
_NL_IDENTIFICATION_SOURCE => 'LC_IDENTIFICATION',
170+
_NL_IDENTIFICATION_ADDRESS => 'LC_IDENTIFICATION',
171+
_NL_IDENTIFICATION_CONTACT => 'LC_IDENTIFICATION',
172+
_NL_IDENTIFICATION_EMAIL => 'LC_IDENTIFICATION',
173+
_NL_IDENTIFICATION_TEL => 'LC_IDENTIFICATION',
174+
_NL_IDENTIFICATION_FAX => 'LC_IDENTIFICATION',
175+
_NL_IDENTIFICATION_LANGUAGE => 'LC_IDENTIFICATION',
176+
_NL_IDENTIFICATION_TERRITORY => 'LC_IDENTIFICATION',
177+
_NL_IDENTIFICATION_AUDIENCE => 'LC_IDENTIFICATION',
178+
_NL_IDENTIFICATION_APPLICATION => 'LC_IDENTIFICATION',
179+
_NL_IDENTIFICATION_ABBREVIATION => 'LC_IDENTIFICATION',
180+
_NL_IDENTIFICATION_REVISION => 'LC_IDENTIFICATION',
181+
_NL_IDENTIFICATION_DATE => 'LC_IDENTIFICATION',
182+
_NL_IDENTIFICATION_CATEGORY => 'LC_IDENTIFICATION',
183+
_NL_MEASUREMENT_MEASUREMENT => 'LC_MEASUREMENT',
184+
_NL_NAME_NAME_FMT => 'LC_NAME',
185+
_NL_NAME_NAME_GEN => 'LC_NAME',
186+
_NL_NAME_NAME_MR => 'LC_NAME',
187+
_NL_NAME_NAME_MRS => 'LC_NAME',
188+
_NL_NAME_NAME_MISS => 'LC_NAME',
189+
_NL_NAME_NAME_MS => 'LC_NAME',
190+
_NL_PAPER_HEIGHT => 'LC_PAPER',
191+
_NL_PAPER_WIDTH => 'LC_PAPER',
192+
_NL_TELEPHONE_TEL_INT_FMT => 'LC_TELEPHONE',
193+
_NL_TELEPHONE_TEL_DOM_FMT => 'LC_TELEPHONE',
194+
_NL_TELEPHONE_INT_SELECT => 'LC_TELEPHONE',
195+
_NL_TELEPHONE_INT_PREFIX => 'LC_TELEPHONE',
196+
);
197+
198+
use_ok('I18N::Langinfo', 'langinfo', @constants, 'CRNCYSTR',
199+
keys %extra_items);
149200

150201
use POSIX;
151202

ext/XS-APItest/t/locale.t

+40
Original file line numberDiff line numberDiff line change
@@ -151,6 +151,46 @@ my %correct_C_responses = (
151151
T_FMT_AMPM => undef,
152152
YESEXPR => undef,
153153
YESSTR => undef,
154+
_NL_ADDRESS_POSTAL_FMT => undef,
155+
_NL_ADDRESS_COUNTRY_NAME => undef,
156+
_NL_ADDRESS_COUNTRY_POST => undef,
157+
_NL_ADDRESS_COUNTRY_AB2 => undef,
158+
_NL_ADDRESS_COUNTRY_AB3 => undef,
159+
_NL_ADDRESS_COUNTRY_CAR => undef,
160+
_NL_ADDRESS_COUNTRY_NUM => 0,
161+
_NL_ADDRESS_COUNTRY_ISBN => undef,
162+
_NL_ADDRESS_LANG_NAME => undef,
163+
_NL_ADDRESS_LANG_AB => undef,
164+
_NL_ADDRESS_LANG_TERM => undef,
165+
_NL_ADDRESS_LANG_LIB => undef,
166+
_NL_IDENTIFICATION_TITLE => undef,
167+
_NL_IDENTIFICATION_SOURCE => undef,
168+
_NL_IDENTIFICATION_ADDRESS => undef,
169+
_NL_IDENTIFICATION_CONTACT => undef,
170+
_NL_IDENTIFICATION_EMAIL => undef,
171+
_NL_IDENTIFICATION_TEL => undef,
172+
_NL_IDENTIFICATION_FAX => undef,
173+
_NL_IDENTIFICATION_LANGUAGE => undef,
174+
_NL_IDENTIFICATION_TERRITORY => "ISO",
175+
_NL_IDENTIFICATION_AUDIENCE => undef,
176+
_NL_IDENTIFICATION_APPLICATION => undef,
177+
_NL_IDENTIFICATION_ABBREVIATION => undef,
178+
_NL_IDENTIFICATION_REVISION => undef,
179+
_NL_IDENTIFICATION_DATE => undef,
180+
_NL_IDENTIFICATION_CATEGORY => undef,
181+
_NL_MEASUREMENT_MEASUREMENT => undef,
182+
_NL_NAME_NAME_FMT => undef,
183+
_NL_NAME_NAME_GEN => undef,
184+
_NL_NAME_NAME_MR => undef,
185+
_NL_NAME_NAME_MRS => undef,
186+
_NL_NAME_NAME_MISS => undef,
187+
_NL_NAME_NAME_MS => undef,
188+
_NL_PAPER_HEIGHT => undef,
189+
_NL_PAPER_WIDTH => undef,
190+
_NL_TELEPHONE_TEL_INT_FMT => undef,
191+
_NL_TELEPHONE_TEL_DOM_FMT => undef,
192+
_NL_TELEPHONE_INT_SELECT => undef,
193+
_NL_TELEPHONE_INT_PREFIX => undef,
154194
);
155195

156196
my $hdr = "../../perl_langinfo.h";

0 commit comments

Comments
 (0)