2 * Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
3 * Copyright (c) 1996,1999 by Internet Software Consortium.
5 * Permission to use, copy, modify, and distribute this software for any
6 * purpose with or without fee is hereby granted, provided that the above
7 * copyright notice and this permission notice appear in all copies.
9 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
10 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
12 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
15 * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18 #if defined(LIBC_SCCS) && !defined(lint)
19 static const char rcsid
[] = "$Id: nis_sv.c,v 1.4 2005/04/27 04:56:34 sra Exp $";
20 #endif /* LIBC_SCCS and not lint */
24 #include "port_before.h"
27 static int __bind_irs_nis_unneeded
;
30 #include <sys/types.h>
31 #include <netinet/in.h>
32 #include <arpa/nameser.h>
34 #include <sys/socket.h>
36 #undef T_NULL /* Silence re-definition warning of T_NULL. */
40 #include <rpcsvc/yp_prot.h>
41 #include <rpcsvc/ypclnt.h>
49 #include <isc/memcluster.h>
52 #include "port_after.h"
71 enum do_what
{ do_none
= 0x0, do_key
= 0x1, do_val
= 0x2, do_all
= 0x3 };
73 static /*const*/ char services_byname
[] = "services.byname";
77 static void sv_close(struct irs_sv
*);
78 static struct servent
* sv_next(struct irs_sv
*);
79 static struct servent
* sv_byname(struct irs_sv
*, const char *,
81 static struct servent
* sv_byport(struct irs_sv
*, int, const char *);
82 static void sv_rewind(struct irs_sv
*);
83 static void sv_minimize(struct irs_sv
*);
85 static struct servent
* makeservent(struct irs_sv
*this);
86 static void nisfree(struct pvt
*, enum do_what
);
91 irs_nis_sv(struct irs_acc
*this) {
95 if (!(sv
= memget(sizeof *sv
))) {
99 memset(sv
, 0x5e, sizeof *sv
);
100 if (!(pvt
= memget(sizeof *pvt
))) {
101 memput(sv
, sizeof *sv
);
105 memset(pvt
, 0, sizeof *pvt
);
107 pvt
->nis_domain
= ((struct nis_p
*)this->private)->domain
;
109 sv
->close
= sv_close
;
111 sv
->byname
= sv_byname
;
112 sv
->byport
= sv_byport
;
113 sv
->rewind
= sv_rewind
;
114 sv
->minimize
= sv_minimize
;
123 sv_close(struct irs_sv
*this) {
124 struct pvt
*pvt
= (struct pvt
*)this->private;
126 nisfree(pvt
, do_all
);
127 if (pvt
->serv
.s_aliases
)
128 free(pvt
->serv
.s_aliases
);
131 memput(pvt
, sizeof *pvt
);
132 memput(this, sizeof *this);
135 static struct servent
*
136 sv_byname(struct irs_sv
*this, const char *name
, const char *proto
) {
137 struct servent
*serv
;
141 while ((serv
= sv_next(this)) != NULL
) {
142 if (proto
!= NULL
&& strcmp(proto
, serv
->s_proto
))
144 if (!strcmp(name
, serv
->s_name
))
146 for (sap
= serv
->s_aliases
; sap
&& *sap
; sap
++)
147 if (!strcmp(name
, *sap
))
153 static struct servent
*
154 sv_byport(struct irs_sv
*this, int port
, const char *proto
) {
155 struct servent
*serv
;
158 while ((serv
= sv_next(this)) != NULL
) {
159 if (proto
!= NULL
&& strcmp(proto
, serv
->s_proto
))
161 if (serv
->s_port
== port
)
168 sv_rewind(struct irs_sv
*this) {
169 struct pvt
*pvt
= (struct pvt
*)this->private;
174 static struct servent
*
175 sv_next(struct irs_sv
*this) {
176 struct pvt
*pvt
= (struct pvt
*)this->private;
177 struct servent
*rval
;
181 if (pvt
->needrewind
) {
182 nisfree(pvt
, do_all
);
183 r
= yp_first(pvt
->nis_domain
, services_byname
,
184 &pvt
->curkey_data
, &pvt
->curkey_len
,
185 &pvt
->curval_data
, &pvt
->curval_len
);
191 nisfree(pvt
, do_val
);
192 r
= yp_next(pvt
->nis_domain
, services_byname
,
193 pvt
->curkey_data
, pvt
->curkey_len
,
194 &newkey_data
, &newkey_len
,
195 &pvt
->curval_data
, &pvt
->curval_len
);
196 nisfree(pvt
, do_key
);
197 pvt
->curkey_data
= newkey_data
;
198 pvt
->curkey_len
= newkey_len
;
204 rval
= makeservent(this);
205 } while (rval
== NULL
);
210 sv_minimize(struct irs_sv
*this) {
217 static struct servent
*
218 makeservent(struct irs_sv
*this) {
219 struct pvt
*pvt
= (struct pvt
*)this->private;
220 static const char spaces
[] = " \t";
226 pvt
->svbuf
= pvt
->curval_data
;
227 pvt
->curval_data
= NULL
;
229 if (pvt
->serv
.s_aliases
) {
230 free(pvt
->serv
.s_aliases
);
231 pvt
->serv
.s_aliases
= NULL
;
234 if ((p
= strpbrk(pvt
->svbuf
, "#\n")))
239 pvt
->serv
.s_name
= p
;
240 p
+= strcspn(p
, spaces
);
244 p
+= strspn(p
, spaces
);
246 pvt
->serv
.s_port
= htons((u_short
) atoi(p
));
247 pvt
->serv
.s_proto
= NULL
;
249 while (*p
&& !isspace((unsigned char)*p
))
251 pvt
->serv
.s_proto
= p
;
252 if (!pvt
->serv
.s_proto
)
256 p
+= strspn(p
, spaces
);
261 if ((n
+ 1) >= m
|| !pvt
->serv
.s_aliases
) {
263 t
= realloc(pvt
->serv
.s_aliases
, m
* sizeof(char *));
268 pvt
->serv
.s_aliases
= t
;
270 pvt
->serv
.s_aliases
[n
++] = p
;
271 p
+= strcspn(p
, spaces
);
275 p
+= strspn(p
, spaces
);
277 if (!pvt
->serv
.s_aliases
)
278 pvt
->serv
.s_aliases
= malloc(sizeof(char *));
279 if (!pvt
->serv
.s_aliases
)
281 pvt
->serv
.s_aliases
[n
] = NULL
;
285 if (pvt
->serv
.s_aliases
) {
286 free(pvt
->serv
.s_aliases
);
287 pvt
->serv
.s_aliases
= NULL
;
297 nisfree(struct pvt
*pvt
, enum do_what do_what
) {
298 if ((do_what
& do_key
) && pvt
->curkey_data
) {
299 free(pvt
->curkey_data
);
300 pvt
->curkey_data
= NULL
;
302 if ((do_what
& do_val
) && pvt
->curval_data
) {
303 free(pvt
->curval_data
);
304 pvt
->curval_data
= NULL
;
308 #endif /*WANT_IRS_NIS*/