4 * Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
5 * Copyright (c) 1996,1999 by Internet Software Consortium.
7 * Permission to use, copy, modify, and distribute this software for any
8 * purpose with or without fee is hereby granted, provided that the above
9 * copyright notice and this permission notice appear in all copies.
11 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
12 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
14 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
17 * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
20 #if defined(LIBC_SCCS) && !defined(lint)
21 static const char rcsid
[] = "Id: nis_sv.c,v 1.4 2005/04/27 04:56:34 sra Exp";
22 #endif /* LIBC_SCCS and not lint */
26 #include "port_before.h"
29 static int __bind_irs_nis_unneeded
;
32 #include <sys/types.h>
33 #include <netinet/in.h>
34 #include <arpa/nameser.h>
36 #include <sys/socket.h>
38 #undef T_NULL /* Silence re-definition warning of T_NULL. */
42 #include <rpcsvc/yp_prot.h>
43 #include <rpcsvc/ypclnt.h>
51 #include <isc/memcluster.h>
54 #include "port_after.h"
73 enum do_what
{ do_none
= 0x0, do_key
= 0x1, do_val
= 0x2, do_all
= 0x3 };
75 static /*const*/ char services_byname
[] = "services.byname";
79 static void sv_close(struct irs_sv
*);
80 static struct servent
* sv_next(struct irs_sv
*);
81 static struct servent
* sv_byname(struct irs_sv
*, const char *,
83 static struct servent
* sv_byport(struct irs_sv
*, int, const char *);
84 static void sv_rewind(struct irs_sv
*);
85 static void sv_minimize(struct irs_sv
*);
87 static struct servent
* makeservent(struct irs_sv
*this);
88 static void nisfree(struct pvt
*, enum do_what
);
93 irs_nis_sv(struct irs_acc
*this) {
97 if (!(sv
= memget(sizeof *sv
))) {
101 memset(sv
, 0x5e, sizeof *sv
);
102 if (!(pvt
= memget(sizeof *pvt
))) {
103 memput(sv
, sizeof *sv
);
107 memset(pvt
, 0, sizeof *pvt
);
109 pvt
->nis_domain
= ((struct nis_p
*)this->private)->domain
;
111 sv
->close
= sv_close
;
113 sv
->byname
= sv_byname
;
114 sv
->byport
= sv_byport
;
115 sv
->rewind
= sv_rewind
;
116 sv
->minimize
= sv_minimize
;
125 sv_close(struct irs_sv
*this) {
126 struct pvt
*pvt
= (struct pvt
*)this->private;
128 nisfree(pvt
, do_all
);
129 if (pvt
->serv
.s_aliases
)
130 free(pvt
->serv
.s_aliases
);
133 memput(pvt
, sizeof *pvt
);
134 memput(this, sizeof *this);
137 static struct servent
*
138 sv_byname(struct irs_sv
*this, const char *name
, const char *proto
) {
139 struct servent
*serv
;
143 while ((serv
= sv_next(this)) != NULL
) {
144 if (proto
!= NULL
&& strcmp(proto
, serv
->s_proto
))
146 if (!strcmp(name
, serv
->s_name
))
148 for (sap
= serv
->s_aliases
; sap
&& *sap
; sap
++)
149 if (!strcmp(name
, *sap
))
155 static struct servent
*
156 sv_byport(struct irs_sv
*this, int port
, const char *proto
) {
157 struct servent
*serv
;
160 while ((serv
= sv_next(this)) != NULL
) {
161 if (proto
!= NULL
&& strcmp(proto
, serv
->s_proto
))
163 if (serv
->s_port
== port
)
170 sv_rewind(struct irs_sv
*this) {
171 struct pvt
*pvt
= (struct pvt
*)this->private;
176 static struct servent
*
177 sv_next(struct irs_sv
*this) {
178 struct pvt
*pvt
= (struct pvt
*)this->private;
179 struct servent
*rval
;
183 if (pvt
->needrewind
) {
184 nisfree(pvt
, do_all
);
185 r
= yp_first(pvt
->nis_domain
, services_byname
,
186 &pvt
->curkey_data
, &pvt
->curkey_len
,
187 &pvt
->curval_data
, &pvt
->curval_len
);
193 nisfree(pvt
, do_val
);
194 r
= yp_next(pvt
->nis_domain
, services_byname
,
195 pvt
->curkey_data
, pvt
->curkey_len
,
196 &newkey_data
, &newkey_len
,
197 &pvt
->curval_data
, &pvt
->curval_len
);
198 nisfree(pvt
, do_key
);
199 pvt
->curkey_data
= newkey_data
;
200 pvt
->curkey_len
= newkey_len
;
206 rval
= makeservent(this);
207 } while (rval
== NULL
);
212 sv_minimize(struct irs_sv
*this) {
219 static struct servent
*
220 makeservent(struct irs_sv
*this) {
221 struct pvt
*pvt
= (struct pvt
*)this->private;
222 static const char spaces
[] = " \t";
228 pvt
->svbuf
= pvt
->curval_data
;
229 pvt
->curval_data
= NULL
;
231 if (pvt
->serv
.s_aliases
) {
232 free(pvt
->serv
.s_aliases
);
233 pvt
->serv
.s_aliases
= NULL
;
236 if ((p
= strpbrk(pvt
->svbuf
, "#\n")))
241 pvt
->serv
.s_name
= p
;
242 p
+= strcspn(p
, spaces
);
246 p
+= strspn(p
, spaces
);
248 pvt
->serv
.s_port
= htons((u_short
) atoi(p
));
249 pvt
->serv
.s_proto
= NULL
;
251 while (*p
&& !isspace((unsigned char)*p
))
253 pvt
->serv
.s_proto
= p
;
254 if (!pvt
->serv
.s_proto
)
258 p
+= strspn(p
, spaces
);
263 if ((n
+ 1) >= m
|| !pvt
->serv
.s_aliases
) {
265 t
= realloc(pvt
->serv
.s_aliases
, m
* sizeof(char *));
270 pvt
->serv
.s_aliases
= t
;
272 pvt
->serv
.s_aliases
[n
++] = p
;
273 p
+= strcspn(p
, spaces
);
277 p
+= strspn(p
, spaces
);
279 if (!pvt
->serv
.s_aliases
)
280 pvt
->serv
.s_aliases
= malloc(sizeof(char *));
281 if (!pvt
->serv
.s_aliases
)
283 pvt
->serv
.s_aliases
[n
] = NULL
;
287 if (pvt
->serv
.s_aliases
) {
288 free(pvt
->serv
.s_aliases
);
289 pvt
->serv
.s_aliases
= NULL
;
299 nisfree(struct pvt
*pvt
, enum do_what do_what
) {
300 if ((do_what
& do_key
) && pvt
->curkey_data
) {
301 free(pvt
->curkey_data
);
302 pvt
->curkey_data
= NULL
;
304 if ((do_what
& do_val
) && pvt
->curval_data
) {
305 free(pvt
->curval_data
);
306 pvt
->curval_data
= NULL
;
310 #endif /*WANT_IRS_NIS*/