Home | History | Annotate | Line # | Download | only in dns
xfrin.c revision 1.1.1.5
      1 /*	$NetBSD: xfrin.c,v 1.1.1.5 2020/08/03 17:07:11 christos Exp $	*/
      2 
      3 /*
      4  * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
      5  *
      6  * This Source Code Form is subject to the terms of the Mozilla Public
      7  * License, v. 2.0. If a copy of the MPL was not distributed with this
      8  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
      9  *
     10  * See the COPYRIGHT file distributed with this work for additional
     11  * information regarding copyright ownership.
     12  */
     13 
     14 /*! \file */
     15 
     16 #include <inttypes.h>
     17 #include <stdbool.h>
     18 
     19 #include <isc/mem.h>
     20 #include <isc/print.h>
     21 #include <isc/random.h>
     22 #include <isc/string.h> /* Required for HP/UX (and others?) */
     23 #include <isc/task.h>
     24 #include <isc/timer.h>
     25 #include <isc/util.h>
     26 
     27 #include <dns/callbacks.h>
     28 #include <dns/catz.h>
     29 #include <dns/db.h>
     30 #include <dns/diff.h>
     31 #include <dns/events.h>
     32 #include <dns/journal.h>
     33 #include <dns/log.h>
     34 #include <dns/message.h>
     35 #include <dns/rdataclass.h>
     36 #include <dns/rdatalist.h>
     37 #include <dns/rdataset.h>
     38 #include <dns/result.h>
     39 #include <dns/soa.h>
     40 #include <dns/tcpmsg.h>
     41 #include <dns/timer.h>
     42 #include <dns/tsig.h>
     43 #include <dns/view.h>
     44 #include <dns/xfrin.h>
     45 #include <dns/zone.h>
     46 
     47 #include <dst/dst.h>
     48 
     49 /*
     50  * Incoming AXFR and IXFR.
     51  */
     52 
     53 /*%
     54  * It would be non-sensical (or at least obtuse) to use FAIL() with an
     55  * ISC_R_SUCCESS code, but the test is there to keep the Solaris compiler
     56  * from complaining about "end-of-loop code not reached".
     57  */
     58 #define FAIL(code)                           \
     59 	do {                                 \
     60 		result = (code);             \
     61 		if (result != ISC_R_SUCCESS) \
     62 			goto failure;        \
     63 	} while (0)
     64 
     65 #define CHECK(op)                            \
     66 	do {                                 \
     67 		result = (op);               \
     68 		if (result != ISC_R_SUCCESS) \
     69 			goto failure;        \
     70 	} while (0)
     71 
     72 /*%
     73  * The states of the *XFR state machine.  We handle both IXFR and AXFR
     74  * with a single integrated state machine because they cannot be distinguished
     75  * immediately - an AXFR response to an IXFR request can only be detected
     76  * when the first two (2) response RRs have already been received.
     77  */
     78 typedef enum {
     79 	XFRST_SOAQUERY,
     80 	XFRST_GOTSOA,
     81 	XFRST_INITIALSOA,
     82 	XFRST_FIRSTDATA,
     83 	XFRST_IXFR_DELSOA,
     84 	XFRST_IXFR_DEL,
     85 	XFRST_IXFR_ADDSOA,
     86 	XFRST_IXFR_ADD,
     87 	XFRST_IXFR_END,
     88 	XFRST_AXFR,
     89 	XFRST_AXFR_END
     90 } xfrin_state_t;
     91 
     92 /*%
     93  * Incoming zone transfer context.
     94  */
     95 
     96 struct dns_xfrin_ctx {
     97 	unsigned int magic;
     98 	isc_mem_t *mctx;
     99 	dns_zone_t *zone;
    100 
    101 	int refcount;
    102 
    103 	isc_task_t *task;
    104 	isc_timer_t *timer;
    105 	isc_socketmgr_t *socketmgr;
    106 
    107 	int connects; /*%< Connect in progress */
    108 	int sends;    /*%< Send in progress */
    109 	int recvs;    /*%< Receive in progress */
    110 	bool shuttingdown;
    111 	isc_result_t shutdown_result;
    112 
    113 	dns_name_t name; /*%< Name of zone to transfer */
    114 	dns_rdataclass_t rdclass;
    115 
    116 	bool checkid, logit;
    117 	dns_messageid_t id;
    118 
    119 	/*%
    120 	 * Requested transfer type (dns_rdatatype_axfr or
    121 	 * dns_rdatatype_ixfr).  The actual transfer type
    122 	 * may differ due to IXFR->AXFR fallback.
    123 	 */
    124 	dns_rdatatype_t reqtype;
    125 	isc_dscp_t dscp;
    126 
    127 	isc_sockaddr_t masteraddr;
    128 	isc_sockaddr_t sourceaddr;
    129 	isc_socket_t *socket;
    130 
    131 	/*% Buffer for IXFR/AXFR request message */
    132 	isc_buffer_t qbuffer;
    133 	unsigned char qbuffer_data[512];
    134 
    135 	/*% Incoming reply TCP message */
    136 	dns_tcpmsg_t tcpmsg;
    137 	bool tcpmsg_valid;
    138 
    139 	/*%
    140 	 * Whether the zone originally had a database attached at the time this
    141 	 * transfer context was created.  Used by maybe_free() when making
    142 	 * logging decisions.
    143 	 */
    144 	bool zone_had_db;
    145 
    146 	dns_db_t *db;
    147 	dns_dbversion_t *ver;
    148 	dns_diff_t diff; /*%< Pending database changes */
    149 	int difflen;	 /*%< Number of pending tuples */
    150 
    151 	xfrin_state_t state;
    152 	uint32_t end_serial;
    153 	bool is_ixfr;
    154 
    155 	unsigned int nmsg;  /*%< Number of messages recvd */
    156 	unsigned int nrecs; /*%< Number of records recvd */
    157 	uint64_t nbytes;    /*%< Number of bytes received */
    158 
    159 	unsigned int maxrecords; /*%< The maximum number of
    160 				  *   records set for the zone */
    161 
    162 	isc_time_t start; /*%< Start time of the transfer */
    163 	isc_time_t end;	  /*%< End time of the transfer */
    164 
    165 	dns_tsigkey_t *tsigkey; /*%< Key used to create TSIG */
    166 	isc_buffer_t *lasttsig; /*%< The last TSIG */
    167 	dst_context_t *tsigctx; /*%< TSIG verification context */
    168 	unsigned int sincetsig; /*%< recvd since the last TSIG */
    169 	dns_xfrindone_t done;
    170 
    171 	/*%
    172 	 * AXFR- and IXFR-specific data.  Only one is used at a time
    173 	 * according to the is_ixfr flag, so this could be a union,
    174 	 * but keeping them separate makes it a bit simpler to clean
    175 	 * things up when destroying the context.
    176 	 */
    177 	dns_rdatacallbacks_t axfr;
    178 
    179 	struct {
    180 		uint32_t request_serial;
    181 		uint32_t current_serial;
    182 		dns_journal_t *journal;
    183 	} ixfr;
    184 };
    185 
    186 #define XFRIN_MAGIC    ISC_MAGIC('X', 'f', 'r', 'I')
    187 #define VALID_XFRIN(x) ISC_MAGIC_VALID(x, XFRIN_MAGIC)
    188 
    189 /**************************************************************************/
    190 /*
    191  * Forward declarations.
    192  */
    193 
    194 static isc_result_t
    195 xfrin_create(isc_mem_t *mctx, dns_zone_t *zone, dns_db_t *db, isc_task_t *task,
    196 	     isc_timermgr_t *timermgr, isc_socketmgr_t *socketmgr,
    197 	     dns_name_t *zonename, dns_rdataclass_t rdclass,
    198 	     dns_rdatatype_t reqtype, const isc_sockaddr_t *masteraddr,
    199 	     const isc_sockaddr_t *sourceaddr, isc_dscp_t dscp,
    200 	     dns_tsigkey_t *tsigkey, dns_xfrin_ctx_t **xfrp);
    201 
    202 static isc_result_t
    203 axfr_init(dns_xfrin_ctx_t *xfr);
    204 static isc_result_t
    205 axfr_makedb(dns_xfrin_ctx_t *xfr, dns_db_t **dbp);
    206 static isc_result_t
    207 axfr_putdata(dns_xfrin_ctx_t *xfr, dns_diffop_t op, dns_name_t *name,
    208 	     dns_ttl_t ttl, dns_rdata_t *rdata);
    209 static isc_result_t
    210 axfr_apply(dns_xfrin_ctx_t *xfr);
    211 static isc_result_t
    212 axfr_commit(dns_xfrin_ctx_t *xfr);
    213 static isc_result_t
    214 axfr_finalize(dns_xfrin_ctx_t *xfr);
    215 
    216 static isc_result_t
    217 ixfr_init(dns_xfrin_ctx_t *xfr);
    218 static isc_result_t
    219 ixfr_apply(dns_xfrin_ctx_t *xfr);
    220 static isc_result_t
    221 ixfr_putdata(dns_xfrin_ctx_t *xfr, dns_diffop_t op, dns_name_t *name,
    222 	     dns_ttl_t ttl, dns_rdata_t *rdata);
    223 static isc_result_t
    224 ixfr_commit(dns_xfrin_ctx_t *xfr);
    225 
    226 static isc_result_t
    227 xfr_rr(dns_xfrin_ctx_t *xfr, dns_name_t *name, uint32_t ttl,
    228        dns_rdata_t *rdata);
    229 
    230 static isc_result_t
    231 xfrin_start(dns_xfrin_ctx_t *xfr);
    232 
    233 static void
    234 xfrin_connect_done(isc_task_t *task, isc_event_t *event);
    235 static isc_result_t
    236 xfrin_send_request(dns_xfrin_ctx_t *xfr);
    237 static void
    238 xfrin_send_done(isc_task_t *task, isc_event_t *event);
    239 static void
    240 xfrin_recv_done(isc_task_t *task, isc_event_t *event);
    241 static void
    242 xfrin_timeout(isc_task_t *task, isc_event_t *event);
    243 
    244 static void
    245 maybe_free(dns_xfrin_ctx_t *xfr);
    246 
    247 static void
    248 xfrin_fail(dns_xfrin_ctx_t *xfr, isc_result_t result, const char *msg);
    249 static isc_result_t
    250 render(dns_message_t *msg, isc_mem_t *mctx, isc_buffer_t *buf);
    251 
    252 static void
    253 xfrin_logv(int level, const char *zonetext, const isc_sockaddr_t *masteraddr,
    254 	   const char *fmt, va_list ap) ISC_FORMAT_PRINTF(4, 0);
    255 
    256 static void
    257 xfrin_log1(int level, const char *zonetext, const isc_sockaddr_t *masteraddr,
    258 	   const char *fmt, ...) ISC_FORMAT_PRINTF(4, 5);
    259 
    260 static void
    261 xfrin_log(dns_xfrin_ctx_t *xfr, int level, const char *fmt, ...)
    262 	ISC_FORMAT_PRINTF(3, 4);
    263 
    264 /**************************************************************************/
    265 /*
    266  * AXFR handling
    267  */
    268 
    269 static isc_result_t
    270 axfr_init(dns_xfrin_ctx_t *xfr) {
    271 	isc_result_t result;
    272 
    273 	xfr->is_ixfr = false;
    274 
    275 	if (xfr->db != NULL) {
    276 		dns_db_detach(&xfr->db);
    277 	}
    278 
    279 	CHECK(axfr_makedb(xfr, &xfr->db));
    280 	dns_rdatacallbacks_init(&xfr->axfr);
    281 	CHECK(dns_db_beginload(xfr->db, &xfr->axfr));
    282 	result = ISC_R_SUCCESS;
    283 failure:
    284 	return (result);
    285 }
    286 
    287 static isc_result_t
    288 axfr_makedb(dns_xfrin_ctx_t *xfr, dns_db_t **dbp) {
    289 	isc_result_t result;
    290 
    291 	result = dns_db_create(xfr->mctx, /* XXX */
    292 			       "rbt",	  /* XXX guess */
    293 			       &xfr->name, dns_dbtype_zone, xfr->rdclass, 0,
    294 			       NULL, /* XXX guess */
    295 			       dbp);
    296 	if (result == ISC_R_SUCCESS) {
    297 		dns_zone_rpz_enable_db(xfr->zone, *dbp);
    298 		dns_zone_catz_enable_db(xfr->zone, *dbp);
    299 	}
    300 	return (result);
    301 }
    302 
    303 static isc_result_t
    304 axfr_putdata(dns_xfrin_ctx_t *xfr, dns_diffop_t op, dns_name_t *name,
    305 	     dns_ttl_t ttl, dns_rdata_t *rdata) {
    306 	isc_result_t result;
    307 
    308 	dns_difftuple_t *tuple = NULL;
    309 
    310 	if (rdata->rdclass != xfr->rdclass) {
    311 		return (DNS_R_BADCLASS);
    312 	}
    313 
    314 	CHECK(dns_zone_checknames(xfr->zone, name, rdata));
    315 	CHECK(dns_difftuple_create(xfr->diff.mctx, op, name, ttl, rdata,
    316 				   &tuple));
    317 	dns_diff_append(&xfr->diff, &tuple);
    318 	if (++xfr->difflen > 100) {
    319 		CHECK(axfr_apply(xfr));
    320 	}
    321 	result = ISC_R_SUCCESS;
    322 failure:
    323 	return (result);
    324 }
    325 
    326 /*
    327  * Store a set of AXFR RRs in the database.
    328  */
    329 static isc_result_t
    330 axfr_apply(dns_xfrin_ctx_t *xfr) {
    331 	isc_result_t result;
    332 	uint64_t records;
    333 
    334 	CHECK(dns_diff_load(&xfr->diff, xfr->axfr.add, xfr->axfr.add_private));
    335 	xfr->difflen = 0;
    336 	dns_diff_clear(&xfr->diff);
    337 	if (xfr->maxrecords != 0U) {
    338 		result = dns_db_getsize(xfr->db, xfr->ver, &records, NULL);
    339 		if (result == ISC_R_SUCCESS && records > xfr->maxrecords) {
    340 			result = DNS_R_TOOMANYRECORDS;
    341 			goto failure;
    342 		}
    343 	}
    344 	result = ISC_R_SUCCESS;
    345 failure:
    346 	return (result);
    347 }
    348 
    349 static isc_result_t
    350 axfr_commit(dns_xfrin_ctx_t *xfr) {
    351 	isc_result_t result;
    352 
    353 	CHECK(axfr_apply(xfr));
    354 	CHECK(dns_db_endload(xfr->db, &xfr->axfr));
    355 	CHECK(dns_zone_verifydb(xfr->zone, xfr->db, NULL));
    356 
    357 	result = ISC_R_SUCCESS;
    358 failure:
    359 	return (result);
    360 }
    361 
    362 static isc_result_t
    363 axfr_finalize(dns_xfrin_ctx_t *xfr) {
    364 	isc_result_t result;
    365 
    366 	CHECK(dns_zone_replacedb(xfr->zone, xfr->db, true));
    367 
    368 	result = ISC_R_SUCCESS;
    369 failure:
    370 	return (result);
    371 }
    372 
    373 /**************************************************************************/
    374 /*
    375  * IXFR handling
    376  */
    377 
    378 static isc_result_t
    379 ixfr_init(dns_xfrin_ctx_t *xfr) {
    380 	isc_result_t result;
    381 	char *journalfile;
    382 
    383 	if (xfr->reqtype != dns_rdatatype_ixfr) {
    384 		xfrin_log(xfr, ISC_LOG_ERROR,
    385 			  "got incremental response to AXFR request");
    386 		return (DNS_R_FORMERR);
    387 	}
    388 
    389 	xfr->is_ixfr = true;
    390 	INSIST(xfr->db != NULL);
    391 	xfr->difflen = 0;
    392 
    393 	journalfile = dns_zone_getjournal(xfr->zone);
    394 	if (journalfile != NULL) {
    395 		CHECK(dns_journal_open(xfr->mctx, journalfile,
    396 				       DNS_JOURNAL_CREATE, &xfr->ixfr.journal));
    397 	}
    398 
    399 	result = ISC_R_SUCCESS;
    400 failure:
    401 	return (result);
    402 }
    403 
    404 static isc_result_t
    405 ixfr_putdata(dns_xfrin_ctx_t *xfr, dns_diffop_t op, dns_name_t *name,
    406 	     dns_ttl_t ttl, dns_rdata_t *rdata) {
    407 	isc_result_t result;
    408 	dns_difftuple_t *tuple = NULL;
    409 
    410 	if (rdata->rdclass != xfr->rdclass) {
    411 		return (DNS_R_BADCLASS);
    412 	}
    413 
    414 	if (op == DNS_DIFFOP_ADD) {
    415 		CHECK(dns_zone_checknames(xfr->zone, name, rdata));
    416 	}
    417 	CHECK(dns_difftuple_create(xfr->diff.mctx, op, name, ttl, rdata,
    418 				   &tuple));
    419 	dns_diff_append(&xfr->diff, &tuple);
    420 	if (++xfr->difflen > 100) {
    421 		CHECK(ixfr_apply(xfr));
    422 	}
    423 	result = ISC_R_SUCCESS;
    424 failure:
    425 	return (result);
    426 }
    427 
    428 /*
    429  * Apply a set of IXFR changes to the database.
    430  */
    431 static isc_result_t
    432 ixfr_apply(dns_xfrin_ctx_t *xfr) {
    433 	isc_result_t result;
    434 	uint64_t records;
    435 
    436 	if (xfr->ver == NULL) {
    437 		CHECK(dns_db_newversion(xfr->db, &xfr->ver));
    438 		if (xfr->ixfr.journal != NULL) {
    439 			CHECK(dns_journal_begin_transaction(xfr->ixfr.journal));
    440 		}
    441 	}
    442 	CHECK(dns_diff_apply(&xfr->diff, xfr->db, xfr->ver));
    443 	if (xfr->maxrecords != 0U) {
    444 		result = dns_db_getsize(xfr->db, xfr->ver, &records, NULL);
    445 		if (result == ISC_R_SUCCESS && records > xfr->maxrecords) {
    446 			result = DNS_R_TOOMANYRECORDS;
    447 			goto failure;
    448 		}
    449 	}
    450 	if (xfr->ixfr.journal != NULL) {
    451 		result = dns_journal_writediff(xfr->ixfr.journal, &xfr->diff);
    452 		if (result != ISC_R_SUCCESS) {
    453 			goto failure;
    454 		}
    455 	}
    456 	dns_diff_clear(&xfr->diff);
    457 	xfr->difflen = 0;
    458 	result = ISC_R_SUCCESS;
    459 failure:
    460 	return (result);
    461 }
    462 
    463 static isc_result_t
    464 ixfr_commit(dns_xfrin_ctx_t *xfr) {
    465 	isc_result_t result;
    466 
    467 	CHECK(ixfr_apply(xfr));
    468 	if (xfr->ver != NULL) {
    469 		CHECK(dns_zone_verifydb(xfr->zone, xfr->db, xfr->ver));
    470 		/* XXX enter ready-to-commit state here */
    471 		if (xfr->ixfr.journal != NULL) {
    472 			CHECK(dns_journal_commit(xfr->ixfr.journal));
    473 		}
    474 		dns_db_closeversion(xfr->db, &xfr->ver, true);
    475 		dns_zone_markdirty(xfr->zone);
    476 	}
    477 	result = ISC_R_SUCCESS;
    478 failure:
    479 	return (result);
    480 }
    481 
    482 /**************************************************************************/
    483 /*
    484  * Common AXFR/IXFR protocol code
    485  */
    486 
    487 /*
    488  * Handle a single incoming resource record according to the current
    489  * state.
    490  */
    491 static isc_result_t
    492 xfr_rr(dns_xfrin_ctx_t *xfr, dns_name_t *name, uint32_t ttl,
    493        dns_rdata_t *rdata) {
    494 	isc_result_t result;
    495 
    496 	xfr->nrecs++;
    497 
    498 	if (rdata->type == dns_rdatatype_none ||
    499 	    dns_rdatatype_ismeta(rdata->type)) {
    500 		FAIL(DNS_R_FORMERR);
    501 	}
    502 
    503 redo:
    504 	switch (xfr->state) {
    505 	case XFRST_SOAQUERY:
    506 		if (rdata->type != dns_rdatatype_soa) {
    507 			xfrin_log(xfr, ISC_LOG_ERROR,
    508 				  "non-SOA response to SOA query");
    509 			FAIL(DNS_R_FORMERR);
    510 		}
    511 		xfr->end_serial = dns_soa_getserial(rdata);
    512 		if (!DNS_SERIAL_GT(xfr->end_serial, xfr->ixfr.request_serial) &&
    513 		    !dns_zone_isforced(xfr->zone))
    514 		{
    515 			xfrin_log(xfr, ISC_LOG_DEBUG(3),
    516 				  "requested serial %u, "
    517 				  "master has %u, not updating",
    518 				  xfr->ixfr.request_serial, xfr->end_serial);
    519 			FAIL(DNS_R_UPTODATE);
    520 		}
    521 		xfr->state = XFRST_GOTSOA;
    522 		break;
    523 
    524 	case XFRST_GOTSOA:
    525 		/*
    526 		 * Skip other records in the answer section.
    527 		 */
    528 		break;
    529 
    530 	case XFRST_INITIALSOA:
    531 		if (rdata->type != dns_rdatatype_soa) {
    532 			xfrin_log(xfr, ISC_LOG_ERROR,
    533 				  "first RR in zone transfer must be SOA");
    534 			FAIL(DNS_R_FORMERR);
    535 		}
    536 		/*
    537 		 * Remember the serial number in the initial SOA.
    538 		 * We need it to recognize the end of an IXFR.
    539 		 */
    540 		xfr->end_serial = dns_soa_getserial(rdata);
    541 		if (xfr->reqtype == dns_rdatatype_ixfr &&
    542 		    !DNS_SERIAL_GT(xfr->end_serial, xfr->ixfr.request_serial) &&
    543 		    !dns_zone_isforced(xfr->zone))
    544 		{
    545 			/*
    546 			 * This must be the single SOA record that is
    547 			 * sent when the current version on the master
    548 			 * is not newer than the version in the request.
    549 			 */
    550 			xfrin_log(xfr, ISC_LOG_DEBUG(3),
    551 				  "requested serial %u, "
    552 				  "master has %u, not updating",
    553 				  xfr->ixfr.request_serial, xfr->end_serial);
    554 			FAIL(DNS_R_UPTODATE);
    555 		}
    556 		if (xfr->reqtype == dns_rdatatype_axfr) {
    557 			xfr->checkid = false;
    558 		}
    559 		xfr->state = XFRST_FIRSTDATA;
    560 		break;
    561 
    562 	case XFRST_FIRSTDATA:
    563 		/*
    564 		 * If the transfer begins with one SOA record, it is an AXFR,
    565 		 * if it begins with two SOAs, it is an IXFR.
    566 		 */
    567 		if (xfr->reqtype == dns_rdatatype_ixfr &&
    568 		    rdata->type == dns_rdatatype_soa &&
    569 		    xfr->ixfr.request_serial == dns_soa_getserial(rdata))
    570 		{
    571 			xfrin_log(xfr, ISC_LOG_DEBUG(3),
    572 				  "got incremental response");
    573 			CHECK(ixfr_init(xfr));
    574 			xfr->state = XFRST_IXFR_DELSOA;
    575 		} else {
    576 			xfrin_log(xfr, ISC_LOG_DEBUG(3),
    577 				  "got nonincremental response");
    578 			CHECK(axfr_init(xfr));
    579 			xfr->state = XFRST_AXFR;
    580 		}
    581 		goto redo;
    582 
    583 	case XFRST_IXFR_DELSOA:
    584 		INSIST(rdata->type == dns_rdatatype_soa);
    585 		CHECK(ixfr_putdata(xfr, DNS_DIFFOP_DEL, name, ttl, rdata));
    586 		xfr->state = XFRST_IXFR_DEL;
    587 		break;
    588 
    589 	case XFRST_IXFR_DEL:
    590 		if (rdata->type == dns_rdatatype_soa) {
    591 			uint32_t soa_serial = dns_soa_getserial(rdata);
    592 			xfr->state = XFRST_IXFR_ADDSOA;
    593 			xfr->ixfr.current_serial = soa_serial;
    594 			goto redo;
    595 		}
    596 		CHECK(ixfr_putdata(xfr, DNS_DIFFOP_DEL, name, ttl, rdata));
    597 		break;
    598 
    599 	case XFRST_IXFR_ADDSOA:
    600 		INSIST(rdata->type == dns_rdatatype_soa);
    601 		CHECK(ixfr_putdata(xfr, DNS_DIFFOP_ADD, name, ttl, rdata));
    602 		xfr->state = XFRST_IXFR_ADD;
    603 		break;
    604 
    605 	case XFRST_IXFR_ADD:
    606 		if (rdata->type == dns_rdatatype_soa) {
    607 			uint32_t soa_serial = dns_soa_getserial(rdata);
    608 			if (soa_serial == xfr->end_serial) {
    609 				CHECK(ixfr_commit(xfr));
    610 				xfr->state = XFRST_IXFR_END;
    611 				break;
    612 			} else if (soa_serial != xfr->ixfr.current_serial) {
    613 				xfrin_log(xfr, ISC_LOG_ERROR,
    614 					  "IXFR out of sync: "
    615 					  "expected serial %u, got %u",
    616 					  xfr->ixfr.current_serial, soa_serial);
    617 				FAIL(DNS_R_FORMERR);
    618 			} else {
    619 				CHECK(ixfr_commit(xfr));
    620 				xfr->state = XFRST_IXFR_DELSOA;
    621 				goto redo;
    622 			}
    623 		}
    624 		if (rdata->type == dns_rdatatype_ns &&
    625 		    dns_name_iswildcard(name)) {
    626 			FAIL(DNS_R_INVALIDNS);
    627 		}
    628 		CHECK(ixfr_putdata(xfr, DNS_DIFFOP_ADD, name, ttl, rdata));
    629 		break;
    630 
    631 	case XFRST_AXFR:
    632 		/*
    633 		 * Old BINDs sent cross class A records for non IN classes.
    634 		 */
    635 		if (rdata->type == dns_rdatatype_a &&
    636 		    rdata->rdclass != xfr->rdclass &&
    637 		    xfr->rdclass != dns_rdataclass_in)
    638 		{
    639 			break;
    640 		}
    641 		CHECK(axfr_putdata(xfr, DNS_DIFFOP_ADD, name, ttl, rdata));
    642 		if (rdata->type == dns_rdatatype_soa) {
    643 			CHECK(axfr_commit(xfr));
    644 			xfr->state = XFRST_AXFR_END;
    645 			break;
    646 		}
    647 		break;
    648 	case XFRST_AXFR_END:
    649 	case XFRST_IXFR_END:
    650 		FAIL(DNS_R_EXTRADATA);
    651 	/* NOTREACHED */
    652 	/* FALLTHROUGH */
    653 	default:
    654 		INSIST(0);
    655 		ISC_UNREACHABLE();
    656 	}
    657 	result = ISC_R_SUCCESS;
    658 failure:
    659 	return (result);
    660 }
    661 
    662 isc_result_t
    663 dns_xfrin_create(dns_zone_t *zone, dns_rdatatype_t xfrtype,
    664 		 const isc_sockaddr_t *masteraddr,
    665 		 const isc_sockaddr_t *sourceaddr, isc_dscp_t dscp,
    666 		 dns_tsigkey_t *tsigkey, isc_mem_t *mctx,
    667 		 isc_timermgr_t *timermgr, isc_socketmgr_t *socketmgr,
    668 		 isc_task_t *task, dns_xfrindone_t done,
    669 		 dns_xfrin_ctx_t **xfrp) {
    670 	dns_name_t *zonename = dns_zone_getorigin(zone);
    671 	dns_xfrin_ctx_t *xfr = NULL;
    672 	isc_result_t result;
    673 	dns_db_t *db = NULL;
    674 
    675 	REQUIRE(xfrp != NULL && *xfrp == NULL);
    676 
    677 	(void)dns_zone_getdb(zone, &db);
    678 
    679 	if (xfrtype == dns_rdatatype_soa || xfrtype == dns_rdatatype_ixfr) {
    680 		REQUIRE(db != NULL);
    681 	}
    682 
    683 	CHECK(xfrin_create(mctx, zone, db, task, timermgr, socketmgr, zonename,
    684 			   dns_zone_getclass(zone), xfrtype, masteraddr,
    685 			   sourceaddr, dscp, tsigkey, &xfr));
    686 
    687 	if (db != NULL) {
    688 		xfr->zone_had_db = true;
    689 	}
    690 
    691 	CHECK(xfrin_start(xfr));
    692 
    693 	xfr->done = done;
    694 	if (xfr->done != NULL) {
    695 		xfr->refcount++;
    696 	}
    697 	*xfrp = xfr;
    698 
    699 failure:
    700 	if (db != NULL) {
    701 		dns_db_detach(&db);
    702 	}
    703 	if (result != ISC_R_SUCCESS) {
    704 		char zonetext[DNS_NAME_MAXTEXT + 32];
    705 		dns_zone_name(zone, zonetext, sizeof(zonetext));
    706 		xfrin_log1(ISC_LOG_ERROR, zonetext, masteraddr,
    707 			   "zone transfer setup failed");
    708 	}
    709 	return (result);
    710 }
    711 
    712 void
    713 dns_xfrin_shutdown(dns_xfrin_ctx_t *xfr) {
    714 	if (!xfr->shuttingdown) {
    715 		xfrin_fail(xfr, ISC_R_CANCELED, "shut down");
    716 	}
    717 }
    718 
    719 void
    720 dns_xfrin_attach(dns_xfrin_ctx_t *source, dns_xfrin_ctx_t **target) {
    721 	REQUIRE(target != NULL && *target == NULL);
    722 	source->refcount++;
    723 	*target = source;
    724 }
    725 
    726 void
    727 dns_xfrin_detach(dns_xfrin_ctx_t **xfrp) {
    728 	dns_xfrin_ctx_t *xfr = *xfrp;
    729 	*xfrp = NULL;
    730 	INSIST(xfr->refcount > 0);
    731 	xfr->refcount--;
    732 	maybe_free(xfr);
    733 }
    734 
    735 static void
    736 xfrin_cancelio(dns_xfrin_ctx_t *xfr) {
    737 	if (xfr->connects > 0) {
    738 		isc_socket_cancel(xfr->socket, xfr->task,
    739 				  ISC_SOCKCANCEL_CONNECT);
    740 	} else if (xfr->recvs > 0) {
    741 		dns_tcpmsg_cancelread(&xfr->tcpmsg);
    742 	} else if (xfr->sends > 0) {
    743 		isc_socket_cancel(xfr->socket, xfr->task, ISC_SOCKCANCEL_SEND);
    744 	}
    745 }
    746 
    747 static void
    748 xfrin_reset(dns_xfrin_ctx_t *xfr) {
    749 	REQUIRE(VALID_XFRIN(xfr));
    750 
    751 	xfrin_log(xfr, ISC_LOG_INFO, "resetting");
    752 
    753 	xfrin_cancelio(xfr);
    754 
    755 	if (xfr->socket != NULL) {
    756 		isc_socket_detach(&xfr->socket);
    757 	}
    758 
    759 	if (xfr->lasttsig != NULL) {
    760 		isc_buffer_free(&xfr->lasttsig);
    761 	}
    762 
    763 	dns_diff_clear(&xfr->diff);
    764 	xfr->difflen = 0;
    765 
    766 	if (xfr->ixfr.journal != NULL) {
    767 		dns_journal_destroy(&xfr->ixfr.journal);
    768 	}
    769 
    770 	if (xfr->axfr.add_private != NULL) {
    771 		(void)dns_db_endload(xfr->db, &xfr->axfr);
    772 	}
    773 
    774 	if (xfr->tcpmsg_valid) {
    775 		dns_tcpmsg_invalidate(&xfr->tcpmsg);
    776 		xfr->tcpmsg_valid = false;
    777 	}
    778 
    779 	if (xfr->ver != NULL) {
    780 		dns_db_closeversion(xfr->db, &xfr->ver, false);
    781 	}
    782 }
    783 
    784 static void
    785 xfrin_fail(dns_xfrin_ctx_t *xfr, isc_result_t result, const char *msg) {
    786 	if (result != DNS_R_UPTODATE && result != DNS_R_TOOMANYRECORDS) {
    787 		xfrin_log(xfr, ISC_LOG_ERROR, "%s: %s", msg,
    788 			  isc_result_totext(result));
    789 		if (xfr->is_ixfr) {
    790 			/* Pass special result code to force AXFR retry */
    791 			result = DNS_R_BADIXFR;
    792 		}
    793 	}
    794 	xfrin_cancelio(xfr);
    795 	/*
    796 	 * Close the journal.
    797 	 */
    798 	if (xfr->ixfr.journal != NULL) {
    799 		dns_journal_destroy(&xfr->ixfr.journal);
    800 	}
    801 	if (xfr->done != NULL) {
    802 		(xfr->done)(xfr->zone, result);
    803 		xfr->done = NULL;
    804 	}
    805 	xfr->shuttingdown = true;
    806 	xfr->shutdown_result = result;
    807 	maybe_free(xfr);
    808 }
    809 
    810 static isc_result_t
    811 xfrin_create(isc_mem_t *mctx, dns_zone_t *zone, dns_db_t *db, isc_task_t *task,
    812 	     isc_timermgr_t *timermgr, isc_socketmgr_t *socketmgr,
    813 	     dns_name_t *zonename, dns_rdataclass_t rdclass,
    814 	     dns_rdatatype_t reqtype, const isc_sockaddr_t *masteraddr,
    815 	     const isc_sockaddr_t *sourceaddr, isc_dscp_t dscp,
    816 	     dns_tsigkey_t *tsigkey, dns_xfrin_ctx_t **xfrp) {
    817 	dns_xfrin_ctx_t *xfr = NULL;
    818 	isc_result_t result;
    819 
    820 	xfr = isc_mem_get(mctx, sizeof(*xfr));
    821 	xfr->mctx = NULL;
    822 	isc_mem_attach(mctx, &xfr->mctx);
    823 	xfr->refcount = 0;
    824 	xfr->zone = NULL;
    825 	dns_zone_iattach(zone, &xfr->zone);
    826 	xfr->task = NULL;
    827 	isc_task_attach(task, &xfr->task);
    828 	xfr->timer = NULL;
    829 	xfr->socketmgr = socketmgr;
    830 	xfr->done = NULL;
    831 
    832 	xfr->connects = 0;
    833 	xfr->sends = 0;
    834 	xfr->recvs = 0;
    835 	xfr->shuttingdown = false;
    836 	xfr->shutdown_result = ISC_R_UNSET;
    837 
    838 	dns_name_init(&xfr->name, NULL);
    839 	xfr->rdclass = rdclass;
    840 	xfr->checkid = true;
    841 	xfr->logit = true;
    842 	xfr->id = (dns_messageid_t)isc_random16();
    843 	xfr->reqtype = reqtype;
    844 	xfr->dscp = dscp;
    845 
    846 	/* sockaddr */
    847 	xfr->socket = NULL;
    848 	/* qbuffer */
    849 	/* qbuffer_data */
    850 	/* tcpmsg */
    851 	xfr->tcpmsg_valid = false;
    852 
    853 	xfr->zone_had_db = false;
    854 	xfr->db = NULL;
    855 	if (db != NULL) {
    856 		dns_db_attach(db, &xfr->db);
    857 	}
    858 	xfr->ver = NULL;
    859 	dns_diff_init(xfr->mctx, &xfr->diff);
    860 	xfr->difflen = 0;
    861 
    862 	if (reqtype == dns_rdatatype_soa) {
    863 		xfr->state = XFRST_SOAQUERY;
    864 	} else {
    865 		xfr->state = XFRST_INITIALSOA;
    866 	}
    867 	/* end_serial */
    868 
    869 	xfr->nmsg = 0;
    870 	xfr->nrecs = 0;
    871 	xfr->nbytes = 0;
    872 	xfr->maxrecords = dns_zone_getmaxrecords(zone);
    873 	isc_time_now(&xfr->start);
    874 
    875 	xfr->tsigkey = NULL;
    876 	if (tsigkey != NULL) {
    877 		dns_tsigkey_attach(tsigkey, &xfr->tsigkey);
    878 	}
    879 	xfr->lasttsig = NULL;
    880 	xfr->tsigctx = NULL;
    881 	xfr->sincetsig = 0;
    882 	xfr->is_ixfr = false;
    883 
    884 	/* ixfr.request_serial */
    885 	/* ixfr.current_serial */
    886 	xfr->ixfr.journal = NULL;
    887 
    888 	xfr->axfr.add = NULL;
    889 	xfr->axfr.add_private = NULL;
    890 
    891 	dns_name_dup(zonename, mctx, &xfr->name);
    892 
    893 	CHECK(isc_timer_create(timermgr, isc_timertype_inactive, NULL, NULL,
    894 			       task, xfrin_timeout, xfr, &xfr->timer));
    895 	CHECK(dns_timer_setidle(xfr->timer, dns_zone_getmaxxfrin(xfr->zone),
    896 				dns_zone_getidlein(xfr->zone), false));
    897 
    898 	xfr->masteraddr = *masteraddr;
    899 
    900 	INSIST(isc_sockaddr_pf(masteraddr) == isc_sockaddr_pf(sourceaddr));
    901 	xfr->sourceaddr = *sourceaddr;
    902 	isc_sockaddr_setport(&xfr->sourceaddr, 0);
    903 
    904 	/*
    905 	 * Reserve 2 bytes for TCP length at the beginning of the buffer.
    906 	 */
    907 	isc_buffer_init(&xfr->qbuffer, &xfr->qbuffer_data[2],
    908 			sizeof(xfr->qbuffer_data) - 2);
    909 
    910 	xfr->magic = XFRIN_MAGIC;
    911 	*xfrp = xfr;
    912 	return (ISC_R_SUCCESS);
    913 
    914 failure:
    915 	if (xfr->timer != NULL) {
    916 		isc_timer_detach(&xfr->timer);
    917 	}
    918 	if (dns_name_dynamic(&xfr->name)) {
    919 		dns_name_free(&xfr->name, xfr->mctx);
    920 	}
    921 	if (xfr->tsigkey != NULL) {
    922 		dns_tsigkey_detach(&xfr->tsigkey);
    923 	}
    924 	if (xfr->db != NULL) {
    925 		dns_db_detach(&xfr->db);
    926 	}
    927 	isc_task_detach(&xfr->task);
    928 	dns_zone_idetach(&xfr->zone);
    929 	isc_mem_putanddetach(&xfr->mctx, xfr, sizeof(*xfr));
    930 
    931 	return (result);
    932 }
    933 
    934 static isc_result_t
    935 xfrin_start(dns_xfrin_ctx_t *xfr) {
    936 	isc_result_t result;
    937 	CHECK(isc_socket_create(xfr->socketmgr,
    938 				isc_sockaddr_pf(&xfr->sourceaddr),
    939 				isc_sockettype_tcp, &xfr->socket));
    940 	isc_socket_setname(xfr->socket, "xfrin", NULL);
    941 #ifndef BROKEN_TCP_BIND_BEFORE_CONNECT
    942 	CHECK(isc_socket_bind(xfr->socket, &xfr->sourceaddr,
    943 			      ISC_SOCKET_REUSEADDRESS));
    944 #endif /* ifndef BROKEN_TCP_BIND_BEFORE_CONNECT */
    945 	isc_socket_dscp(xfr->socket, xfr->dscp);
    946 	CHECK(isc_socket_connect(xfr->socket, &xfr->masteraddr, xfr->task,
    947 				 xfrin_connect_done, xfr));
    948 	xfr->connects++;
    949 	return (ISC_R_SUCCESS);
    950 failure:
    951 	xfrin_fail(xfr, result, "failed setting up socket");
    952 	return (result);
    953 }
    954 
    955 /* XXX the resolver could use this, too */
    956 
    957 static isc_result_t
    958 render(dns_message_t *msg, isc_mem_t *mctx, isc_buffer_t *buf) {
    959 	dns_compress_t cctx;
    960 	bool cleanup_cctx = false;
    961 	isc_result_t result;
    962 
    963 	CHECK(dns_compress_init(&cctx, -1, mctx));
    964 	cleanup_cctx = true;
    965 	CHECK(dns_message_renderbegin(msg, &cctx, buf));
    966 	CHECK(dns_message_rendersection(msg, DNS_SECTION_QUESTION, 0));
    967 	CHECK(dns_message_rendersection(msg, DNS_SECTION_ANSWER, 0));
    968 	CHECK(dns_message_rendersection(msg, DNS_SECTION_AUTHORITY, 0));
    969 	CHECK(dns_message_rendersection(msg, DNS_SECTION_ADDITIONAL, 0));
    970 	CHECK(dns_message_renderend(msg));
    971 	result = ISC_R_SUCCESS;
    972 failure:
    973 	if (cleanup_cctx) {
    974 		dns_compress_invalidate(&cctx);
    975 	}
    976 	return (result);
    977 }
    978 
    979 /*
    980  * A connection has been established.
    981  */
    982 static void
    983 xfrin_connect_done(isc_task_t *task, isc_event_t *event) {
    984 	isc_socket_connev_t *cev = (isc_socket_connev_t *)event;
    985 	dns_xfrin_ctx_t *xfr = (dns_xfrin_ctx_t *)event->ev_arg;
    986 	isc_result_t result = cev->result;
    987 	char sourcetext[ISC_SOCKADDR_FORMATSIZE];
    988 	char signerbuf[DNS_NAME_FORMATSIZE];
    989 	const char *signer = "", *sep = "";
    990 	isc_sockaddr_t sockaddr;
    991 	dns_zonemgr_t *zmgr;
    992 	isc_time_t now;
    993 
    994 	REQUIRE(VALID_XFRIN(xfr));
    995 
    996 	UNUSED(task);
    997 
    998 	INSIST(event->ev_type == ISC_SOCKEVENT_CONNECT);
    999 	isc_event_free(&event);
   1000 
   1001 	xfr->connects--;
   1002 	if (xfr->shuttingdown) {
   1003 		maybe_free(xfr);
   1004 		return;
   1005 	}
   1006 
   1007 	zmgr = dns_zone_getmgr(xfr->zone);
   1008 	if (zmgr != NULL) {
   1009 		if (result != ISC_R_SUCCESS) {
   1010 			TIME_NOW(&now);
   1011 			dns_zonemgr_unreachableadd(zmgr, &xfr->masteraddr,
   1012 						   &xfr->sourceaddr, &now);
   1013 			goto failure;
   1014 		} else {
   1015 			dns_zonemgr_unreachabledel(zmgr, &xfr->masteraddr,
   1016 						   &xfr->sourceaddr);
   1017 		}
   1018 	}
   1019 
   1020 	result = isc_socket_getsockname(xfr->socket, &sockaddr);
   1021 	if (result == ISC_R_SUCCESS) {
   1022 		isc_sockaddr_format(&sockaddr, sourcetext, sizeof(sourcetext));
   1023 	} else {
   1024 		strlcpy(sourcetext, "<UNKNOWN>", sizeof(sourcetext));
   1025 	}
   1026 
   1027 	if (xfr->tsigkey != NULL && xfr->tsigkey->key != NULL) {
   1028 		dns_name_format(dst_key_name(xfr->tsigkey->key), signerbuf,
   1029 				sizeof(signerbuf));
   1030 		sep = " TSIG ";
   1031 		signer = signerbuf;
   1032 	}
   1033 
   1034 	xfrin_log(xfr, ISC_LOG_INFO, "connected using %s%s%s", sourcetext, sep,
   1035 		  signer);
   1036 
   1037 	dns_tcpmsg_init(xfr->mctx, xfr->socket, &xfr->tcpmsg);
   1038 	xfr->tcpmsg_valid = true;
   1039 
   1040 	CHECK(xfrin_send_request(xfr));
   1041 failure:
   1042 	if (result != ISC_R_SUCCESS) {
   1043 		xfrin_fail(xfr, result, "failed to connect");
   1044 	}
   1045 }
   1046 
   1047 /*
   1048  * Convert a tuple into a dns_name_t suitable for inserting
   1049  * into the given dns_message_t.
   1050  */
   1051 static isc_result_t
   1052 tuple2msgname(dns_difftuple_t *tuple, dns_message_t *msg, dns_name_t **target) {
   1053 	isc_result_t result;
   1054 	dns_rdata_t *rdata = NULL;
   1055 	dns_rdatalist_t *rdl = NULL;
   1056 	dns_rdataset_t *rds = NULL;
   1057 	dns_name_t *name = NULL;
   1058 
   1059 	REQUIRE(target != NULL && *target == NULL);
   1060 
   1061 	CHECK(dns_message_gettemprdata(msg, &rdata));
   1062 	dns_rdata_init(rdata);
   1063 	dns_rdata_clone(&tuple->rdata, rdata);
   1064 
   1065 	CHECK(dns_message_gettemprdatalist(msg, &rdl));
   1066 	dns_rdatalist_init(rdl);
   1067 	rdl->type = tuple->rdata.type;
   1068 	rdl->rdclass = tuple->rdata.rdclass;
   1069 	rdl->ttl = tuple->ttl;
   1070 	ISC_LIST_APPEND(rdl->rdata, rdata, link);
   1071 
   1072 	CHECK(dns_message_gettemprdataset(msg, &rds));
   1073 	CHECK(dns_rdatalist_tordataset(rdl, rds));
   1074 
   1075 	CHECK(dns_message_gettempname(msg, &name));
   1076 	dns_name_init(name, NULL);
   1077 	dns_name_clone(&tuple->name, name);
   1078 	ISC_LIST_APPEND(name->list, rds, link);
   1079 
   1080 	*target = name;
   1081 	return (ISC_R_SUCCESS);
   1082 
   1083 failure:
   1084 
   1085 	if (rds != NULL) {
   1086 		dns_rdataset_disassociate(rds);
   1087 		dns_message_puttemprdataset(msg, &rds);
   1088 	}
   1089 	if (rdl != NULL) {
   1090 		ISC_LIST_UNLINK(rdl->rdata, rdata, link);
   1091 		dns_message_puttemprdatalist(msg, &rdl);
   1092 	}
   1093 	if (rdata != NULL) {
   1094 		dns_message_puttemprdata(msg, &rdata);
   1095 	}
   1096 
   1097 	return (result);
   1098 }
   1099 
   1100 /*
   1101  * Build an *XFR request and send its length prefix.
   1102  */
   1103 static isc_result_t
   1104 xfrin_send_request(dns_xfrin_ctx_t *xfr) {
   1105 	isc_result_t result;
   1106 	isc_region_t region;
   1107 	dns_rdataset_t *qrdataset = NULL;
   1108 	dns_message_t *msg = NULL;
   1109 	dns_difftuple_t *soatuple = NULL;
   1110 	dns_name_t *qname = NULL;
   1111 	dns_dbversion_t *ver = NULL;
   1112 	dns_name_t *msgsoaname = NULL;
   1113 
   1114 	/* Create the request message */
   1115 	CHECK(dns_message_create(xfr->mctx, DNS_MESSAGE_INTENTRENDER, &msg));
   1116 	CHECK(dns_message_settsigkey(msg, xfr->tsigkey));
   1117 
   1118 	/* Create a name for the question section. */
   1119 	CHECK(dns_message_gettempname(msg, &qname));
   1120 	dns_name_init(qname, NULL);
   1121 	dns_name_clone(&xfr->name, qname);
   1122 
   1123 	/* Formulate the question and attach it to the question name. */
   1124 	CHECK(dns_message_gettemprdataset(msg, &qrdataset));
   1125 	dns_rdataset_makequestion(qrdataset, xfr->rdclass, xfr->reqtype);
   1126 	ISC_LIST_APPEND(qname->list, qrdataset, link);
   1127 	qrdataset = NULL;
   1128 
   1129 	dns_message_addname(msg, qname, DNS_SECTION_QUESTION);
   1130 	qname = NULL;
   1131 
   1132 	if (xfr->reqtype == dns_rdatatype_ixfr) {
   1133 		/* Get the SOA and add it to the authority section. */
   1134 		/* XXX is using the current version the right thing? */
   1135 		dns_db_currentversion(xfr->db, &ver);
   1136 		CHECK(dns_db_createsoatuple(xfr->db, ver, xfr->mctx,
   1137 					    DNS_DIFFOP_EXISTS, &soatuple));
   1138 		xfr->ixfr.request_serial = dns_soa_getserial(&soatuple->rdata);
   1139 		xfr->ixfr.current_serial = xfr->ixfr.request_serial;
   1140 		xfrin_log(xfr, ISC_LOG_DEBUG(3),
   1141 			  "requesting IXFR for serial %u",
   1142 			  xfr->ixfr.request_serial);
   1143 
   1144 		CHECK(tuple2msgname(soatuple, msg, &msgsoaname));
   1145 		dns_message_addname(msg, msgsoaname, DNS_SECTION_AUTHORITY);
   1146 	} else if (xfr->reqtype == dns_rdatatype_soa) {
   1147 		CHECK(dns_db_getsoaserial(xfr->db, NULL,
   1148 					  &xfr->ixfr.request_serial));
   1149 	}
   1150 
   1151 	xfr->checkid = true;
   1152 	xfr->logit = true;
   1153 	xfr->id++;
   1154 	xfr->nmsg = 0;
   1155 	xfr->nrecs = 0;
   1156 	xfr->nbytes = 0;
   1157 	isc_time_now(&xfr->start);
   1158 	msg->id = xfr->id;
   1159 	if (xfr->tsigctx != NULL) {
   1160 		dst_context_destroy(&xfr->tsigctx);
   1161 	}
   1162 
   1163 	CHECK(render(msg, xfr->mctx, &xfr->qbuffer));
   1164 
   1165 	/*
   1166 	 * Free the last tsig, if there is one.
   1167 	 */
   1168 	if (xfr->lasttsig != NULL) {
   1169 		isc_buffer_free(&xfr->lasttsig);
   1170 	}
   1171 
   1172 	/*
   1173 	 * Save the query TSIG and don't let message_destroy free it.
   1174 	 */
   1175 	CHECK(dns_message_getquerytsig(msg, xfr->mctx, &xfr->lasttsig));
   1176 
   1177 	isc_buffer_usedregion(&xfr->qbuffer, &region);
   1178 	INSIST(region.length <= 65535);
   1179 
   1180 	/*
   1181 	 * Record message length and adjust region to include TCP
   1182 	 * length field.
   1183 	 */
   1184 	xfr->qbuffer_data[0] = (region.length >> 8) & 0xff;
   1185 	xfr->qbuffer_data[1] = region.length & 0xff;
   1186 	region.base -= 2;
   1187 	region.length += 2;
   1188 	CHECK(isc_socket_send(xfr->socket, &region, xfr->task, xfrin_send_done,
   1189 			      xfr));
   1190 	xfr->sends++;
   1191 
   1192 failure:
   1193 	if (qname != NULL) {
   1194 		dns_message_puttempname(msg, &qname);
   1195 	}
   1196 	if (qrdataset != NULL) {
   1197 		dns_message_puttemprdataset(msg, &qrdataset);
   1198 	}
   1199 	if (msg != NULL) {
   1200 		dns_message_destroy(&msg);
   1201 	}
   1202 	if (soatuple != NULL) {
   1203 		dns_difftuple_free(&soatuple);
   1204 	}
   1205 	if (ver != NULL) {
   1206 		dns_db_closeversion(xfr->db, &ver, false);
   1207 	}
   1208 	return (result);
   1209 }
   1210 
   1211 static void
   1212 xfrin_send_done(isc_task_t *task, isc_event_t *event) {
   1213 	isc_socketevent_t *sev = (isc_socketevent_t *)event;
   1214 	dns_xfrin_ctx_t *xfr = (dns_xfrin_ctx_t *)event->ev_arg;
   1215 	isc_result_t result;
   1216 
   1217 	REQUIRE(VALID_XFRIN(xfr));
   1218 
   1219 	UNUSED(task);
   1220 
   1221 	INSIST(event->ev_type == ISC_SOCKEVENT_SENDDONE);
   1222 
   1223 	xfr->sends--;
   1224 	xfrin_log(xfr, ISC_LOG_DEBUG(3), "sent request data");
   1225 	CHECK(sev->result);
   1226 
   1227 	CHECK(dns_tcpmsg_readmessage(&xfr->tcpmsg, xfr->task, xfrin_recv_done,
   1228 				     xfr));
   1229 	xfr->recvs++;
   1230 failure:
   1231 	isc_event_free(&event);
   1232 	if (result != ISC_R_SUCCESS) {
   1233 		xfrin_fail(xfr, result, "failed sending request data");
   1234 	}
   1235 }
   1236 
   1237 static void
   1238 xfrin_recv_done(isc_task_t *task, isc_event_t *ev) {
   1239 	dns_xfrin_ctx_t *xfr = (dns_xfrin_ctx_t *)ev->ev_arg;
   1240 	isc_result_t result;
   1241 	dns_message_t *msg = NULL;
   1242 	dns_name_t *name;
   1243 	dns_tcpmsg_t *tcpmsg;
   1244 	const dns_name_t *tsigowner = NULL;
   1245 
   1246 	REQUIRE(VALID_XFRIN(xfr));
   1247 
   1248 	UNUSED(task);
   1249 
   1250 	INSIST(ev->ev_type == DNS_EVENT_TCPMSG);
   1251 	tcpmsg = ev->ev_sender;
   1252 	isc_event_free(&ev);
   1253 
   1254 	xfr->recvs--;
   1255 	if (xfr->shuttingdown) {
   1256 		maybe_free(xfr);
   1257 		return;
   1258 	}
   1259 
   1260 	CHECK(tcpmsg->result);
   1261 
   1262 	xfrin_log(xfr, ISC_LOG_DEBUG(7), "received %u bytes",
   1263 		  tcpmsg->buffer.used);
   1264 
   1265 	CHECK(isc_timer_touch(xfr->timer));
   1266 
   1267 	CHECK(dns_message_create(xfr->mctx, DNS_MESSAGE_INTENTPARSE, &msg));
   1268 
   1269 	CHECK(dns_message_settsigkey(msg, xfr->tsigkey));
   1270 	CHECK(dns_message_setquerytsig(msg, xfr->lasttsig));
   1271 
   1272 	msg->tsigctx = xfr->tsigctx;
   1273 	xfr->tsigctx = NULL;
   1274 
   1275 	dns_message_setclass(msg, xfr->rdclass);
   1276 
   1277 	if (xfr->nmsg > 0) {
   1278 		msg->tcp_continuation = 1;
   1279 	}
   1280 
   1281 	result = dns_message_parse(msg, &tcpmsg->buffer,
   1282 				   DNS_MESSAGEPARSE_PRESERVEORDER);
   1283 
   1284 	if (result == ISC_R_SUCCESS) {
   1285 		dns_message_logpacket(msg, "received message from",
   1286 				      &tcpmsg->address, DNS_LOGCATEGORY_XFER_IN,
   1287 				      DNS_LOGMODULE_XFER_IN, ISC_LOG_DEBUG(10),
   1288 				      xfr->mctx);
   1289 	} else {
   1290 		xfrin_log(xfr, ISC_LOG_DEBUG(10), "dns_message_parse: %s",
   1291 			  dns_result_totext(result));
   1292 	}
   1293 
   1294 	if (result != ISC_R_SUCCESS || msg->rcode != dns_rcode_noerror ||
   1295 	    msg->opcode != dns_opcode_query || msg->rdclass != xfr->rdclass ||
   1296 	    (xfr->checkid && msg->id != xfr->id))
   1297 	{
   1298 		if (result == ISC_R_SUCCESS && msg->rcode != dns_rcode_noerror)
   1299 		{
   1300 			result = ISC_RESULTCLASS_DNSRCODE + msg->rcode; /*XXX*/
   1301 		} else if (result == ISC_R_SUCCESS &&
   1302 			   msg->opcode != dns_opcode_query) {
   1303 			result = DNS_R_UNEXPECTEDOPCODE;
   1304 		} else if (result == ISC_R_SUCCESS &&
   1305 			   msg->rdclass != xfr->rdclass) {
   1306 			result = DNS_R_BADCLASS;
   1307 		} else if (result == ISC_R_SUCCESS || result == DNS_R_NOERROR) {
   1308 			result = DNS_R_UNEXPECTEDID;
   1309 		}
   1310 		if (xfr->reqtype == dns_rdatatype_axfr ||
   1311 		    xfr->reqtype == dns_rdatatype_soa) {
   1312 			goto failure;
   1313 		}
   1314 		xfrin_log(xfr, ISC_LOG_DEBUG(3), "got %s, retrying with AXFR",
   1315 			  isc_result_totext(result));
   1316 	try_axfr:
   1317 		dns_message_destroy(&msg);
   1318 		xfrin_reset(xfr);
   1319 		xfr->reqtype = dns_rdatatype_soa;
   1320 		xfr->state = XFRST_SOAQUERY;
   1321 		(void)xfrin_start(xfr);
   1322 		return;
   1323 	} else if (!xfr->checkid && msg->id != xfr->id && xfr->logit) {
   1324 		xfrin_log(xfr, ISC_LOG_WARNING,
   1325 			  "detected message ID mismatch on incoming AXFR "
   1326 			  "stream, transfer will fail in BIND 9.17.2 and "
   1327 			  "later if AXFR source is not fixed");
   1328 		xfr->logit = false;
   1329 	}
   1330 
   1331 	/*
   1332 	 * Does the server know about IXFR?  If it doesn't we will get
   1333 	 * a message with a empty answer section or a potentially a CNAME /
   1334 	 * DNAME, the later is handled by xfr_rr() which will return FORMERR
   1335 	 * if the first RR in the answer section is not a SOA record.
   1336 	 */
   1337 	if (xfr->reqtype == dns_rdatatype_ixfr &&
   1338 	    xfr->state == XFRST_INITIALSOA &&
   1339 	    msg->counts[DNS_SECTION_ANSWER] == 0)
   1340 	{
   1341 		xfrin_log(xfr, ISC_LOG_DEBUG(3),
   1342 			  "empty answer section, retrying with AXFR");
   1343 		goto try_axfr;
   1344 	}
   1345 
   1346 	if (xfr->reqtype == dns_rdatatype_soa &&
   1347 	    (msg->flags & DNS_MESSAGEFLAG_AA) == 0) {
   1348 		FAIL(DNS_R_NOTAUTHORITATIVE);
   1349 	}
   1350 
   1351 	result = dns_message_checksig(msg, dns_zone_getview(xfr->zone));
   1352 	if (result != ISC_R_SUCCESS) {
   1353 		xfrin_log(xfr, ISC_LOG_DEBUG(3), "TSIG check failed: %s",
   1354 			  isc_result_totext(result));
   1355 		goto failure;
   1356 	}
   1357 
   1358 	for (result = dns_message_firstname(msg, DNS_SECTION_ANSWER);
   1359 	     result == ISC_R_SUCCESS;
   1360 	     result = dns_message_nextname(msg, DNS_SECTION_ANSWER))
   1361 	{
   1362 		dns_rdataset_t *rds;
   1363 
   1364 		name = NULL;
   1365 		dns_message_currentname(msg, DNS_SECTION_ANSWER, &name);
   1366 		for (rds = ISC_LIST_HEAD(name->list); rds != NULL;
   1367 		     rds = ISC_LIST_NEXT(rds, link))
   1368 		{
   1369 			for (result = dns_rdataset_first(rds);
   1370 			     result == ISC_R_SUCCESS;
   1371 			     result = dns_rdataset_next(rds))
   1372 			{
   1373 				dns_rdata_t rdata = DNS_RDATA_INIT;
   1374 				dns_rdataset_current(rds, &rdata);
   1375 				CHECK(xfr_rr(xfr, name, rds->ttl, &rdata));
   1376 			}
   1377 		}
   1378 	}
   1379 	if (result != ISC_R_NOMORE) {
   1380 		goto failure;
   1381 	}
   1382 
   1383 	if (dns_message_gettsig(msg, &tsigowner) != NULL) {
   1384 		/*
   1385 		 * Reset the counter.
   1386 		 */
   1387 		xfr->sincetsig = 0;
   1388 
   1389 		/*
   1390 		 * Free the last tsig, if there is one.
   1391 		 */
   1392 		if (xfr->lasttsig != NULL) {
   1393 			isc_buffer_free(&xfr->lasttsig);
   1394 		}
   1395 
   1396 		/*
   1397 		 * Update the last tsig pointer.
   1398 		 */
   1399 		CHECK(dns_message_getquerytsig(msg, xfr->mctx, &xfr->lasttsig));
   1400 	} else if (dns_message_gettsigkey(msg) != NULL) {
   1401 		xfr->sincetsig++;
   1402 		if (xfr->sincetsig > 100 || xfr->nmsg == 0 ||
   1403 		    xfr->state == XFRST_AXFR_END ||
   1404 		    xfr->state == XFRST_IXFR_END)
   1405 		{
   1406 			result = DNS_R_EXPECTEDTSIG;
   1407 			goto failure;
   1408 		}
   1409 	}
   1410 
   1411 	/*
   1412 	 * Update the number of messages received.
   1413 	 */
   1414 	xfr->nmsg++;
   1415 
   1416 	/*
   1417 	 * Update the number of bytes received.
   1418 	 */
   1419 	xfr->nbytes += tcpmsg->buffer.used;
   1420 
   1421 	/*
   1422 	 * Take the context back.
   1423 	 */
   1424 	INSIST(xfr->tsigctx == NULL);
   1425 	xfr->tsigctx = msg->tsigctx;
   1426 	msg->tsigctx = NULL;
   1427 
   1428 	dns_message_destroy(&msg);
   1429 
   1430 	switch (xfr->state) {
   1431 	case XFRST_GOTSOA:
   1432 		xfr->reqtype = dns_rdatatype_axfr;
   1433 		xfr->state = XFRST_INITIALSOA;
   1434 		CHECK(xfrin_send_request(xfr));
   1435 		break;
   1436 	case XFRST_AXFR_END:
   1437 		CHECK(axfr_finalize(xfr));
   1438 	/* FALLTHROUGH */
   1439 	case XFRST_IXFR_END:
   1440 		/*
   1441 		 * Close the journal.
   1442 		 */
   1443 		if (xfr->ixfr.journal != NULL) {
   1444 			dns_journal_destroy(&xfr->ixfr.journal);
   1445 		}
   1446 
   1447 		/*
   1448 		 * Inform the caller we succeeded.
   1449 		 */
   1450 		if (xfr->done != NULL) {
   1451 			(xfr->done)(xfr->zone, ISC_R_SUCCESS);
   1452 			xfr->done = NULL;
   1453 		}
   1454 		/*
   1455 		 * We should have no outstanding events at this
   1456 		 * point, thus maybe_free() should succeed.
   1457 		 */
   1458 		xfr->shuttingdown = true;
   1459 		xfr->shutdown_result = ISC_R_SUCCESS;
   1460 		maybe_free(xfr);
   1461 		break;
   1462 	default:
   1463 		/*
   1464 		 * Read the next message.
   1465 		 */
   1466 		CHECK(dns_tcpmsg_readmessage(&xfr->tcpmsg, xfr->task,
   1467 					     xfrin_recv_done, xfr));
   1468 		xfr->recvs++;
   1469 	}
   1470 	return;
   1471 
   1472 failure:
   1473 	if (msg != NULL) {
   1474 		dns_message_destroy(&msg);
   1475 	}
   1476 	if (result != ISC_R_SUCCESS) {
   1477 		xfrin_fail(xfr, result, "failed while receiving responses");
   1478 	}
   1479 }
   1480 
   1481 static void
   1482 xfrin_timeout(isc_task_t *task, isc_event_t *event) {
   1483 	dns_xfrin_ctx_t *xfr = (dns_xfrin_ctx_t *)event->ev_arg;
   1484 
   1485 	REQUIRE(VALID_XFRIN(xfr));
   1486 
   1487 	UNUSED(task);
   1488 
   1489 	isc_event_free(&event);
   1490 	/*
   1491 	 * This will log "giving up: timeout".
   1492 	 */
   1493 	xfrin_fail(xfr, ISC_R_TIMEDOUT, "giving up");
   1494 }
   1495 
   1496 static void
   1497 maybe_free(dns_xfrin_ctx_t *xfr) {
   1498 	uint64_t msecs;
   1499 	uint64_t persec;
   1500 	const char *result_str;
   1501 
   1502 	REQUIRE(VALID_XFRIN(xfr));
   1503 
   1504 	if (!xfr->shuttingdown || xfr->refcount != 0 || xfr->connects != 0 ||
   1505 	    xfr->sends != 0 || xfr->recvs != 0)
   1506 	{
   1507 		return;
   1508 	}
   1509 
   1510 	INSIST(!xfr->shuttingdown || xfr->shutdown_result != ISC_R_UNSET);
   1511 
   1512 	/* If we're called through dns_xfrin_detach() and are not
   1513 	 * shutting down, we can't know what the transfer status is as
   1514 	 * we are only called when the last reference is lost.
   1515 	 */
   1516 	result_str = (xfr->shuttingdown
   1517 			      ? isc_result_totext(xfr->shutdown_result)
   1518 			      : "unknown");
   1519 	xfrin_log(xfr, ISC_LOG_INFO, "Transfer status: %s", result_str);
   1520 
   1521 	/*
   1522 	 * Calculate the length of time the transfer took,
   1523 	 * and print a log message with the bytes and rate.
   1524 	 */
   1525 	isc_time_now(&xfr->end);
   1526 	msecs = isc_time_microdiff(&xfr->end, &xfr->start) / 1000;
   1527 	if (msecs == 0) {
   1528 		msecs = 1;
   1529 	}
   1530 	persec = (xfr->nbytes * 1000) / msecs;
   1531 	xfrin_log(xfr, ISC_LOG_INFO,
   1532 		  "Transfer completed: %d messages, %d records, "
   1533 		  "%" PRIu64 " bytes, "
   1534 		  "%u.%03u secs (%u bytes/sec)",
   1535 		  xfr->nmsg, xfr->nrecs, xfr->nbytes,
   1536 		  (unsigned int)(msecs / 1000), (unsigned int)(msecs % 1000),
   1537 		  (unsigned int)persec);
   1538 
   1539 	if (xfr->socket != NULL) {
   1540 		isc_socket_detach(&xfr->socket);
   1541 	}
   1542 
   1543 	if (xfr->timer != NULL) {
   1544 		isc_timer_detach(&xfr->timer);
   1545 	}
   1546 
   1547 	if (xfr->task != NULL) {
   1548 		isc_task_detach(&xfr->task);
   1549 	}
   1550 
   1551 	if (xfr->tsigkey != NULL) {
   1552 		dns_tsigkey_detach(&xfr->tsigkey);
   1553 	}
   1554 
   1555 	if (xfr->lasttsig != NULL) {
   1556 		isc_buffer_free(&xfr->lasttsig);
   1557 	}
   1558 
   1559 	dns_diff_clear(&xfr->diff);
   1560 
   1561 	if (xfr->ixfr.journal != NULL) {
   1562 		dns_journal_destroy(&xfr->ixfr.journal);
   1563 	}
   1564 
   1565 	if (xfr->axfr.add_private != NULL) {
   1566 		(void)dns_db_endload(xfr->db, &xfr->axfr);
   1567 	}
   1568 
   1569 	if (xfr->tcpmsg_valid) {
   1570 		dns_tcpmsg_invalidate(&xfr->tcpmsg);
   1571 	}
   1572 
   1573 	if (xfr->tsigctx != NULL) {
   1574 		dst_context_destroy(&xfr->tsigctx);
   1575 	}
   1576 
   1577 	if ((xfr->name.attributes & DNS_NAMEATTR_DYNAMIC) != 0) {
   1578 		dns_name_free(&xfr->name, xfr->mctx);
   1579 	}
   1580 
   1581 	if (xfr->ver != NULL) {
   1582 		dns_db_closeversion(xfr->db, &xfr->ver, false);
   1583 	}
   1584 
   1585 	if (xfr->db != NULL) {
   1586 		dns_db_detach(&xfr->db);
   1587 	}
   1588 
   1589 	if (xfr->zone != NULL) {
   1590 		if (!xfr->zone_had_db && xfr->shuttingdown &&
   1591 		    xfr->shutdown_result == ISC_R_SUCCESS &&
   1592 		    dns_zone_gettype(xfr->zone) == dns_zone_mirror)
   1593 		{
   1594 			dns_zone_log(xfr->zone, ISC_LOG_INFO,
   1595 				     "mirror zone is now in use");
   1596 		}
   1597 		xfrin_log(xfr, ISC_LOG_DEBUG(99), "freeing transfer context");
   1598 		/*
   1599 		 * xfr->zone must not be detached before xfrin_log() is called.
   1600 		 */
   1601 		dns_zone_idetach(&xfr->zone);
   1602 	}
   1603 
   1604 	isc_mem_putanddetach(&xfr->mctx, xfr, sizeof(*xfr));
   1605 }
   1606 
   1607 /*
   1608  * Log incoming zone transfer messages in a format like
   1609  * transfer of <zone> from <address>: <message>
   1610  */
   1611 static void
   1612 xfrin_logv(int level, const char *zonetext, const isc_sockaddr_t *masteraddr,
   1613 	   const char *fmt, va_list ap) {
   1614 	char mastertext[ISC_SOCKADDR_FORMATSIZE];
   1615 	char msgtext[2048];
   1616 
   1617 	isc_sockaddr_format(masteraddr, mastertext, sizeof(mastertext));
   1618 	vsnprintf(msgtext, sizeof(msgtext), fmt, ap);
   1619 
   1620 	isc_log_write(dns_lctx, DNS_LOGCATEGORY_XFER_IN, DNS_LOGMODULE_XFER_IN,
   1621 		      level, "transfer of '%s' from %s: %s", zonetext,
   1622 		      mastertext, msgtext);
   1623 }
   1624 
   1625 /*
   1626  * Logging function for use when a xfrin_ctx_t has not yet been created.
   1627  */
   1628 
   1629 static void
   1630 xfrin_log1(int level, const char *zonetext, const isc_sockaddr_t *masteraddr,
   1631 	   const char *fmt, ...) {
   1632 	va_list ap;
   1633 
   1634 	if (!isc_log_wouldlog(dns_lctx, level)) {
   1635 		return;
   1636 	}
   1637 
   1638 	va_start(ap, fmt);
   1639 	xfrin_logv(level, zonetext, masteraddr, fmt, ap);
   1640 	va_end(ap);
   1641 }
   1642 
   1643 /*
   1644  * Logging function for use when there is a xfrin_ctx_t.
   1645  */
   1646 
   1647 static void
   1648 xfrin_log(dns_xfrin_ctx_t *xfr, int level, const char *fmt, ...) {
   1649 	va_list ap;
   1650 	char zonetext[DNS_NAME_MAXTEXT + 32];
   1651 
   1652 	if (!isc_log_wouldlog(dns_lctx, level)) {
   1653 		return;
   1654 	}
   1655 
   1656 	dns_zone_name(xfr->zone, zonetext, sizeof(zonetext));
   1657 
   1658 	va_start(ap, fmt);
   1659 	xfrin_logv(level, zonetext, &xfr->masteraddr, fmt, ap);
   1660 	va_end(ap);
   1661 }
   1662