1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
24 * Use is subject to license terms.
25 */
26
27
28/*
29 * General purpse string manipulation routines
30 */
31
32#include	<stdio.h>
33#include	<_conv.h>
34
35
36/*
37 * Implementation of isspace() that does not require <ctype.h>
38 * or <sys/ctype.h>, appropriate for simple non-localized use.
39 */
40int
41conv_strproc_isspace(int c)
42{
43	return ((c == ' ') || (c == '\t') || (c == '\r') || (c == '\n'));
44}
45
46/*
47 * Remove leading and trailing whitespace from the given string.
48 *
49 * entry:
50 *	str - String to be trimmed
51 *
52 * exit:
53 *	The pointer to the trimmed string is returned.
54 *
55 * note:
56 *	Leading whitespace is trimmed by advancing the given str pointer,
57 *	and not by making a copy or allocing more memory. Hence, the caller
58 *	should retain a copy of the original str pointer if they need to
59 *	free the original memory or otherwise access it.
60 *
61 *	Trailing whitespace is trimmed by inserting a NULL termination
62 *	in the position at which the first trailing whitespce character
63 *	lies. This routine can therefore modify the memory used by
64 *	the input string.
65 */
66char *
67conv_strproc_trim(char *str)
68{
69	char	*tail;
70
71	/* Skip leading whitespace */
72	while (conv_strproc_isspace(*str))
73		str++;
74
75	/* Back up over trailing whitespace */
76	tail = str + strlen(str);
77	while ((tail > str) && conv_strproc_isspace(*(tail - 1)))
78		tail--;
79	*tail = '\0';
80
81	return (str);
82}
83
84/*
85 * Given a debug token of the form:
86 *
87 *	token=value
88 *
89 * extract and return a pointer to the value.
90 *
91 * entry:
92 *	str - String to process
93 *	token_len = Length of the token, not counting the '=' character,
94 *		or any whitespace between the token and the '='.
95 *	to_upper - True to convert the returned value to upper case.
96 *	value - Address of pointer to receive the value string.
97 *
98 * exit:
99 *	On success, *value is updated to point at the value string,
100 *	and True (1) is returned. On failure, False (0) is returned.
101 *
102 * note:
103 *	If CONV_SPEXV_F_UCASE is specified, this routine modifies
104 *	the memory pointed at by str.
105 */
106Boolean
107conv_strproc_extract_value(char *str, size_t token_len, int flags,
108    const char **value)
109{
110	int	trim = (flags & CONV_SPEXV_F_NOTRIM) == 0;
111
112	/* Skip the token */
113	str += token_len;
114
115	/*
116	 * If TRIM, skip whitespace between token and '='
117	 */
118	if (trim)
119		while (conv_strproc_isspace(*str))
120			str++;
121
122	/* If there's not a '=' here, this isn't the token we thought it was */
123	if (*str != '=')
124		return (FALSE);
125
126	str++;			/* skip the '=' */
127
128	/* if TRIM, skip whitespace following the '=' */
129	if (trim)
130		while (conv_strproc_isspace(*str))
131			str++;
132
133	/* Null value and it's not OK? Make it an error. */
134	if (((flags & CONV_SPEXV_F_NULLOK) == 0) && (*str == '\0'))
135		return (FALSE);
136
137	*value = str;
138
139	/* Convert to uppercase on request */
140	if (flags & CONV_SPEXV_F_UCASE)
141		for (; *str; str++)
142			if ((*str >= 'a') && (*str <= 'z'))
143				*str = *str - ('a' - 'A');
144
145	return (TRUE);
146}
147