1 /* $NetBSD: yp_match.c,v 1.16 2003/12/10 12:06:25 agc Exp $ */
4 * Copyright (c) 1992, 1993 Theo de Raadt <deraadt@fsa.ca>
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
17 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29 #include <sys/cdefs.h>
30 #if defined(LIBC_SCCS) && !defined(lint)
31 __RCSID("$NetBSD: yp_match.c,v 1.16 2003/12/10 12:06:25 agc Exp $");
34 #include "namespace.h"
42 #include <rpcsvc/yp_prot.h>
43 #include <rpcsvc/ypclnt.h>
48 extern struct timeval _yplib_timeout
;
49 extern int _yplib_nerrs
;
50 extern char _yp_domain
[];
53 __weak_alias(yp_match
,_yp_match
)
59 static struct ypmatch_ent
{
60 struct ypmatch_ent
*next
;
67 static bool_t ypmatch_add
__P((const char *, const char *, int, char *, int));
68 static bool_t ypmatch_find
__P((const char *, const char *, int, const char **,
72 ypmatch_add(map
, key
, keylen
, val
, vallen
)
79 struct ypmatch_ent
*ep
;
82 _DIAGASSERT(map
!= NULL
);
83 _DIAGASSERT(key
!= NULL
);
84 _DIAGASSERT(val
!= NULL
);
88 for (ep
= ypmc
; ep
; ep
= ep
->next
)
92 if ((ep
= malloc(sizeof *ep
)) == NULL
)
94 (void)memset(ep
, 0, sizeof *ep
);
109 if ((ep
->key
= malloc((size_t)keylen
)) == NULL
)
112 if ((ep
->val
= malloc((size_t)vallen
)) == NULL
) {
121 (void)memcpy(ep
->key
, key
, (size_t)ep
->keylen
);
122 (void)memcpy(ep
->val
, val
, (size_t)ep
->vallen
);
125 if (strcmp(ep
->map
, map
)) {
127 if ((ep
->map
= strdup(map
)) == NULL
)
131 if ((ep
->map
= strdup(map
)) == NULL
)
135 ep
->expire_t
= t
+ _yplib_cache
;
140 ypmatch_find(map
, key
, keylen
, val
, vallen
)
147 struct ypmatch_ent
*ep
;
150 _DIAGASSERT(map
!= NULL
);
151 _DIAGASSERT(key
!= NULL
);
152 _DIAGASSERT(val
!= NULL
);
159 for (ep
= ypmc
; ep
; ep
= ep
->next
) {
160 if (ep
->keylen
!= keylen
)
162 if (strcmp(ep
->map
, map
))
164 if (memcmp(ep
->key
, key
, (size_t)keylen
))
166 if (t
> ep
->expire_t
)
170 *vallen
= ep
->vallen
;
178 yp_match(indomain
, inmap
, inkey
, inkeylen
, outval
, outvallen
)
179 const char *indomain
;
186 struct dom_binding
*ysd
;
187 struct ypresp_val yprv
;
188 struct ypreq_key yprk
;
191 if (outval
== NULL
|| outvallen
== NULL
)
192 return YPERR_BADARGS
;
196 if (_yp_invalid_domain(indomain
))
197 return YPERR_BADARGS
;
198 if (inmap
== NULL
|| *inmap
== '\0'
199 || strlen(inmap
) > YPMAXMAP
)
200 return YPERR_BADARGS
;
201 if (inkey
== NULL
|| inkeylen
== 0)
202 return YPERR_BADARGS
;
205 if (_yp_dobind(indomain
, &ysd
) != 0)
209 if (!strcmp(_yp_domain
, indomain
) && ypmatch_find(inmap
, inkey
,
210 inkeylen
, &yprv
.valdat
.dptr
, &yprv
.valdat
.dsize
)) {
211 *outvallen
= yprv
.valdat
.dsize
;
212 if ((*outval
= malloc((size_t)(*outvallen
+ 1))) == NULL
)
214 (void)memcpy(*outval
, yprv
.valdat
.dptr
, (size_t)*outvallen
);
215 (*outval
)[*outvallen
] = '\0';
220 yprk
.domain
= indomain
;
222 yprk
.keydat
.dptr
= __UNCONST(inkey
);
223 yprk
.keydat
.dsize
= inkeylen
;
225 memset(&yprv
, 0, sizeof yprv
);
227 r
= clnt_call(ysd
->dom_client
, (rpcproc_t
)YPPROC_MATCH
,
228 (xdrproc_t
)xdr_ypreq_key
, &yprk
,
229 (xdrproc_t
)xdr_ypresp_val
, &yprv
,
231 if (r
!= RPC_SUCCESS
) {
232 if (++nerrs
== _yplib_nerrs
) {
233 clnt_perror(ysd
->dom_client
, "yp_match: clnt_call");
239 if (!(r
= ypprot_err(yprv
.status
))) {
240 *outvallen
= yprv
.valdat
.dsize
;
241 if ((*outval
= malloc((size_t)(*outvallen
+ 1))) == NULL
)
243 (void)memcpy(*outval
, yprv
.valdat
.dptr
, (size_t)*outvallen
);
244 (*outval
)[*outvallen
] = '\0';
246 if (strcmp(_yp_domain
, indomain
) == 0)
247 if (!ypmatch_add(inmap
, inkey
, inkeylen
,
248 *outval
, *outvallen
))
252 xdr_free((xdrproc_t
)xdr_ypresp_val
, (char *)(void *)&yprv
);