xref: /titanic_44/usr/src/lib/libnsl/nss/parse.c (revision 7c478bd95313f5f23a4c958a745db2134aa03244)
1*7c478bd9Sstevel@tonic-gate /*
2*7c478bd9Sstevel@tonic-gate  * CDDL HEADER START
3*7c478bd9Sstevel@tonic-gate  *
4*7c478bd9Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*7c478bd9Sstevel@tonic-gate  * Common Development and Distribution License, Version 1.0 only
6*7c478bd9Sstevel@tonic-gate  * (the "License").  You may not use this file except in compliance
7*7c478bd9Sstevel@tonic-gate  * with the License.
8*7c478bd9Sstevel@tonic-gate  *
9*7c478bd9Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10*7c478bd9Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
11*7c478bd9Sstevel@tonic-gate  * See the License for the specific language governing permissions
12*7c478bd9Sstevel@tonic-gate  * and limitations under the License.
13*7c478bd9Sstevel@tonic-gate  *
14*7c478bd9Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
15*7c478bd9Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16*7c478bd9Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
17*7c478bd9Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
18*7c478bd9Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
19*7c478bd9Sstevel@tonic-gate  *
20*7c478bd9Sstevel@tonic-gate  * CDDL HEADER END
21*7c478bd9Sstevel@tonic-gate  */
22*7c478bd9Sstevel@tonic-gate /*
23*7c478bd9Sstevel@tonic-gate  * Copyright (c) 1999 by Sun Microsystems, Inc.
24*7c478bd9Sstevel@tonic-gate  * All rights reserved.
25*7c478bd9Sstevel@tonic-gate  */
26*7c478bd9Sstevel@tonic-gate 
27*7c478bd9Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
28*7c478bd9Sstevel@tonic-gate 
29*7c478bd9Sstevel@tonic-gate #include <stdio.h>
30*7c478bd9Sstevel@tonic-gate #include <stdlib.h>
31*7c478bd9Sstevel@tonic-gate #include <strings.h>
32*7c478bd9Sstevel@tonic-gate 
33*7c478bd9Sstevel@tonic-gate char *_strpbrk_escape(char *, char *);
34*7c478bd9Sstevel@tonic-gate 
35*7c478bd9Sstevel@tonic-gate /*
36*7c478bd9Sstevel@tonic-gate  * _strtok_escape()
37*7c478bd9Sstevel@tonic-gate  *   Like strtok_r, except we don't break on a token if it is escaped
38*7c478bd9Sstevel@tonic-gate  *   with the escape character (\).
39*7c478bd9Sstevel@tonic-gate  */
40*7c478bd9Sstevel@tonic-gate char *
41*7c478bd9Sstevel@tonic-gate _strtok_escape(char *string, char *sepset, char **lasts)
42*7c478bd9Sstevel@tonic-gate {
43*7c478bd9Sstevel@tonic-gate 	char	*q, *r;
44*7c478bd9Sstevel@tonic-gate 
45*7c478bd9Sstevel@tonic-gate 	/* first or subsequent call */
46*7c478bd9Sstevel@tonic-gate 	if (string == NULL)
47*7c478bd9Sstevel@tonic-gate 		string = *lasts;
48*7c478bd9Sstevel@tonic-gate 
49*7c478bd9Sstevel@tonic-gate 	if (string == 0)		/* return if no tokens remaining */
50*7c478bd9Sstevel@tonic-gate 		return (NULL);
51*7c478bd9Sstevel@tonic-gate 
52*7c478bd9Sstevel@tonic-gate 	if (*string == '\0')		/* return if no tokens remaining */
53*7c478bd9Sstevel@tonic-gate 		return (NULL);
54*7c478bd9Sstevel@tonic-gate 
55*7c478bd9Sstevel@tonic-gate 	if ((r = _strpbrk_escape(string, sepset)) == NULL)/* move past token */
56*7c478bd9Sstevel@tonic-gate 		*lasts = 0;	/* indicate this is last token */
57*7c478bd9Sstevel@tonic-gate 	else {
58*7c478bd9Sstevel@tonic-gate 		*r = '\0';
59*7c478bd9Sstevel@tonic-gate 		*lasts = r+1;
60*7c478bd9Sstevel@tonic-gate 	}
61*7c478bd9Sstevel@tonic-gate 	return (string);
62*7c478bd9Sstevel@tonic-gate }
63*7c478bd9Sstevel@tonic-gate 
64*7c478bd9Sstevel@tonic-gate /*
65*7c478bd9Sstevel@tonic-gate  * Return ptr to first occurrence of any non-escaped character from `brkset'
66*7c478bd9Sstevel@tonic-gate  * in the character string `string'; NULL if none exists.
67*7c478bd9Sstevel@tonic-gate  */
68*7c478bd9Sstevel@tonic-gate char *
69*7c478bd9Sstevel@tonic-gate _strpbrk_escape(char *string, char *brkset)
70*7c478bd9Sstevel@tonic-gate {
71*7c478bd9Sstevel@tonic-gate 	const char *p;
72*7c478bd9Sstevel@tonic-gate 	const char *first = string;
73*7c478bd9Sstevel@tonic-gate 
74*7c478bd9Sstevel@tonic-gate 	do {
75*7c478bd9Sstevel@tonic-gate 		for (p = brkset; *p != '\0' && *p != *string; ++p)
76*7c478bd9Sstevel@tonic-gate 			;
77*7c478bd9Sstevel@tonic-gate 		if (p == string)
78*7c478bd9Sstevel@tonic-gate 			return ((char *)string);
79*7c478bd9Sstevel@tonic-gate 		if (*p != '\0') {
80*7c478bd9Sstevel@tonic-gate 			if (*(string-1) != '\\')
81*7c478bd9Sstevel@tonic-gate 				return ((char *)string);
82*7c478bd9Sstevel@tonic-gate 		}
83*7c478bd9Sstevel@tonic-gate 	} while (*string++);
84*7c478bd9Sstevel@tonic-gate 
85*7c478bd9Sstevel@tonic-gate 	return (NULL);
86*7c478bd9Sstevel@tonic-gate }
87*7c478bd9Sstevel@tonic-gate 
88*7c478bd9Sstevel@tonic-gate 
89*7c478bd9Sstevel@tonic-gate char   *
90*7c478bd9Sstevel@tonic-gate _escape(char *s, char *esc)
91*7c478bd9Sstevel@tonic-gate {
92*7c478bd9Sstevel@tonic-gate 	int	nescs = 0;	/* number of escapes to place in s */
93*7c478bd9Sstevel@tonic-gate 	int	i, j;
94*7c478bd9Sstevel@tonic-gate 	int	len_s;
95*7c478bd9Sstevel@tonic-gate 	char	*tmp;
96*7c478bd9Sstevel@tonic-gate 
97*7c478bd9Sstevel@tonic-gate 	if (s == NULL || esc == NULL)
98*7c478bd9Sstevel@tonic-gate 		return (NULL);
99*7c478bd9Sstevel@tonic-gate 
100*7c478bd9Sstevel@tonic-gate 	len_s = strlen(s);
101*7c478bd9Sstevel@tonic-gate 	for (i = 0; i < len_s; i++)
102*7c478bd9Sstevel@tonic-gate 		if (strchr(esc, s[i]))
103*7c478bd9Sstevel@tonic-gate 			nescs++;
104*7c478bd9Sstevel@tonic-gate 	if ((tmp = (char *) malloc(nescs + len_s + 1)) == NULL)
105*7c478bd9Sstevel@tonic-gate 		return (NULL);
106*7c478bd9Sstevel@tonic-gate 	for (i = 0, j = 0; i < len_s; i++) {
107*7c478bd9Sstevel@tonic-gate 		if (strchr(esc, s[i])) {
108*7c478bd9Sstevel@tonic-gate 			tmp[j++] = '\\';
109*7c478bd9Sstevel@tonic-gate 		}
110*7c478bd9Sstevel@tonic-gate 		tmp[j++] = s[i];
111*7c478bd9Sstevel@tonic-gate 	}
112*7c478bd9Sstevel@tonic-gate 	tmp[len_s + nescs] = '\0';
113*7c478bd9Sstevel@tonic-gate 	return (tmp);
114*7c478bd9Sstevel@tonic-gate }
115*7c478bd9Sstevel@tonic-gate 
116*7c478bd9Sstevel@tonic-gate 
117*7c478bd9Sstevel@tonic-gate char *
118*7c478bd9Sstevel@tonic-gate _unescape(char *s, char *esc)
119*7c478bd9Sstevel@tonic-gate {
120*7c478bd9Sstevel@tonic-gate 	int	len_s;
121*7c478bd9Sstevel@tonic-gate 	int	i, j;
122*7c478bd9Sstevel@tonic-gate 	char	*tmp;
123*7c478bd9Sstevel@tonic-gate 
124*7c478bd9Sstevel@tonic-gate 	if (s == NULL || esc == NULL)
125*7c478bd9Sstevel@tonic-gate 		return ((char *)NULL);
126*7c478bd9Sstevel@tonic-gate 
127*7c478bd9Sstevel@tonic-gate 	len_s = strlen(s);
128*7c478bd9Sstevel@tonic-gate 	if ((tmp = (char *) malloc(len_s + 1)) == NULL)
129*7c478bd9Sstevel@tonic-gate 		return ((char *)NULL);
130*7c478bd9Sstevel@tonic-gate 	for (i = 0, j = 0; i < len_s; i++) {
131*7c478bd9Sstevel@tonic-gate 		if (s[i] == '\\' && strchr(esc, s[i + 1]))
132*7c478bd9Sstevel@tonic-gate 			tmp[j++] = s[++i];
133*7c478bd9Sstevel@tonic-gate 		else
134*7c478bd9Sstevel@tonic-gate 			tmp[j++] = s[i];
135*7c478bd9Sstevel@tonic-gate 	}
136*7c478bd9Sstevel@tonic-gate 	tmp[j] = NULL;
137*7c478bd9Sstevel@tonic-gate 	return (tmp);
138*7c478bd9Sstevel@tonic-gate }
139*7c478bd9Sstevel@tonic-gate 
140*7c478bd9Sstevel@tonic-gate char *
141*7c478bd9Sstevel@tonic-gate _strdup_null(char *s)
142*7c478bd9Sstevel@tonic-gate {
143*7c478bd9Sstevel@tonic-gate 	return (strdup(s ? s : ""));
144*7c478bd9Sstevel@tonic-gate }
145*7c478bd9Sstevel@tonic-gate 
146*7c478bd9Sstevel@tonic-gate 
147*7c478bd9Sstevel@tonic-gate /*
148*7c478bd9Sstevel@tonic-gate  * read a line into buffer from a mmap'ed file.
149*7c478bd9Sstevel@tonic-gate  * return length of line read.
150*7c478bd9Sstevel@tonic-gate  */
151*7c478bd9Sstevel@tonic-gate int
152*7c478bd9Sstevel@tonic-gate _readbufline(char *mapbuf,	/* input mmap buffer */
153*7c478bd9Sstevel@tonic-gate     int mapsize,		/* input size */
154*7c478bd9Sstevel@tonic-gate     char *buffer,		/* output storage */
155*7c478bd9Sstevel@tonic-gate     int buflen,			/* output size */
156*7c478bd9Sstevel@tonic-gate     int *lastlen)		/* input read till here last time */
157*7c478bd9Sstevel@tonic-gate {
158*7c478bd9Sstevel@tonic-gate 	int	linelen;
159*7c478bd9Sstevel@tonic-gate 
160*7c478bd9Sstevel@tonic-gate 	while (1) {
161*7c478bd9Sstevel@tonic-gate 		linelen = 0;
162*7c478bd9Sstevel@tonic-gate 		while (linelen < buflen - 1) {	/* "- 1" saves room for \n\0 */
163*7c478bd9Sstevel@tonic-gate 			if (*lastlen >= mapsize) {
164*7c478bd9Sstevel@tonic-gate 				if (linelen == 0 ||
165*7c478bd9Sstevel@tonic-gate 					buffer[linelen - 1] == '\\') {
166*7c478bd9Sstevel@tonic-gate 						return (-1);
167*7c478bd9Sstevel@tonic-gate 					} else {
168*7c478bd9Sstevel@tonic-gate 						buffer[linelen] = '\n';
169*7c478bd9Sstevel@tonic-gate 						buffer[linelen + 1] = '\0';
170*7c478bd9Sstevel@tonic-gate 						return (linelen);
171*7c478bd9Sstevel@tonic-gate 					}
172*7c478bd9Sstevel@tonic-gate 			}
173*7c478bd9Sstevel@tonic-gate 			switch (mapbuf[*lastlen]) {
174*7c478bd9Sstevel@tonic-gate 			case '\n':
175*7c478bd9Sstevel@tonic-gate 				(*lastlen)++;
176*7c478bd9Sstevel@tonic-gate 				if (linelen > 0 &&
177*7c478bd9Sstevel@tonic-gate 				    buffer[linelen - 1] == '\\') {
178*7c478bd9Sstevel@tonic-gate 					--linelen;	/* remove the '\\' */
179*7c478bd9Sstevel@tonic-gate 				} else {
180*7c478bd9Sstevel@tonic-gate 					buffer[linelen] = '\n';
181*7c478bd9Sstevel@tonic-gate 					buffer[linelen + 1] = '\0';
182*7c478bd9Sstevel@tonic-gate 					return (linelen);
183*7c478bd9Sstevel@tonic-gate 				}
184*7c478bd9Sstevel@tonic-gate 				break;
185*7c478bd9Sstevel@tonic-gate 			default:
186*7c478bd9Sstevel@tonic-gate 				buffer[linelen] = mapbuf[*lastlen];
187*7c478bd9Sstevel@tonic-gate 				(*lastlen)++;
188*7c478bd9Sstevel@tonic-gate 				linelen++;
189*7c478bd9Sstevel@tonic-gate 			}
190*7c478bd9Sstevel@tonic-gate 		}
191*7c478bd9Sstevel@tonic-gate 		/* Buffer overflow -- eat rest of line and loop again */
192*7c478bd9Sstevel@tonic-gate 		while (mapbuf[*lastlen] != '\n') {
193*7c478bd9Sstevel@tonic-gate 			if (mapbuf[*lastlen] == EOF) {
194*7c478bd9Sstevel@tonic-gate 				return (-1);
195*7c478bd9Sstevel@tonic-gate 			}
196*7c478bd9Sstevel@tonic-gate 			(*lastlen)++;
197*7c478bd9Sstevel@tonic-gate 		};
198*7c478bd9Sstevel@tonic-gate 	}
199*7c478bd9Sstevel@tonic-gate }
200