xref: /illumos-gate/usr/src/lib/libresolv2/common/irs/getnetent_r.c (revision 581cede61ac9c14d8d4ea452562a567189eead78)
1 /*
2  * Copyright 1999-2002 Sun Microsystems, Inc.  All rights reserved.
3  * Use is subject to license terms.
4  */
5 
6 /*
7  * Copyright (c) 1998-1999 by Internet Software Consortium.
8  *
9  * Permission to use, copy, modify, and distribute this software for any
10  * purpose with or without fee is hereby granted, provided that the above
11  * copyright notice and this permission notice appear in all copies.
12  *
13  * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM DISCLAIMS
14  * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES
15  * OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE
16  * CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
17  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
18  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
19  * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
20  * SOFTWARE.
21  */
22 
23 #pragma ident	"%Z%%M%	%I%	%E% SMI"
24 
25 #if defined(LIBC_SCCS) && !defined(lint)
26 static const char rcsid[] = "$Id: getnetent_r.c,v 8.6 2001/11/01 08:02:11 marka Exp $";
27 #endif /* LIBC_SCCS and not lint */
28 
29 #include <port_before.h>
30 #if !defined(_REENTRANT) || !defined(DO_PTHREADS)
31 	static int getnetent_r_not_required = 0;
32 #else
33 #include <errno.h>
34 #include <string.h>
35 #include <stdio.h>
36 #include <sys/types.h>
37 #include <netinet/in.h>
38 #include <netdb.h>
39 #include <sys/param.h>
40 #include <port_after.h>
41 
42 #ifdef NET_R_RETURN
43 
44 static NET_R_RETURN
45 copy_netent(struct netent *, struct netent *, NET_R_COPY_ARGS);
46 
47 NET_R_RETURN
48 getnetbyname_r(const char *name,  struct netent *nptr, NET_R_ARGS) {
49 	struct netent *ne = getnetbyname(name);
50 #ifdef NET_R_SETANSWER
51 	int n = 0;
52 
53 	if (ne == NULL || (n = copy_netent(ne, nptr, NET_R_COPY)) != 0)
54 		*answerp = NULL;
55 	else
56 		*answerp = ne;
57 	if (ne == NULL)
58 		*h_errnop = h_errno;
59 	return (n);
60 #else
61 	if (ne == NULL)
62 		return (NET_R_BAD);
63 
64 	return (copy_netent(ne, nptr, NET_R_COPY));
65 #endif
66 }
67 
68 #ifndef GETNETBYADDR_ADDR_T
69 #define GETNETBYADDR_ADDR_T long
70 #endif
71 NET_R_RETURN
72 getnetbyaddr_r(GETNETBYADDR_ADDR_T addr, int type, struct netent *nptr, NET_R_ARGS) {
73 	struct netent *ne = getnetbyaddr(addr, type);
74 #ifdef NET_R_SETANSWER
75 	int n = 0;
76 
77 	if (ne == NULL || (n = copy_netent(ne, nptr, NET_R_COPY)) != 0)
78 		*answerp = NULL;
79 	else
80 		*answerp = ne;
81 	if (ne == NULL)
82 		*h_errnop = h_errno;
83 	return (n);
84 #else
85 
86 	if (ne == NULL)
87 		return (NET_R_BAD);
88 
89 	return (copy_netent(ne, nptr, NET_R_COPY));
90 #endif
91 }
92 
93 /*
94  *	These assume a single context is in operation per thread.
95  *	If this is not the case we will need to call irs directly
96  *	rather than through the base functions.
97  */
98 
99 NET_R_RETURN
100 getnetent_r(struct netent *nptr, NET_R_ARGS) {
101 	struct netent *ne = getnetent();
102 #ifdef NET_R_SETANSWER
103 	int n = 0;
104 
105 	if (ne == NULL || (n = copy_netent(ne, nptr, NET_R_COPY)) != 0)
106 		*answerp = NULL;
107 	else
108 		*answerp = ne;
109 	if (ne == NULL)
110 		*h_errnop = h_errno;
111 	return (n);
112 #else
113 
114 	if (ne == NULL)
115 		return (NET_R_BAD);
116 
117 	return (copy_netent(ne, nptr, NET_R_COPY));
118 #endif
119 }
120 
121 NET_R_SET_RETURN
122 #ifdef NET_R_ENT_ARGS
123 setnetent_r(int stay_open, NET_R_ENT_ARGS)
124 #else
125 setnetent_r(int stay_open)
126 #endif
127 {
128 	setnetent(stay_open);
129 #ifdef NET_R_SET_RESULT
130 	return (NET_R_SET_RESULT);
131 #endif
132 }
133 
134 NET_R_END_RETURN
135 #ifdef NET_R_ENT_ARGS
136 endnetent_r(NET_R_ENT_ARGS)
137 #else
138 endnetent_r()
139 #endif
140 {
141 	endnetent();
142 	NET_R_END_RESULT(NET_R_OK);
143 }
144 
145 /* Private */
146 
147 #ifndef NETENT_DATA
148 static NET_R_RETURN
149 copy_netent(struct netent *ne, struct netent *nptr, NET_R_COPY_ARGS) {
150 	char *cp;
151 	int i, n;
152 	int numptr, len;
153 
154 	/* Find out the amount of space required to store the answer. */
155 	numptr = 1; /* NULL ptr */
156 	len = (char *)ALIGN(buf) - buf;
157 	for (i = 0; ne->n_aliases[i]; i++, numptr++) {
158 		len += strlen(ne->n_aliases[i]) + 1;
159 	}
160 	len += strlen(ne->n_name) + 1;
161 	len += numptr * sizeof(char*);
162 
163 	if (len > (int)buflen) {
164 		errno = ERANGE;
165 		return (NET_R_BAD);
166 	}
167 
168 	/* copy net value and type */
169 	nptr->n_addrtype = ne->n_addrtype;
170 	nptr->n_net = ne->n_net;
171 
172 	cp = (char *)ALIGN(buf) + numptr * sizeof(char *);
173 
174 	/* copy official name */
175 	n = strlen(ne->n_name) + 1;
176 	strcpy(cp, ne->n_name);
177 	nptr->n_name = cp;
178 	cp += n;
179 
180 	/* copy aliases */
181 	nptr->n_aliases = (char **)ALIGN(buf);
182 	for (i = 0 ; ne->n_aliases[i]; i++) {
183 		n = strlen(ne->n_aliases[i]) + 1;
184 		strcpy(cp, ne->n_aliases[i]);
185 		nptr->n_aliases[i] = cp;
186 		cp += n;
187 	}
188 	nptr->n_aliases[i] = NULL;
189 
190 	return (NET_R_OK);
191 }
192 #else /* !NETENT_DATA */
193 static int
194 copy_netent(struct netent *ne, struct netent *nptr, NET_R_COPY_ARGS) {
195 	char *cp, *eob;
196 	int i, n;
197 
198 	/* copy net value and type */
199 	nptr->n_addrtype = ne->n_addrtype;
200 	nptr->n_net = ne->n_net;
201 
202 	/* copy official name */
203 	cp = ndptr->line;
204 	eob = ndptr->line + sizeof(ndptr->line);
205 	if ((n = strlen(ne->n_name) + 1) < (eob - cp)) {
206 		strcpy(cp, ne->n_name);
207 		nptr->n_name = cp;
208 		cp += n;
209 	} else {
210 		return (-1);
211 	}
212 
213 	/* copy aliases */
214 	i = 0;
215 	nptr->n_aliases = ndptr->net_aliases;
216 	while (ne->n_aliases[i] && i < (_MAXALIASES-1)) {
217 		if ((n = strlen(ne->n_aliases[i]) + 1) < (eob - cp)) {
218 			strcpy(cp, ne->n_aliases[i]);
219 			nptr->n_aliases[i] = cp;
220 			cp += n;
221 		} else {
222 			break;
223 		}
224 		i++;
225 	}
226 	nptr->n_aliases[i] = NULL;
227 
228 	return (NET_R_OK);
229 }
230 #endif /* !NETENT_DATA */
231 #else /* NET_R_RETURN */
232 	static int getnetent_r_unknown_system = 0;
233 #endif /* NET_R_RETURN */
234 #endif /* !defined(_REENTRANT) || !defined(DO_PTHREADS) */
235