xref: /minix3/external/bsd/bind/dist/lib/dns/dlz.c (revision 00b67f09dd46474d133c95011a48590a8e8f94c7)
1*00b67f09SDavid van Moolenbroek /*	$NetBSD: dlz.c,v 1.7 2014/12/10 04:37:58 christos Exp $	*/
2*00b67f09SDavid van Moolenbroek 
3*00b67f09SDavid van Moolenbroek /*
4*00b67f09SDavid van Moolenbroek  * Portions Copyright (C) 2005, 2007, 2009-2013  Internet Systems Consortium, Inc. ("ISC")
5*00b67f09SDavid van Moolenbroek  * Portions Copyright (C) 1999-2001  Internet Software Consortium.
6*00b67f09SDavid van Moolenbroek  *
7*00b67f09SDavid van Moolenbroek  * Permission to use, copy, modify, and/or distribute this software for any
8*00b67f09SDavid van Moolenbroek  * purpose with or without fee is hereby granted, provided that the above
9*00b67f09SDavid van Moolenbroek  * copyright notice and this permission notice appear in all copies.
10*00b67f09SDavid van Moolenbroek  *
11*00b67f09SDavid van Moolenbroek  * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
12*00b67f09SDavid van Moolenbroek  * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
13*00b67f09SDavid van Moolenbroek  * AND FITNESS.  IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
14*00b67f09SDavid van Moolenbroek  * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
15*00b67f09SDavid van Moolenbroek  * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
16*00b67f09SDavid van Moolenbroek  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17*00b67f09SDavid van Moolenbroek  * PERFORMANCE OF THIS SOFTWARE.
18*00b67f09SDavid van Moolenbroek  */
19*00b67f09SDavid van Moolenbroek 
20*00b67f09SDavid van Moolenbroek /*
21*00b67f09SDavid van Moolenbroek  * Copyright (C) 2002 Stichting NLnet, Netherlands, stichting@nlnet.nl.
22*00b67f09SDavid van Moolenbroek  *
23*00b67f09SDavid van Moolenbroek  * Permission to use, copy, modify, and distribute this software for any
24*00b67f09SDavid van Moolenbroek  * purpose with or without fee is hereby granted, provided that the
25*00b67f09SDavid van Moolenbroek  * above copyright notice and this permission notice appear in all
26*00b67f09SDavid van Moolenbroek  * copies.
27*00b67f09SDavid van Moolenbroek  *
28*00b67f09SDavid van Moolenbroek  * THE SOFTWARE IS PROVIDED "AS IS" AND STICHTING NLNET
29*00b67f09SDavid van Moolenbroek  * DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
30*00b67f09SDavid van Moolenbroek  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
31*00b67f09SDavid van Moolenbroek  * STICHTING NLNET BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
32*00b67f09SDavid van Moolenbroek  * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
33*00b67f09SDavid van Moolenbroek  * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
34*00b67f09SDavid van Moolenbroek  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE
35*00b67f09SDavid van Moolenbroek  * USE OR PERFORMANCE OF THIS SOFTWARE.
36*00b67f09SDavid van Moolenbroek  *
37*00b67f09SDavid van Moolenbroek  * The development of Dynamically Loadable Zones (DLZ) for Bind 9 was
38*00b67f09SDavid van Moolenbroek  * conceived and contributed by Rob Butler.
39*00b67f09SDavid van Moolenbroek  *
40*00b67f09SDavid van Moolenbroek  * Permission to use, copy, modify, and distribute this software for any
41*00b67f09SDavid van Moolenbroek  * purpose with or without fee is hereby granted, provided that the
42*00b67f09SDavid van Moolenbroek  * above copyright notice and this permission notice appear in all
43*00b67f09SDavid van Moolenbroek  * copies.
44*00b67f09SDavid van Moolenbroek  *
45*00b67f09SDavid van Moolenbroek  * THE SOFTWARE IS PROVIDED "AS IS" AND ROB BUTLER
46*00b67f09SDavid van Moolenbroek  * DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
47*00b67f09SDavid van Moolenbroek  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
48*00b67f09SDavid van Moolenbroek  * ROB BUTLER BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR
49*00b67f09SDavid van Moolenbroek  * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS
50*00b67f09SDavid van Moolenbroek  * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
51*00b67f09SDavid van Moolenbroek  * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE
52*00b67f09SDavid van Moolenbroek  * USE OR PERFORMANCE OF THIS SOFTWARE.
53*00b67f09SDavid van Moolenbroek  */
54*00b67f09SDavid van Moolenbroek 
55*00b67f09SDavid van Moolenbroek /* Id */
56*00b67f09SDavid van Moolenbroek 
57*00b67f09SDavid van Moolenbroek /*! \file */
58*00b67f09SDavid van Moolenbroek 
59*00b67f09SDavid van Moolenbroek /***
60*00b67f09SDavid van Moolenbroek  *** Imports
61*00b67f09SDavid van Moolenbroek  ***/
62*00b67f09SDavid van Moolenbroek 
63*00b67f09SDavid van Moolenbroek #include <config.h>
64*00b67f09SDavid van Moolenbroek 
65*00b67f09SDavid van Moolenbroek #include <dns/db.h>
66*00b67f09SDavid van Moolenbroek #include <dns/dlz.h>
67*00b67f09SDavid van Moolenbroek #include <dns/fixedname.h>
68*00b67f09SDavid van Moolenbroek #include <dns/log.h>
69*00b67f09SDavid van Moolenbroek #include <dns/master.h>
70*00b67f09SDavid van Moolenbroek #include <dns/ssu.h>
71*00b67f09SDavid van Moolenbroek #include <dns/zone.h>
72*00b67f09SDavid van Moolenbroek 
73*00b67f09SDavid van Moolenbroek 
74*00b67f09SDavid van Moolenbroek #include <isc/buffer.h>
75*00b67f09SDavid van Moolenbroek #include <isc/magic.h>
76*00b67f09SDavid van Moolenbroek #include <isc/mem.h>
77*00b67f09SDavid van Moolenbroek #include <isc/once.h>
78*00b67f09SDavid van Moolenbroek #include <isc/rwlock.h>
79*00b67f09SDavid van Moolenbroek #include <isc/string.h>
80*00b67f09SDavid van Moolenbroek #include <isc/util.h>
81*00b67f09SDavid van Moolenbroek 
82*00b67f09SDavid van Moolenbroek /***
83*00b67f09SDavid van Moolenbroek  *** Supported DLZ DB Implementations Registry
84*00b67f09SDavid van Moolenbroek  ***/
85*00b67f09SDavid van Moolenbroek 
86*00b67f09SDavid van Moolenbroek static ISC_LIST(dns_dlzimplementation_t) dlz_implementations;
87*00b67f09SDavid van Moolenbroek static isc_rwlock_t dlz_implock;
88*00b67f09SDavid van Moolenbroek static isc_once_t once = ISC_ONCE_INIT;
89*00b67f09SDavid van Moolenbroek 
90*00b67f09SDavid van Moolenbroek static void
dlz_initialize(void)91*00b67f09SDavid van Moolenbroek dlz_initialize(void) {
92*00b67f09SDavid van Moolenbroek 	RUNTIME_CHECK(isc_rwlock_init(&dlz_implock, 0, 0) == ISC_R_SUCCESS);
93*00b67f09SDavid van Moolenbroek 	ISC_LIST_INIT(dlz_implementations);
94*00b67f09SDavid van Moolenbroek }
95*00b67f09SDavid van Moolenbroek 
96*00b67f09SDavid van Moolenbroek /*%
97*00b67f09SDavid van Moolenbroek  * Searches the dlz_implementations list for a driver matching name.
98*00b67f09SDavid van Moolenbroek  */
99*00b67f09SDavid van Moolenbroek static inline dns_dlzimplementation_t *
dlz_impfind(const char * name)100*00b67f09SDavid van Moolenbroek dlz_impfind(const char *name) {
101*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *imp;
102*00b67f09SDavid van Moolenbroek 
103*00b67f09SDavid van Moolenbroek 	for (imp = ISC_LIST_HEAD(dlz_implementations);
104*00b67f09SDavid van Moolenbroek 	     imp != NULL;
105*00b67f09SDavid van Moolenbroek 	     imp = ISC_LIST_NEXT(imp, link))
106*00b67f09SDavid van Moolenbroek 		if (strcasecmp(name, imp->name) == 0)
107*00b67f09SDavid van Moolenbroek 			return (imp);
108*00b67f09SDavid van Moolenbroek 	return (NULL);
109*00b67f09SDavid van Moolenbroek }
110*00b67f09SDavid van Moolenbroek 
111*00b67f09SDavid van Moolenbroek /***
112*00b67f09SDavid van Moolenbroek  *** Basic DLZ Methods
113*00b67f09SDavid van Moolenbroek  ***/
114*00b67f09SDavid van Moolenbroek 
115*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlzallowzonexfr(dns_view_t * view,dns_name_t * name,isc_sockaddr_t * clientaddr,dns_db_t ** dbp)116*00b67f09SDavid van Moolenbroek dns_dlzallowzonexfr(dns_view_t *view, dns_name_t *name,
117*00b67f09SDavid van Moolenbroek 		    isc_sockaddr_t *clientaddr, dns_db_t **dbp)
118*00b67f09SDavid van Moolenbroek {
119*00b67f09SDavid van Moolenbroek 	isc_result_t result = ISC_R_NOTFOUND;
120*00b67f09SDavid van Moolenbroek 	dns_dlzallowzonexfr_t allowzonexfr;
121*00b67f09SDavid van Moolenbroek 	dns_dlzdb_t *dlzdb;
122*00b67f09SDavid van Moolenbroek 
123*00b67f09SDavid van Moolenbroek 	/*
124*00b67f09SDavid van Moolenbroek 	 * Performs checks to make sure data is as we expect it to be.
125*00b67f09SDavid van Moolenbroek 	 */
126*00b67f09SDavid van Moolenbroek 	REQUIRE(name != NULL);
127*00b67f09SDavid van Moolenbroek 	REQUIRE(dbp != NULL && *dbp == NULL);
128*00b67f09SDavid van Moolenbroek 
129*00b67f09SDavid van Moolenbroek 	/*
130*00b67f09SDavid van Moolenbroek 	 * Find a driver in which the zone exists and transfer is supported
131*00b67f09SDavid van Moolenbroek 	 */
132*00b67f09SDavid van Moolenbroek 	for (dlzdb = ISC_LIST_HEAD(view->dlz_searched);
133*00b67f09SDavid van Moolenbroek 	     dlzdb != NULL;
134*00b67f09SDavid van Moolenbroek 	     dlzdb = ISC_LIST_NEXT(dlzdb, link))
135*00b67f09SDavid van Moolenbroek 	{
136*00b67f09SDavid van Moolenbroek 		REQUIRE(DNS_DLZ_VALID(dlzdb));
137*00b67f09SDavid van Moolenbroek 
138*00b67f09SDavid van Moolenbroek 		allowzonexfr = dlzdb->implementation->methods->allowzonexfr;
139*00b67f09SDavid van Moolenbroek 		result = (*allowzonexfr)(dlzdb->implementation->driverarg,
140*00b67f09SDavid van Moolenbroek 					 dlzdb->dbdata, dlzdb->mctx,
141*00b67f09SDavid van Moolenbroek 					 view->rdclass, name, clientaddr, dbp);
142*00b67f09SDavid van Moolenbroek 
143*00b67f09SDavid van Moolenbroek 		/*
144*00b67f09SDavid van Moolenbroek 		 * if ISC_R_NOPERM, we found the right database but
145*00b67f09SDavid van Moolenbroek 		 * the zone may not transfer.
146*00b67f09SDavid van Moolenbroek 		 */
147*00b67f09SDavid van Moolenbroek 		if (result == ISC_R_SUCCESS || result == ISC_R_NOPERM)
148*00b67f09SDavid van Moolenbroek 			return (result);
149*00b67f09SDavid van Moolenbroek 	}
150*00b67f09SDavid van Moolenbroek 
151*00b67f09SDavid van Moolenbroek 	if (result == ISC_R_NOTIMPLEMENTED)
152*00b67f09SDavid van Moolenbroek 		result = ISC_R_NOTFOUND;
153*00b67f09SDavid van Moolenbroek 
154*00b67f09SDavid van Moolenbroek 	return (result);
155*00b67f09SDavid van Moolenbroek }
156*00b67f09SDavid van Moolenbroek 
157*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlzcreate(isc_mem_t * mctx,const char * dlzname,const char * drivername,unsigned int argc,char * argv[],dns_dlzdb_t ** dbp)158*00b67f09SDavid van Moolenbroek dns_dlzcreate(isc_mem_t *mctx, const char *dlzname, const char *drivername,
159*00b67f09SDavid van Moolenbroek 	      unsigned int argc, char *argv[], dns_dlzdb_t **dbp)
160*00b67f09SDavid van Moolenbroek {
161*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *impinfo;
162*00b67f09SDavid van Moolenbroek 	isc_result_t result;
163*00b67f09SDavid van Moolenbroek 	dns_dlzdb_t *db = NULL;
164*00b67f09SDavid van Moolenbroek 
165*00b67f09SDavid van Moolenbroek 	/*
166*00b67f09SDavid van Moolenbroek 	 * initialize the dlz_implementations list, this is guaranteed
167*00b67f09SDavid van Moolenbroek 	 * to only really happen once.
168*00b67f09SDavid van Moolenbroek 	 */
169*00b67f09SDavid van Moolenbroek 	RUNTIME_CHECK(isc_once_do(&once, dlz_initialize) == ISC_R_SUCCESS);
170*00b67f09SDavid van Moolenbroek 
171*00b67f09SDavid van Moolenbroek 	/*
172*00b67f09SDavid van Moolenbroek 	 * Performs checks to make sure data is as we expect it to be.
173*00b67f09SDavid van Moolenbroek 	 */
174*00b67f09SDavid van Moolenbroek 	REQUIRE(dbp != NULL && *dbp == NULL);
175*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzname != NULL);
176*00b67f09SDavid van Moolenbroek 	REQUIRE(drivername != NULL);
177*00b67f09SDavid van Moolenbroek 	REQUIRE(mctx != NULL);
178*00b67f09SDavid van Moolenbroek 
179*00b67f09SDavid van Moolenbroek 	/* write log message */
180*00b67f09SDavid van Moolenbroek 	isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
181*00b67f09SDavid van Moolenbroek 		      DNS_LOGMODULE_DLZ, ISC_LOG_INFO,
182*00b67f09SDavid van Moolenbroek 		      "Loading '%s' using driver %s", dlzname, drivername);
183*00b67f09SDavid van Moolenbroek 
184*00b67f09SDavid van Moolenbroek 	/* lock the dlz_implementations list so we can search it. */
185*00b67f09SDavid van Moolenbroek 	RWLOCK(&dlz_implock, isc_rwlocktype_read);
186*00b67f09SDavid van Moolenbroek 
187*00b67f09SDavid van Moolenbroek 	/* search for the driver implementation	 */
188*00b67f09SDavid van Moolenbroek 	impinfo = dlz_impfind(drivername);
189*00b67f09SDavid van Moolenbroek 	if (impinfo == NULL) {
190*00b67f09SDavid van Moolenbroek 		RWUNLOCK(&dlz_implock, isc_rwlocktype_read);
191*00b67f09SDavid van Moolenbroek 
192*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
193*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_ERROR,
194*00b67f09SDavid van Moolenbroek 			      "unsupported DLZ database driver '%s'."
195*00b67f09SDavid van Moolenbroek 			      "  %s not loaded.",
196*00b67f09SDavid van Moolenbroek 			      drivername, dlzname);
197*00b67f09SDavid van Moolenbroek 
198*00b67f09SDavid van Moolenbroek 		return (ISC_R_NOTFOUND);
199*00b67f09SDavid van Moolenbroek 	}
200*00b67f09SDavid van Moolenbroek 
201*00b67f09SDavid van Moolenbroek 	/* Allocate memory to hold the DLZ database driver */
202*00b67f09SDavid van Moolenbroek 	db = isc_mem_get(mctx, sizeof(dns_dlzdb_t));
203*00b67f09SDavid van Moolenbroek 	if (db == NULL) {
204*00b67f09SDavid van Moolenbroek 		RWUNLOCK(&dlz_implock, isc_rwlocktype_read);
205*00b67f09SDavid van Moolenbroek 		return (ISC_R_NOMEMORY);
206*00b67f09SDavid van Moolenbroek 	}
207*00b67f09SDavid van Moolenbroek 
208*00b67f09SDavid van Moolenbroek 	/* Make sure memory region is set to all 0's */
209*00b67f09SDavid van Moolenbroek 	memset(db, 0, sizeof(dns_dlzdb_t));
210*00b67f09SDavid van Moolenbroek 
211*00b67f09SDavid van Moolenbroek 	ISC_LINK_INIT(db, link);
212*00b67f09SDavid van Moolenbroek 	db->implementation = impinfo;
213*00b67f09SDavid van Moolenbroek 	if (dlzname != NULL)
214*00b67f09SDavid van Moolenbroek 		db->dlzname = isc_mem_strdup(mctx, dlzname);
215*00b67f09SDavid van Moolenbroek 
216*00b67f09SDavid van Moolenbroek 	/* Create a new database using implementation 'drivername'. */
217*00b67f09SDavid van Moolenbroek 	result = ((impinfo->methods->create)(mctx, dlzname, argc, argv,
218*00b67f09SDavid van Moolenbroek 					     impinfo->driverarg,
219*00b67f09SDavid van Moolenbroek 					     &db->dbdata));
220*00b67f09SDavid van Moolenbroek 
221*00b67f09SDavid van Moolenbroek 	/* mark the DLZ driver as valid */
222*00b67f09SDavid van Moolenbroek 	if (result == ISC_R_SUCCESS) {
223*00b67f09SDavid van Moolenbroek 		RWUNLOCK(&dlz_implock, isc_rwlocktype_read);
224*00b67f09SDavid van Moolenbroek 		db->magic = DNS_DLZ_MAGIC;
225*00b67f09SDavid van Moolenbroek 		isc_mem_attach(mctx, &db->mctx);
226*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
227*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2),
228*00b67f09SDavid van Moolenbroek 			      "DLZ driver loaded successfully.");
229*00b67f09SDavid van Moolenbroek 		*dbp = db;
230*00b67f09SDavid van Moolenbroek 		return (ISC_R_SUCCESS);
231*00b67f09SDavid van Moolenbroek 	} else {
232*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
233*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_ERROR,
234*00b67f09SDavid van Moolenbroek 			      "DLZ driver failed to load.");
235*00b67f09SDavid van Moolenbroek 	}
236*00b67f09SDavid van Moolenbroek 
237*00b67f09SDavid van Moolenbroek 	/* impinfo->methods->create failed. */
238*00b67f09SDavid van Moolenbroek 	RWUNLOCK(&dlz_implock, isc_rwlocktype_read);
239*00b67f09SDavid van Moolenbroek 	isc_mem_put(mctx, db, sizeof(dns_dlzdb_t));
240*00b67f09SDavid van Moolenbroek 	return (result);
241*00b67f09SDavid van Moolenbroek }
242*00b67f09SDavid van Moolenbroek 
243*00b67f09SDavid van Moolenbroek void
dns_dlzdestroy(dns_dlzdb_t ** dbp)244*00b67f09SDavid van Moolenbroek dns_dlzdestroy(dns_dlzdb_t **dbp) {
245*00b67f09SDavid van Moolenbroek 	isc_mem_t *mctx;
246*00b67f09SDavid van Moolenbroek 	dns_dlzdestroy_t destroy;
247*00b67f09SDavid van Moolenbroek 
248*00b67f09SDavid van Moolenbroek 	/* Write debugging message to log */
249*00b67f09SDavid van Moolenbroek 	isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
250*00b67f09SDavid van Moolenbroek 		      DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2),
251*00b67f09SDavid van Moolenbroek 		      "Unloading DLZ driver.");
252*00b67f09SDavid van Moolenbroek 
253*00b67f09SDavid van Moolenbroek 	/*
254*00b67f09SDavid van Moolenbroek 	 * Perform checks to make sure data is as we expect it to be.
255*00b67f09SDavid van Moolenbroek 	 */
256*00b67f09SDavid van Moolenbroek 	REQUIRE(dbp != NULL && DNS_DLZ_VALID(*dbp));
257*00b67f09SDavid van Moolenbroek 
258*00b67f09SDavid van Moolenbroek 	if ((*dbp)->ssutable != NULL) {
259*00b67f09SDavid van Moolenbroek 		dns_ssutable_detach(&(*dbp)->ssutable);
260*00b67f09SDavid van Moolenbroek 	}
261*00b67f09SDavid van Moolenbroek 
262*00b67f09SDavid van Moolenbroek 	/* call the drivers destroy method */
263*00b67f09SDavid van Moolenbroek 	if ((*dbp) != NULL) {
264*00b67f09SDavid van Moolenbroek 		mctx = (*dbp)->mctx;
265*00b67f09SDavid van Moolenbroek 		if ((*dbp)->dlzname != NULL)
266*00b67f09SDavid van Moolenbroek 			isc_mem_free(mctx, (*dbp)->dlzname);
267*00b67f09SDavid van Moolenbroek 		destroy = (*dbp)->implementation->methods->destroy;
268*00b67f09SDavid van Moolenbroek 		(*destroy)((*dbp)->implementation->driverarg,(*dbp)->dbdata);
269*00b67f09SDavid van Moolenbroek 		/* return memory */
270*00b67f09SDavid van Moolenbroek 		isc_mem_put(mctx, (*dbp), sizeof(dns_dlzdb_t));
271*00b67f09SDavid van Moolenbroek 		isc_mem_detach(&mctx);
272*00b67f09SDavid van Moolenbroek 	}
273*00b67f09SDavid van Moolenbroek 
274*00b67f09SDavid van Moolenbroek 	*dbp = NULL;
275*00b67f09SDavid van Moolenbroek }
276*00b67f09SDavid van Moolenbroek 
277*00b67f09SDavid van Moolenbroek /*%
278*00b67f09SDavid van Moolenbroek  * Registers a DLZ driver.  This basically just adds the dlz
279*00b67f09SDavid van Moolenbroek  * driver to the list of available drivers in the dlz_implementations list.
280*00b67f09SDavid van Moolenbroek  */
281*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlzregister(const char * drivername,const dns_dlzmethods_t * methods,void * driverarg,isc_mem_t * mctx,dns_dlzimplementation_t ** dlzimp)282*00b67f09SDavid van Moolenbroek dns_dlzregister(const char *drivername, const dns_dlzmethods_t *methods,
283*00b67f09SDavid van Moolenbroek 		void *driverarg, isc_mem_t *mctx,
284*00b67f09SDavid van Moolenbroek 		dns_dlzimplementation_t **dlzimp)
285*00b67f09SDavid van Moolenbroek {
286*00b67f09SDavid van Moolenbroek 
287*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *dlz_imp;
288*00b67f09SDavid van Moolenbroek 
289*00b67f09SDavid van Moolenbroek 	/* Write debugging message to log */
290*00b67f09SDavid van Moolenbroek 	isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
291*00b67f09SDavid van Moolenbroek 		      DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2),
292*00b67f09SDavid van Moolenbroek 		      "Registering DLZ driver '%s'", drivername);
293*00b67f09SDavid van Moolenbroek 
294*00b67f09SDavid van Moolenbroek 	/*
295*00b67f09SDavid van Moolenbroek 	 * Performs checks to make sure data is as we expect it to be.
296*00b67f09SDavid van Moolenbroek 	 */
297*00b67f09SDavid van Moolenbroek 	REQUIRE(drivername != NULL);
298*00b67f09SDavid van Moolenbroek 	REQUIRE(methods != NULL);
299*00b67f09SDavid van Moolenbroek 	REQUIRE(methods->create != NULL);
300*00b67f09SDavid van Moolenbroek 	REQUIRE(methods->destroy != NULL);
301*00b67f09SDavid van Moolenbroek 	REQUIRE(methods->findzone != NULL);
302*00b67f09SDavid van Moolenbroek 	REQUIRE(mctx != NULL);
303*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzimp != NULL && *dlzimp == NULL);
304*00b67f09SDavid van Moolenbroek 
305*00b67f09SDavid van Moolenbroek 	/*
306*00b67f09SDavid van Moolenbroek 	 * initialize the dlz_implementations list, this is guaranteed
307*00b67f09SDavid van Moolenbroek 	 * to only really happen once.
308*00b67f09SDavid van Moolenbroek 	 */
309*00b67f09SDavid van Moolenbroek 	RUNTIME_CHECK(isc_once_do(&once, dlz_initialize) == ISC_R_SUCCESS);
310*00b67f09SDavid van Moolenbroek 
311*00b67f09SDavid van Moolenbroek 	/* lock the dlz_implementations list so we can modify it. */
312*00b67f09SDavid van Moolenbroek 	RWLOCK(&dlz_implock, isc_rwlocktype_write);
313*00b67f09SDavid van Moolenbroek 
314*00b67f09SDavid van Moolenbroek 	/*
315*00b67f09SDavid van Moolenbroek 	 * check that another already registered driver isn't using
316*00b67f09SDavid van Moolenbroek 	 * the same name
317*00b67f09SDavid van Moolenbroek 	 */
318*00b67f09SDavid van Moolenbroek 	dlz_imp = dlz_impfind(drivername);
319*00b67f09SDavid van Moolenbroek 	if (dlz_imp != NULL) {
320*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
321*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2),
322*00b67f09SDavid van Moolenbroek 			      "DLZ Driver '%s' already registered",
323*00b67f09SDavid van Moolenbroek 			      drivername);
324*00b67f09SDavid van Moolenbroek 		RWUNLOCK(&dlz_implock, isc_rwlocktype_write);
325*00b67f09SDavid van Moolenbroek 		return (ISC_R_EXISTS);
326*00b67f09SDavid van Moolenbroek 	}
327*00b67f09SDavid van Moolenbroek 
328*00b67f09SDavid van Moolenbroek 	/*
329*00b67f09SDavid van Moolenbroek 	 * Allocate memory for a dlz_implementation object.  Error if
330*00b67f09SDavid van Moolenbroek 	 * we cannot.
331*00b67f09SDavid van Moolenbroek 	 */
332*00b67f09SDavid van Moolenbroek 	dlz_imp = isc_mem_get(mctx, sizeof(dns_dlzimplementation_t));
333*00b67f09SDavid van Moolenbroek 	if (dlz_imp == NULL) {
334*00b67f09SDavid van Moolenbroek 		RWUNLOCK(&dlz_implock, isc_rwlocktype_write);
335*00b67f09SDavid van Moolenbroek 		return (ISC_R_NOMEMORY);
336*00b67f09SDavid van Moolenbroek 	}
337*00b67f09SDavid van Moolenbroek 
338*00b67f09SDavid van Moolenbroek 	/* Make sure memory region is set to all 0's */
339*00b67f09SDavid van Moolenbroek 	memset(dlz_imp, 0, sizeof(dns_dlzimplementation_t));
340*00b67f09SDavid van Moolenbroek 
341*00b67f09SDavid van Moolenbroek 	/* Store the data passed into this method */
342*00b67f09SDavid van Moolenbroek 	dlz_imp->name = drivername;
343*00b67f09SDavid van Moolenbroek 	dlz_imp->methods = methods;
344*00b67f09SDavid van Moolenbroek 	dlz_imp->mctx = NULL;
345*00b67f09SDavid van Moolenbroek 	dlz_imp->driverarg = driverarg;
346*00b67f09SDavid van Moolenbroek 
347*00b67f09SDavid van Moolenbroek 	/* attach the new dlz_implementation object to a memory context */
348*00b67f09SDavid van Moolenbroek 	isc_mem_attach(mctx, &dlz_imp->mctx);
349*00b67f09SDavid van Moolenbroek 
350*00b67f09SDavid van Moolenbroek 	/*
351*00b67f09SDavid van Moolenbroek 	 * prepare the dlz_implementation object to be put in a list,
352*00b67f09SDavid van Moolenbroek 	 * and append it to the list
353*00b67f09SDavid van Moolenbroek 	 */
354*00b67f09SDavid van Moolenbroek 	ISC_LINK_INIT(dlz_imp, link);
355*00b67f09SDavid van Moolenbroek 	ISC_LIST_APPEND(dlz_implementations, dlz_imp, link);
356*00b67f09SDavid van Moolenbroek 
357*00b67f09SDavid van Moolenbroek 	/* Unlock the dlz_implementations list.	 */
358*00b67f09SDavid van Moolenbroek 	RWUNLOCK(&dlz_implock, isc_rwlocktype_write);
359*00b67f09SDavid van Moolenbroek 
360*00b67f09SDavid van Moolenbroek 	/* Pass back the dlz_implementation that we created. */
361*00b67f09SDavid van Moolenbroek 	*dlzimp = dlz_imp;
362*00b67f09SDavid van Moolenbroek 
363*00b67f09SDavid van Moolenbroek 	return (ISC_R_SUCCESS);
364*00b67f09SDavid van Moolenbroek }
365*00b67f09SDavid van Moolenbroek 
366*00b67f09SDavid van Moolenbroek /*%
367*00b67f09SDavid van Moolenbroek  * Helper function for dns_dlzstrtoargv().
368*00b67f09SDavid van Moolenbroek  * Pardon the gratuitous recursion.
369*00b67f09SDavid van Moolenbroek  */
370*00b67f09SDavid van Moolenbroek static isc_result_t
dns_dlzstrtoargvsub(isc_mem_t * mctx,char * s,unsigned int * argcp,char *** argvp,unsigned int n)371*00b67f09SDavid van Moolenbroek dns_dlzstrtoargvsub(isc_mem_t *mctx, char *s, unsigned int *argcp,
372*00b67f09SDavid van Moolenbroek 		    char ***argvp, unsigned int n)
373*00b67f09SDavid van Moolenbroek {
374*00b67f09SDavid van Moolenbroek 	isc_result_t result;
375*00b67f09SDavid van Moolenbroek 
376*00b67f09SDavid van Moolenbroek  restart:
377*00b67f09SDavid van Moolenbroek 	/* Discard leading whitespace. */
378*00b67f09SDavid van Moolenbroek 	while (*s == ' ' || *s == '\t')
379*00b67f09SDavid van Moolenbroek 		s++;
380*00b67f09SDavid van Moolenbroek 
381*00b67f09SDavid van Moolenbroek 	if (*s == '\0') {
382*00b67f09SDavid van Moolenbroek 		/* We have reached the end of the string. */
383*00b67f09SDavid van Moolenbroek 		*argcp = n;
384*00b67f09SDavid van Moolenbroek 		*argvp = isc_mem_get(mctx, n * sizeof(char *));
385*00b67f09SDavid van Moolenbroek 		if (*argvp == NULL)
386*00b67f09SDavid van Moolenbroek 			return (ISC_R_NOMEMORY);
387*00b67f09SDavid van Moolenbroek 	} else {
388*00b67f09SDavid van Moolenbroek 		char *p = s;
389*00b67f09SDavid van Moolenbroek 		while (*p != ' ' && *p != '\t' && *p != '\0' && *p != '{') {
390*00b67f09SDavid van Moolenbroek 			if (*p == '\n') {
391*00b67f09SDavid van Moolenbroek 				*p = ' ';
392*00b67f09SDavid van Moolenbroek 				goto restart;
393*00b67f09SDavid van Moolenbroek 			}
394*00b67f09SDavid van Moolenbroek 			p++;
395*00b67f09SDavid van Moolenbroek 		}
396*00b67f09SDavid van Moolenbroek 
397*00b67f09SDavid van Moolenbroek 		/* do "grouping", items between { and } are one arg */
398*00b67f09SDavid van Moolenbroek 		if (*p == '{') {
399*00b67f09SDavid van Moolenbroek 			char *t = p;
400*00b67f09SDavid van Moolenbroek 			/*
401*00b67f09SDavid van Moolenbroek 			 * shift all characters to left by 1 to get rid of '{'
402*00b67f09SDavid van Moolenbroek 			 */
403*00b67f09SDavid van Moolenbroek 			while (*t != '\0') {
404*00b67f09SDavid van Moolenbroek 				t++;
405*00b67f09SDavid van Moolenbroek 				*(t-1) = *t;
406*00b67f09SDavid van Moolenbroek 			}
407*00b67f09SDavid van Moolenbroek 			while (*p != '\0' && *p != '}') {
408*00b67f09SDavid van Moolenbroek 				p++;
409*00b67f09SDavid van Moolenbroek 			}
410*00b67f09SDavid van Moolenbroek 			/* get rid of '}' character */
411*00b67f09SDavid van Moolenbroek 			if (*p == '}') {
412*00b67f09SDavid van Moolenbroek 				*p = '\0';
413*00b67f09SDavid van Moolenbroek 				p++;
414*00b67f09SDavid van Moolenbroek 			}
415*00b67f09SDavid van Moolenbroek 			/* normal case, no "grouping" */
416*00b67f09SDavid van Moolenbroek 		} else if (*p != '\0')
417*00b67f09SDavid van Moolenbroek 			*p++ = '\0';
418*00b67f09SDavid van Moolenbroek 
419*00b67f09SDavid van Moolenbroek 		result = dns_dlzstrtoargvsub(mctx, p, argcp, argvp, n + 1);
420*00b67f09SDavid van Moolenbroek 		if (result != ISC_R_SUCCESS)
421*00b67f09SDavid van Moolenbroek 			return (result);
422*00b67f09SDavid van Moolenbroek 		(*argvp)[n] = s;
423*00b67f09SDavid van Moolenbroek 	}
424*00b67f09SDavid van Moolenbroek 	return (ISC_R_SUCCESS);
425*00b67f09SDavid van Moolenbroek }
426*00b67f09SDavid van Moolenbroek 
427*00b67f09SDavid van Moolenbroek /*%
428*00b67f09SDavid van Moolenbroek  * Tokenize the string "s" into whitespace-separated words,
429*00b67f09SDavid van Moolenbroek  * return the number of words in '*argcp' and an array
430*00b67f09SDavid van Moolenbroek  * of pointers to the words in '*argvp'.  The caller
431*00b67f09SDavid van Moolenbroek  * must free the array using isc_mem_put().  The string
432*00b67f09SDavid van Moolenbroek  * is modified in-place.
433*00b67f09SDavid van Moolenbroek  */
434*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlzstrtoargv(isc_mem_t * mctx,char * s,unsigned int * argcp,char *** argvp)435*00b67f09SDavid van Moolenbroek dns_dlzstrtoargv(isc_mem_t *mctx, char *s,
436*00b67f09SDavid van Moolenbroek 		 unsigned int *argcp, char ***argvp)
437*00b67f09SDavid van Moolenbroek {
438*00b67f09SDavid van Moolenbroek 	return(dns_dlzstrtoargvsub(mctx, s, argcp, argvp, 0));
439*00b67f09SDavid van Moolenbroek }
440*00b67f09SDavid van Moolenbroek 
441*00b67f09SDavid van Moolenbroek /*%
442*00b67f09SDavid van Moolenbroek  * Unregisters a DLZ driver.  This basically just removes the dlz
443*00b67f09SDavid van Moolenbroek  * driver from the list of available drivers in the dlz_implementations list.
444*00b67f09SDavid van Moolenbroek  */
445*00b67f09SDavid van Moolenbroek void
dns_dlzunregister(dns_dlzimplementation_t ** dlzimp)446*00b67f09SDavid van Moolenbroek dns_dlzunregister(dns_dlzimplementation_t **dlzimp) {
447*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *dlz_imp;
448*00b67f09SDavid van Moolenbroek 	isc_mem_t *mctx;
449*00b67f09SDavid van Moolenbroek 
450*00b67f09SDavid van Moolenbroek 	/* Write debugging message to log */
451*00b67f09SDavid van Moolenbroek 	isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
452*00b67f09SDavid van Moolenbroek 		      DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2),
453*00b67f09SDavid van Moolenbroek 		      "Unregistering DLZ driver.");
454*00b67f09SDavid van Moolenbroek 
455*00b67f09SDavid van Moolenbroek 	/*
456*00b67f09SDavid van Moolenbroek 	 * Performs checks to make sure data is as we expect it to be.
457*00b67f09SDavid van Moolenbroek 	 */
458*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzimp != NULL && *dlzimp != NULL);
459*00b67f09SDavid van Moolenbroek 
460*00b67f09SDavid van Moolenbroek 	/*
461*00b67f09SDavid van Moolenbroek 	 * initialize the dlz_implementations list, this is guaranteed
462*00b67f09SDavid van Moolenbroek 	 * to only really happen once.
463*00b67f09SDavid van Moolenbroek 	 */
464*00b67f09SDavid van Moolenbroek 	RUNTIME_CHECK(isc_once_do(&once, dlz_initialize) == ISC_R_SUCCESS);
465*00b67f09SDavid van Moolenbroek 
466*00b67f09SDavid van Moolenbroek 	dlz_imp = *dlzimp;
467*00b67f09SDavid van Moolenbroek 
468*00b67f09SDavid van Moolenbroek 	/* lock the dlz_implementations list so we can modify it. */
469*00b67f09SDavid van Moolenbroek 	RWLOCK(&dlz_implock, isc_rwlocktype_write);
470*00b67f09SDavid van Moolenbroek 
471*00b67f09SDavid van Moolenbroek 	/* remove the dlz_implementation object from the list */
472*00b67f09SDavid van Moolenbroek 	ISC_LIST_UNLINK(dlz_implementations, dlz_imp, link);
473*00b67f09SDavid van Moolenbroek 	mctx = dlz_imp->mctx;
474*00b67f09SDavid van Moolenbroek 
475*00b67f09SDavid van Moolenbroek 	/*
476*00b67f09SDavid van Moolenbroek 	 * Return the memory back to the available memory pool and
477*00b67f09SDavid van Moolenbroek 	 * remove it from the memory context.
478*00b67f09SDavid van Moolenbroek 	 */
479*00b67f09SDavid van Moolenbroek 	isc_mem_put(mctx, dlz_imp, sizeof(dns_dlzimplementation_t));
480*00b67f09SDavid van Moolenbroek 	isc_mem_detach(&mctx);
481*00b67f09SDavid van Moolenbroek 
482*00b67f09SDavid van Moolenbroek 	/* Unlock the dlz_implementations list. */
483*00b67f09SDavid van Moolenbroek 	RWUNLOCK(&dlz_implock, isc_rwlocktype_write);
484*00b67f09SDavid van Moolenbroek }
485*00b67f09SDavid van Moolenbroek 
486*00b67f09SDavid van Moolenbroek /*
487*00b67f09SDavid van Moolenbroek  * Create a writeable DLZ zone. This can be called by DLZ drivers
488*00b67f09SDavid van Moolenbroek  * during configure() to create a zone that can be updated. The zone
489*00b67f09SDavid van Moolenbroek  * type is set to dns_zone_dlz, which is equivalent to a master zone
490*00b67f09SDavid van Moolenbroek  *
491*00b67f09SDavid van Moolenbroek  * This function uses a callback setup in dns_dlzconfigure() to call
492*00b67f09SDavid van Moolenbroek  * into the server zone code to setup the remaining pieces of server
493*00b67f09SDavid van Moolenbroek  * specific functionality on the zone
494*00b67f09SDavid van Moolenbroek  */
495*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlz_writeablezone(dns_view_t * view,dns_dlzdb_t * dlzdb,const char * zone_name)496*00b67f09SDavid van Moolenbroek dns_dlz_writeablezone(dns_view_t *view, dns_dlzdb_t *dlzdb,
497*00b67f09SDavid van Moolenbroek 		      const char *zone_name)
498*00b67f09SDavid van Moolenbroek {
499*00b67f09SDavid van Moolenbroek 	dns_zone_t *zone = NULL;
500*00b67f09SDavid van Moolenbroek 	dns_zone_t *dupzone = NULL;
501*00b67f09SDavid van Moolenbroek 	isc_result_t result;
502*00b67f09SDavid van Moolenbroek 	isc_buffer_t buffer;
503*00b67f09SDavid van Moolenbroek 	dns_fixedname_t fixorigin;
504*00b67f09SDavid van Moolenbroek 	dns_name_t *origin;
505*00b67f09SDavid van Moolenbroek 
506*00b67f09SDavid van Moolenbroek 	REQUIRE(DNS_DLZ_VALID(dlzdb));
507*00b67f09SDavid van Moolenbroek 
508*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzdb->configure_callback != NULL);
509*00b67f09SDavid van Moolenbroek 
510*00b67f09SDavid van Moolenbroek 	isc_buffer_constinit(&buffer, zone_name, strlen(zone_name));
511*00b67f09SDavid van Moolenbroek 	isc_buffer_add(&buffer, strlen(zone_name));
512*00b67f09SDavid van Moolenbroek 	dns_fixedname_init(&fixorigin);
513*00b67f09SDavid van Moolenbroek 	result = dns_name_fromtext(dns_fixedname_name(&fixorigin),
514*00b67f09SDavid van Moolenbroek 				   &buffer, dns_rootname, 0, NULL);
515*00b67f09SDavid van Moolenbroek 	if (result != ISC_R_SUCCESS)
516*00b67f09SDavid van Moolenbroek 		goto cleanup;
517*00b67f09SDavid van Moolenbroek 	origin = dns_fixedname_name(&fixorigin);
518*00b67f09SDavid van Moolenbroek 
519*00b67f09SDavid van Moolenbroek 	if (!dlzdb->search) {
520*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
521*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_WARNING,
522*00b67f09SDavid van Moolenbroek 			      "DLZ %s has 'search no;', but attempted to "
523*00b67f09SDavid van Moolenbroek 			      "register writeable zone %s.",
524*00b67f09SDavid van Moolenbroek 			      dlzdb->dlzname, zone_name);
525*00b67f09SDavid van Moolenbroek 		result = ISC_R_SUCCESS;
526*00b67f09SDavid van Moolenbroek 		goto cleanup;
527*00b67f09SDavid van Moolenbroek 	}
528*00b67f09SDavid van Moolenbroek 
529*00b67f09SDavid van Moolenbroek 	/* See if the zone already exists */
530*00b67f09SDavid van Moolenbroek 	result = dns_view_findzone(view, origin, &dupzone);
531*00b67f09SDavid van Moolenbroek 	if (result == ISC_R_SUCCESS) {
532*00b67f09SDavid van Moolenbroek 		dns_zone_detach(&dupzone);
533*00b67f09SDavid van Moolenbroek 		result = ISC_R_EXISTS;
534*00b67f09SDavid van Moolenbroek 		goto cleanup;
535*00b67f09SDavid van Moolenbroek 	}
536*00b67f09SDavid van Moolenbroek 	INSIST(dupzone == NULL);
537*00b67f09SDavid van Moolenbroek 
538*00b67f09SDavid van Moolenbroek 	/* Create it */
539*00b67f09SDavid van Moolenbroek 	result = dns_zone_create(&zone, view->mctx);
540*00b67f09SDavid van Moolenbroek 	if (result != ISC_R_SUCCESS)
541*00b67f09SDavid van Moolenbroek 		goto cleanup;
542*00b67f09SDavid van Moolenbroek 	result = dns_zone_setorigin(zone, origin);
543*00b67f09SDavid van Moolenbroek 	if (result != ISC_R_SUCCESS)
544*00b67f09SDavid van Moolenbroek 		goto cleanup;
545*00b67f09SDavid van Moolenbroek 	dns_zone_setview(zone, view);
546*00b67f09SDavid van Moolenbroek 
547*00b67f09SDavid van Moolenbroek 	dns_zone_setadded(zone, ISC_TRUE);
548*00b67f09SDavid van Moolenbroek 
549*00b67f09SDavid van Moolenbroek 	if (dlzdb->ssutable == NULL) {
550*00b67f09SDavid van Moolenbroek 		result = dns_ssutable_createdlz(dlzdb->mctx,
551*00b67f09SDavid van Moolenbroek 						&dlzdb->ssutable, dlzdb);
552*00b67f09SDavid van Moolenbroek 		if (result != ISC_R_SUCCESS)
553*00b67f09SDavid van Moolenbroek 			goto cleanup;
554*00b67f09SDavid van Moolenbroek 	}
555*00b67f09SDavid van Moolenbroek 	dns_zone_setssutable(zone, dlzdb->ssutable);
556*00b67f09SDavid van Moolenbroek 
557*00b67f09SDavid van Moolenbroek 	result = dlzdb->configure_callback(view, dlzdb, zone);
558*00b67f09SDavid van Moolenbroek 	if (result != ISC_R_SUCCESS)
559*00b67f09SDavid van Moolenbroek 		goto cleanup;
560*00b67f09SDavid van Moolenbroek 
561*00b67f09SDavid van Moolenbroek 	result = dns_view_addzone(view, zone);
562*00b67f09SDavid van Moolenbroek 
563*00b67f09SDavid van Moolenbroek 
564*00b67f09SDavid van Moolenbroek  cleanup:
565*00b67f09SDavid van Moolenbroek 	if (zone != NULL)
566*00b67f09SDavid van Moolenbroek 		dns_zone_detach(&zone);
567*00b67f09SDavid van Moolenbroek 
568*00b67f09SDavid van Moolenbroek 	return (result);
569*00b67f09SDavid van Moolenbroek }
570*00b67f09SDavid van Moolenbroek 
571*00b67f09SDavid van Moolenbroek /*%
572*00b67f09SDavid van Moolenbroek  * Configure a DLZ driver. This is optional, and if supplied gives
573*00b67f09SDavid van Moolenbroek  * the backend an opportunity to configure parameters related to DLZ.
574*00b67f09SDavid van Moolenbroek  */
575*00b67f09SDavid van Moolenbroek isc_result_t
dns_dlzconfigure(dns_view_t * view,dns_dlzdb_t * dlzdb,dlzconfigure_callback_t callback)576*00b67f09SDavid van Moolenbroek dns_dlzconfigure(dns_view_t *view, dns_dlzdb_t *dlzdb,
577*00b67f09SDavid van Moolenbroek 		 dlzconfigure_callback_t callback)
578*00b67f09SDavid van Moolenbroek {
579*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *impl;
580*00b67f09SDavid van Moolenbroek 	isc_result_t result;
581*00b67f09SDavid van Moolenbroek 
582*00b67f09SDavid van Moolenbroek 	REQUIRE(DNS_DLZ_VALID(dlzdb));
583*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzdb->implementation != NULL);
584*00b67f09SDavid van Moolenbroek 
585*00b67f09SDavid van Moolenbroek 	impl = dlzdb->implementation;
586*00b67f09SDavid van Moolenbroek 
587*00b67f09SDavid van Moolenbroek 	if (impl->methods->configure == NULL)
588*00b67f09SDavid van Moolenbroek 		return (ISC_R_SUCCESS);
589*00b67f09SDavid van Moolenbroek 
590*00b67f09SDavid van Moolenbroek 	dlzdb->configure_callback = callback;
591*00b67f09SDavid van Moolenbroek 
592*00b67f09SDavid van Moolenbroek 	result = impl->methods->configure(impl->driverarg, dlzdb->dbdata,
593*00b67f09SDavid van Moolenbroek 					  view, dlzdb);
594*00b67f09SDavid van Moolenbroek 	return (result);
595*00b67f09SDavid van Moolenbroek }
596*00b67f09SDavid van Moolenbroek 
597*00b67f09SDavid van Moolenbroek isc_boolean_t
dns_dlz_ssumatch(dns_dlzdb_t * dlzdatabase,dns_name_t * signer,dns_name_t * name,isc_netaddr_t * tcpaddr,dns_rdatatype_t type,const dst_key_t * key)598*00b67f09SDavid van Moolenbroek dns_dlz_ssumatch(dns_dlzdb_t *dlzdatabase, dns_name_t *signer,
599*00b67f09SDavid van Moolenbroek 		 dns_name_t *name, isc_netaddr_t *tcpaddr,
600*00b67f09SDavid van Moolenbroek 		 dns_rdatatype_t type, const dst_key_t *key)
601*00b67f09SDavid van Moolenbroek {
602*00b67f09SDavid van Moolenbroek 	dns_dlzimplementation_t *impl;
603*00b67f09SDavid van Moolenbroek 	isc_boolean_t r;
604*00b67f09SDavid van Moolenbroek 
605*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzdatabase != NULL);
606*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzdatabase->implementation != NULL);
607*00b67f09SDavid van Moolenbroek 	REQUIRE(dlzdatabase->implementation->methods != NULL);
608*00b67f09SDavid van Moolenbroek 	impl = dlzdatabase->implementation;
609*00b67f09SDavid van Moolenbroek 
610*00b67f09SDavid van Moolenbroek 	if (impl->methods->ssumatch == NULL) {
611*00b67f09SDavid van Moolenbroek 		isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE,
612*00b67f09SDavid van Moolenbroek 			      DNS_LOGMODULE_DLZ, ISC_LOG_INFO,
613*00b67f09SDavid van Moolenbroek 			      "No ssumatch method for DLZ database");
614*00b67f09SDavid van Moolenbroek 		return (ISC_FALSE);
615*00b67f09SDavid van Moolenbroek 	}
616*00b67f09SDavid van Moolenbroek 
617*00b67f09SDavid van Moolenbroek 	r = impl->methods->ssumatch(signer, name, tcpaddr, type, key,
618*00b67f09SDavid van Moolenbroek 				    impl->driverarg, dlzdatabase->dbdata);
619*00b67f09SDavid van Moolenbroek 	return (r);
620*00b67f09SDavid van Moolenbroek }
621