]> git.saurik.com Git - apple/libinfo.git/blame_incremental - lookup.subproj/lu_network.c
Libinfo-89.1.tar.gz
[apple/libinfo.git] / lookup.subproj / lu_network.c
... / ...
CommitLineData
1/*
2 * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * Portions Copyright (c) 1999 Apple Computer, Inc. All Rights
7 * Reserved. This file contains Original Code and/or Modifications of
8 * Original Code as defined in and that are subject to the Apple Public
9 * Source License Version 1.1 (the "License"). You may not use this file
10 * except in compliance with the License. Please obtain a copy of the
11 * License at http://www.apple.com/publicsource and read it before using
12 * this file.
13 *
14 * The Original Code and all software distributed under the License are
15 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE OR NON- INFRINGEMENT. Please see the
19 * License for the specific language governing rights and limitations
20 * under the License.
21 *
22 * @APPLE_LICENSE_HEADER_END@
23 */
24/*
25 * network lookup
26 * Copyright (C) 1989 by NeXT, Inc.
27 */
28#include <stdlib.h>
29#include <mach/mach.h>
30#include <stdio.h>
31#include <string.h>
32#include "lookup.h"
33#include <rpc/types.h>
34#include <rpc/xdr.h>
35#include "_lu_types.h"
36#include <netdb.h>
37#include "lu_utils.h"
38#include <sys/socket.h>
39#import <netinet/in.h>
40
41extern struct netent *_res_getnetbyaddr();
42extern struct netent *_res_getnetbyname();
43extern struct netent *_old_getnetbyaddr();
44extern struct netent *_old_getnetbyname();
45extern struct netent *_old_getnetent();
46extern void _old_setnetent();
47extern void _old_endnetent();
48
49static lookup_state n_state = LOOKUP_CACHE;
50static struct netent global_n;
51static int global_free = 1;
52static char *n_data = NULL;
53static unsigned n_datalen;
54static int n_nentries;
55static int n_start = 1;
56static XDR n_xdr;
57
58static void
59freeold(void)
60{
61 char **aliases;
62
63 if (global_free == 1) return;
64
65 free(global_n.n_name);
66
67 aliases = global_n.n_aliases;
68 if (aliases != NULL)
69 {
70 while (*aliases != NULL) free(*aliases++);
71 free(global_n.n_aliases);
72 }
73
74 global_free = 1;
75}
76
77static void
78convert_n(_lu_netent *lu_n)
79{
80 int i, len;
81
82 freeold();
83
84 global_n.n_name = strdup(lu_n->n_names.n_names_val[0]);
85
86 len = lu_n->n_names.n_names_len - 1;
87 global_n.n_aliases = malloc((len + 1) * sizeof(char *));
88
89 for (i = 0; i < len; i++)
90 {
91 global_n.n_aliases[i] = strdup(lu_n->n_names.n_names_val[i + 1]);
92 }
93
94 global_n.n_aliases[len] = NULL;
95
96 global_n.n_addrtype = AF_INET;
97 global_n.n_net = lu_n->n_net;
98
99 global_free = 0;
100}
101
102static struct netent *
103lu_getnetbyaddr(long addr, int type)
104{
105 unsigned datalen;
106 _lu_netent_ptr lu_n;
107 XDR xdr;
108 static int proc = -1;
109 unit lookup_buf[MAX_INLINE_UNITS];
110
111 if (type != AF_INET)
112 {
113 return (NULL);
114 }
115
116 if (proc < 0)
117 {
118 if (_lookup_link(_lu_port, "getnetbyaddr", &proc) != KERN_SUCCESS)
119 {
120 return (NULL);
121 }
122 }
123
124 addr = htonl(addr);
125 datalen = MAX_INLINE_UNITS;
126 if (_lookup_one(_lu_port, proc, (unit *)&addr, 1, lookup_buf, &datalen)
127 != KERN_SUCCESS)
128 {
129 return (NULL);
130 }
131
132 datalen *= BYTES_PER_XDR_UNIT;
133 xdrmem_create(&xdr, lookup_buf, datalen, XDR_DECODE);
134 lu_n = NULL;
135 if (!xdr__lu_netent_ptr(&xdr, &lu_n) || (lu_n == NULL))
136 {
137 xdr_destroy(&xdr);
138 return (NULL);
139 }
140
141 xdr_destroy(&xdr);
142
143 convert_n(lu_n);
144 xdr_free(xdr__lu_netent_ptr, &lu_n);
145 return (&global_n);
146}
147
148static struct netent *
149lu_getnetbyname(const char *name)
150{
151 unsigned datalen;
152 char namebuf[_LU_MAXLUSTRLEN + BYTES_PER_XDR_UNIT];
153 XDR outxdr;
154 XDR inxdr;
155 _lu_netent_ptr lu_n;
156 static int proc = -1;
157 unit lookup_buf[MAX_INLINE_UNITS];
158
159 if (proc < 0)
160 {
161 if (_lookup_link(_lu_port, "getnetbyname", &proc) != KERN_SUCCESS)
162 {
163 return (NULL);
164 }
165 }
166
167 xdrmem_create(&outxdr, namebuf, sizeof(namebuf), XDR_ENCODE);
168 if (!xdr__lu_string(&outxdr, &name))
169 {
170 xdr_destroy(&outxdr);
171 return (NULL);
172 }
173
174 datalen = MAX_INLINE_UNITS;
175 if (_lookup_one(_lu_port, proc, (unit *)namebuf,
176 xdr_getpos(&outxdr) / BYTES_PER_XDR_UNIT, lookup_buf, &datalen)
177 != KERN_SUCCESS)
178 {
179 xdr_destroy(&outxdr);
180 return (NULL);
181 }
182
183 xdr_destroy(&outxdr);
184
185 datalen *= BYTES_PER_XDR_UNIT;
186 xdrmem_create(&inxdr, lookup_buf, datalen,
187 XDR_DECODE);
188 lu_n = NULL;
189 if (!xdr__lu_netent_ptr(&inxdr, &lu_n) || (lu_n == NULL))
190 {
191 xdr_destroy(&inxdr);
192 return (NULL);
193 }
194
195 xdr_destroy(&inxdr);
196
197 convert_n(lu_n);
198 xdr_free(xdr__lu_netent_ptr, &lu_n);
199 return (&global_n);
200}
201
202static void
203lu_endnetent()
204{
205 n_nentries = 0;
206 if (n_data != NULL)
207 {
208 freeold();
209 vm_deallocate(mach_task_self(), (vm_address_t)n_data, n_datalen);
210 n_data = NULL;
211 }
212}
213
214static void
215lu_setnetent()
216{
217 lu_endnetent();
218 n_start = 1;
219}
220
221static struct netent *
222lu_getnetent()
223{
224 static int proc = -1;
225 _lu_netent lu_n;
226
227 if (n_start == 1)
228 {
229 n_start = 0;
230
231 if (proc < 0)
232 {
233 if (_lookup_link(_lu_port, "getnetent", &proc) != KERN_SUCCESS)
234 {
235 lu_endnetent();
236 return (NULL);
237 }
238 }
239
240 if (_lookup_all(_lu_port, proc, NULL, 0, &n_data, &n_datalen)
241 != KERN_SUCCESS)
242 {
243 lu_endnetent();
244 return (NULL);
245 }
246
247#ifdef NOTDEF
248/* NOTDEF because OOL buffers are counted in bytes with untyped IPC */
249 n_datalen *= BYTES_PER_XDR_UNIT;
250#endif
251 xdrmem_create(&n_xdr, n_data, n_datalen,
252 XDR_DECODE);
253 if (!xdr_int(&n_xdr, &n_nentries))
254 {
255 xdr_destroy(&n_xdr);
256 lu_endnetent();
257 return (NULL);
258 }
259 }
260
261 if (n_nentries == 0)
262 {
263 xdr_destroy(&n_xdr);
264 lu_endnetent();
265 return (NULL);
266 }
267
268 bzero(&lu_n, sizeof(lu_n));
269 if (!xdr__lu_netent(&n_xdr, &lu_n))
270 {
271 xdr_destroy(&n_xdr);
272 lu_endnetent();
273 return (NULL);
274 }
275
276 n_nentries--;
277 convert_n(&lu_n);
278 xdr_free(xdr__lu_netent, &lu_n);
279 return (&global_n);
280}
281
282struct netent *
283getnetbyaddr(long addr, int type)
284{
285 struct netent *res;
286
287 if (_lu_running())
288 {
289 res = lu_getnetbyaddr(addr, type);
290 }
291 else
292 {
293 res = _res_getnetbyaddr(addr, type);
294 if (res == NULL) res = _old_getnetbyaddr(addr, type);
295 }
296
297 return res;
298}
299
300struct netent *
301getnetbyname(const char *name)
302{
303 struct netent *res;
304
305 if (_lu_running())
306 {
307 res = lu_getnetbyname(name);
308 }
309 else
310 {
311 res = _res_getnetbyname(name);
312 if (res == NULL) res = _old_getnetbyname(name);
313 }
314
315 return res;
316}
317
318struct netent *
319getnetent(void)
320{
321 GETENT(lu_getnetent, _old_getnetent, &n_state, struct netent);
322}
323
324void
325setnetent(int stayopen)
326{
327 SETSTATE(lu_setnetent, _old_setnetent, &n_state, stayopen);
328}
329
330void
331endnetent(void)
332{
333 UNSETSTATE(lu_endnetent, _old_endnetent, &n_state);
334}