Print this page
2964 need POSIX 2008 locale object support
Reviewed by: Robert Mustacchi <rm@joyent.com>
Split |
Close |
Expand all |
Collapse all |
--- old/usr/src/lib/libc/port/locale/ldpart.c
+++ new/usr/src/lib/libc/port/locale/ldpart.c
1 1 /*
2 + * Copyright 2013 Garrett D'Amore <garrett@damore.org>
2 3 * Copyright 2010 Nexenta Systems, Inc. All rights reserved.
3 4 * Copyright (c) 2000, 2001 Alexey Zelkin <phantom@FreeBSD.org>
4 5 * All rights reserved.
5 6 *
6 7 * Redistribution and use in source and binary forms, with or without
7 8 * modification, are permitted provided that the following conditions
8 9 * are met:
9 10 * 1. Redistributions of source code must retain the above copyright
10 11 * notice, this list of conditions and the following disclaimer.
11 12 * 2. Redistributions in binary form must reproduce the above copyright
12 13 * notice, this list of conditions and the following disclaimer in the
13 14 * documentation and/or other materials provided with the distribution.
14 15 *
15 16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19 20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21 22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 26 * SUCH DAMAGE.
26 27 */
27 28
28 29 #include "lint.h"
29 30 #include "file64.h"
30 31 #include <sys/types.h>
31 32 #include <sys/stat.h>
32 33 #include <errno.h>
33 34 #include <fcntl.h>
34 35 #include <limits.h>
35 36 #include <stdlib.h>
↓ open down ↓ |
24 lines elided |
↑ open up ↑ |
36 37 #include <string.h>
37 38 #include <unistd.h>
38 39 #include <stdio.h>
39 40
40 41 #include "ldpart.h"
41 42 #include "setlocale.h"
42 43
43 44 static int split_lines(char *, const char *);
44 45
45 46 int
46 -__part_load_locale(const char *name, int *using_locale,
47 +__part_load_locale(const char *name,
47 48 char **locale_buf, const char *category_filename,
48 49 int locale_buf_size_max, int locale_buf_size_min,
49 50 const char **dst_localebuf)
50 51 {
51 52 int saverr, fd, i, num_lines;
52 53 char *lbuf, *p;
53 54 const char *plim;
54 55 char filename[PATH_MAX];
55 56 struct stat st;
56 57 size_t namesize, bufsize;
57 58
58 - /* 'name' must be already checked. */
59 - if (strcmp(name, "C") == 0 || strcmp(name, "POSIX") == 0) {
60 - *using_locale = 0;
61 - return (_LDP_CACHE);
62 - }
63 -
64 59 /*
65 - * If the locale name is the same as our cache, use the cache.
66 - */
67 - if (*locale_buf != NULL && strcmp(name, *locale_buf) == 0) {
68 - *using_locale = 1;
69 - return (_LDP_CACHE);
70 - }
71 -
72 - /*
73 60 * Slurp the locale file into the cache.
74 61 */
75 62 namesize = strlen(name) + 1;
76 63
77 64 /* 'PathLocale' must be already set & checked. */
78 65
79 66 (void) snprintf(filename, sizeof (filename), "%s/%s/%s/LCL_DATA",
80 67 _PathLocale, name, category_filename);
81 68
82 69 if ((fd = open(filename, O_RDONLY)) < 0)
83 70 return (_LDP_ERROR);
84 71 if (fstat(fd, &st) != 0)
85 72 goto bad_locale;
86 73 if (st.st_size <= 0) {
87 74 errno = EINVAL;
88 75 goto bad_locale;
89 76 }
90 77 bufsize = namesize + st.st_size;
91 78 if ((lbuf = malloc(bufsize)) == NULL) {
92 79 errno = ENOMEM;
93 80 goto bad_locale;
94 81 }
95 82 (void) strcpy(lbuf, name);
96 83 p = lbuf + namesize;
97 84 plim = p + st.st_size;
98 85 if (read(fd, p, (size_t)st.st_size) != st.st_size)
99 86 goto bad_lbuf;
100 87 /*
101 88 * Parse the locale file into localebuf.
102 89 */
103 90 if (plim[-1] != '\n') {
104 91 errno = EINVAL;
105 92 goto bad_lbuf;
106 93 }
107 94 num_lines = split_lines(p, plim);
108 95 if (num_lines >= locale_buf_size_max)
109 96 num_lines = locale_buf_size_max;
↓ open down ↓ |
27 lines elided |
↑ open up ↑ |
110 97 else if (num_lines >= locale_buf_size_min)
111 98 num_lines = locale_buf_size_min;
112 99 else {
113 100 errno = EINVAL;
114 101 goto bad_lbuf;
115 102 }
116 103 (void) close(fd);
117 104 /*
118 105 * Record the successful parse in the cache.
119 106 */
120 - if (*locale_buf != NULL)
121 - free(*locale_buf);
122 107 *locale_buf = lbuf;
123 108 for (p = *locale_buf, i = 0; i < num_lines; i++)
124 109 dst_localebuf[i] = (p += strlen(p) + 1);
125 110 for (i = num_lines; i < locale_buf_size_max; i++)
126 111 dst_localebuf[i] = NULL;
127 - *using_locale = 1;
128 112
129 113 return (_LDP_LOADED);
130 114
131 115 bad_lbuf:
132 116 saverr = errno;
133 117 free(lbuf);
134 118 errno = saverr;
135 119 bad_locale:
136 120 saverr = errno;
137 121 (void) close(fd);
138 122 errno = saverr;
139 123
140 124 return (_LDP_ERROR);
141 125 }
142 126
143 127 static int
144 128 split_lines(char *p, const char *plim)
145 129 {
146 130 int i;
147 131
148 132 i = 0;
149 133 while (p < plim) {
150 134 if (*p == '\n') {
151 135 *p = '\0';
152 136 i++;
153 137 }
154 138 p++;
155 139 }
156 140 return (i);
157 141 }
↓ open down ↓ |
20 lines elided |
↑ open up ↑ |
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX