static inline void freestruct_cert(ARGS_FREESTRUCT) { dns_rdata_cert_t *cert = source; REQUIRE(cert != NULL); REQUIRE(cert->common.rdtype == dns_rdatatype_cert); if (cert->mctx == NULL) return; if (cert->certificate != NULL) isc_mem_free(cert->mctx, cert->certificate); cert->mctx = NULL; }
static inline void freestruct_txt(ARGS_FREESTRUCT) { dns_rdata_txt_t *txt = source; REQUIRE(source != NULL); REQUIRE(txt->common.rdtype == 16); if (txt->mctx == NULL) return; if (txt->txt != NULL) isc_mem_free(txt->mctx, txt->txt); txt->mctx = NULL; }
static inline void freestruct_sshfp(ARGS_FREESTRUCT) { dns_rdata_sshfp_t *sshfp = source; REQUIRE(sshfp != NULL); REQUIRE(sshfp->common.rdtype == 44); if (sshfp->mctx == NULL) return; if (sshfp->digest != NULL) isc_mem_free(sshfp->mctx, sshfp->digest); sshfp->mctx = NULL; }
static inline void freestruct_key(ARGS_FREESTRUCT) { dns_rdata_key_t *key = (dns_rdata_key_t *) source; REQUIRE(source != NULL); REQUIRE(key->common.rdtype == dns_rdatatype_key); if (key->mctx == NULL) return; if (key->data != NULL) isc_mem_free(key->mctx, key->data); key->mctx = NULL; }
static inline void freestruct_openpgpkey(ARGS_FREESTRUCT) { dns_rdata_openpgpkey_t *sig = (dns_rdata_openpgpkey_t *) source; REQUIRE(source != NULL); REQUIRE(sig->common.rdtype == dns_rdatatype_openpgpkey); if (sig->mctx == NULL) return; if (sig->keyring != NULL) isc_mem_free(sig->mctx, sig->keyring); sig->mctx = NULL; }
static inline void freestruct_unspec(ARGS_FREESTRUCT) { dns_rdata_unspec_t *unspec = source; REQUIRE(source != NULL); REQUIRE(unspec->common.rdtype == 103); if (unspec->mctx == NULL) return; if (unspec->data != NULL) isc_mem_free(unspec->mctx, unspec->data); unspec->mctx = NULL; }
static inline void freestruct_dlv(ARGS_FREESTRUCT) { dns_rdata_dlv_t *dlv = source; REQUIRE(dlv != NULL); REQUIRE(dlv->common.rdtype == 32769); if (dlv->mctx == NULL) return; if (dlv->digest != NULL) isc_mem_free(dlv->mctx, dlv->digest); dlv->mctx = NULL; }
static inline void freestruct_tlsa(ARGS_FREESTRUCT) { dns_rdata_tlsa_t *tlsa = source; REQUIRE(tlsa != NULL); REQUIRE(tlsa->common.rdtype == dns_rdatatype_tlsa); if (tlsa->mctx == NULL) return; if (tlsa->data != NULL) isc_mem_free(tlsa->mctx, tlsa->data); tlsa->mctx = NULL; }
static inline void freestruct_opt(ARGS_FREESTRUCT) { dns_rdata_opt_t *opt = source; REQUIRE(source != NULL); REQUIRE(opt->common.rdtype == 41); if (opt->mctx == NULL) return; if (opt->options != NULL) isc_mem_free(opt->mctx, opt->options); opt->mctx = NULL; }
static inline void freestruct_in_apl(ARGS_FREESTRUCT) { dns_rdata_in_apl_t *apl = source; REQUIRE(source != NULL); REQUIRE(apl->common.rdtype == 42); REQUIRE(apl->common.rdclass == 1); if (apl->mctx == NULL) return; if (apl->apl != NULL) isc_mem_free(apl->mctx, apl->apl); apl->mctx = NULL; }
static inline void freestruct_cdnskey(ARGS_FREESTRUCT) { dns_rdata_cdnskey_t *dnskey = (dns_rdata_cdnskey_t *) source; REQUIRE(source != NULL); REQUIRE(dnskey->common.rdtype == 60); if (dnskey->mctx == NULL) return; if (dnskey->data != NULL) isc_mem_free(dnskey->mctx, dnskey->data); dnskey->mctx = NULL; }
static inline void freestruct_nsec3param(ARGS_FREESTRUCT) { dns_rdata_nsec3param_t *nsec3param = source; REQUIRE(source != NULL); REQUIRE(nsec3param->common.rdtype == 51); if (nsec3param->mctx == NULL) return; if (nsec3param->salt != NULL) isc_mem_free(nsec3param->mctx, nsec3param->salt); nsec3param->mctx = NULL; }
static void stub_dlz_destroy(void *driverarg, void *dbdata) { config_data_t *cd; isc_mem_t *mctx; UNUSED(driverarg); cd = (config_data_t *) dbdata; /* * Write debugging message to log */ isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_DEBUG(2), "Unloading DLZ_stub driver."); isc_mem_free(ns_g_mctx, cd->myzone); isc_mem_free(ns_g_mctx, cd->myname); isc_mem_free(ns_g_mctx, cd->myip); mctx = cd->mctx; isc_mem_put(mctx, cd, sizeof(config_data_t)); isc_mem_detach(&mctx); }
static inline void freestruct_sig(ARGS_FREESTRUCT) { dns_rdata_sig_t *sig = (dns_rdata_sig_t *) source; REQUIRE(source != NULL); REQUIRE(sig->common.rdtype == dns_rdatatype_sig); if (sig->mctx == NULL) return; dns_name_free(&sig->signer, sig->mctx); if (sig->signature != NULL) isc_mem_free(sig->mctx, sig->signature); sig->mctx = NULL; }
static void manager_free(isc_taskmgr_t *manager) { isc_mem_t *mctx; #ifdef ISC_PLATFORM_USETHREADS (void)isc_condition_destroy(&manager->exclusive_granted); (void)isc_condition_destroy(&manager->work_available); isc_mem_free(manager->mctx, manager->threads); #endif /* ISC_PLATFORM_USETHREADS */ DESTROYLOCK(&manager->lock); manager->magic = 0; mctx = manager->mctx; isc_mem_put(mctx, manager, sizeof(*manager)); isc_mem_detach(&mctx); }
static inline void freestruct_in_dhcid (ARGS_FREESTRUCT) { dns_rdata_in_dhcid_t *dhcid = source; REQUIRE (dhcid != NULL); REQUIRE (dhcid->common.rdtype == 49); REQUIRE (dhcid->common.rdclass == 1); if (dhcid->mctx == NULL) return; if (dhcid->dhcid != NULL) isc_mem_free (dhcid->mctx, dhcid->dhcid); dhcid->mctx = NULL; }
static inline void freestruct_in_nsap(ARGS_FREESTRUCT) { dns_rdata_in_nsap_t *nsap = source; REQUIRE(source != NULL); REQUIRE(nsap->common.rdclass == 1); REQUIRE(nsap->common.rdtype == 22); if (nsap->mctx == NULL) return; if (nsap->nsap != NULL) isc_mem_free(nsap->mctx, nsap->nsap); nsap->mctx = NULL; }
static inline void freestruct_ipseckey(ARGS_FREESTRUCT) { dns_rdata_ipseckey_t *ipseckey = source; REQUIRE(source != NULL); REQUIRE(ipseckey->common.rdtype == 45); if (ipseckey->mctx == NULL) return; if (ipseckey->gateway_type == 3) dns_name_free(&ipseckey->gateway, ipseckey->mctx); if (ipseckey->key != NULL) isc_mem_free(ipseckey->mctx, ipseckey->key); ipseckey->mctx = NULL; }
isc_result_t isc_file_splitpath (isc_mem_t * mctx, char *path, char **dirname, char **basename) { char *dir, *file, *slash; char *backslash; slash = strrchr (path, '/'); backslash = strrchr (path, '\\'); if ((slash != NULL && backslash != NULL && backslash > slash) || (slash == NULL && backslash != NULL)) slash = backslash; if (slash == path) { file = ++slash; dir = isc_mem_strdup (mctx, "/"); } else if (slash != NULL) { file = ++slash; dir = isc_mem_allocate (mctx, slash - path); if (dir != NULL) strlcpy (dir, path, slash - path); } else { file = path; dir = isc_mem_strdup (mctx, "."); } if (dir == NULL) return (ISC_R_NOMEMORY); if (*file == '\0') { isc_mem_free (mctx, dir); return (ISC_R_INVALIDFILE); } *dirname = dir; *basename = file; return (ISC_R_SUCCESS); }
static void reset_probe (struct probe_trans *trans) { struct probe_ns *pns; struct server *server; isc_result_t result; REQUIRE (trans->resid == NULL); REQUIRE (trans->reqid == NULL); update_stat (trans); dns_message_reset (trans->qmessage, DNS_MESSAGE_INTENTRENDER); dns_message_reset (trans->rmessage, DNS_MESSAGE_INTENTPARSE); trans->inuse = ISC_FALSE; if (trans->domain != NULL) isc_mem_free (mctx, trans->domain); trans->domain = NULL; if (trans->qname != NULL) dns_fixedname_invalidate (&trans->fixedname); trans->qname = NULL; trans->qlabel = qlabels; trans->qname_found = ISC_FALSE; trans->current_ns = NULL; while ((pns = ISC_LIST_HEAD (trans->nslist)) != NULL) { ISC_LIST_UNLINK (trans->nslist, pns, link); while ((server = ISC_LIST_HEAD (pns->servers)) != NULL) { ISC_LIST_UNLINK (pns->servers, server, link); isc_mem_put (mctx, server, sizeof (*server)); } isc_mem_put (mctx, pns, sizeof (*pns)); } outstanding_probes--; result = probe_domain (trans); if (result == ISC_R_NOMORE && outstanding_probes == 0) isc_app_ctxshutdown (actx); }
static isc_boolean_t compare_labelsequences(dns_rbtnode_t *node, const char *labelstr) { dns_name_t name; isc_result_t result; char *nodestr = NULL; isc_boolean_t is_equal; dns_name_init(&name, NULL); dns_rbt_namefromnode(node, &name); result = dns_name_tostring(&name, &nodestr, mctx); ATF_REQUIRE_EQ(result, ISC_R_SUCCESS); is_equal = strcmp(labelstr, nodestr) == 0 ? ISC_TRUE : ISC_FALSE; isc_mem_free(mctx, nodestr); return (is_equal); }
static isc_result_t odbc_getField(SQLHSTMT *stmnt, SQLSMALLINT field, char **data) { SQLLEN size; REQUIRE(data != NULL && *data == NULL); if (sqlOK(SQLColAttribute(stmnt, field, SQL_DESC_DISPLAY_SIZE, NULL, 0, NULL, &size)) && size > 0) { *data = isc_mem_allocate(ns_g_mctx, size + 1); if (data != NULL) { if (sqlOK(SQLGetData(stmnt, field, SQL_C_CHAR, *data, size + 1,&size))) return ISC_R_SUCCESS; isc_mem_free(ns_g_mctx, *data); } } return ISC_R_FAILURE; }
static inline isc_result_t tostruct_isdn(ARGS_TOSTRUCT) { dns_rdata_isdn_t *isdn = target; isc_region_t r; REQUIRE(rdata->type == dns_rdatatype_isdn); REQUIRE(target != NULL); REQUIRE(rdata->length != 0); isdn->common.rdclass = rdata->rdclass; isdn->common.rdtype = rdata->type; ISC_LINK_INIT(&isdn->common, link); dns_rdata_toregion(rdata, &r); isdn->isdn_len = uint8_fromregion(&r); isc_region_consume(&r, 1); isdn->isdn = mem_maybedup(mctx, r.base, isdn->isdn_len); if (isdn->isdn == NULL) return (ISC_R_NOMEMORY); isc_region_consume(&r, isdn->isdn_len); if (r.length == 0) { isdn->subaddress_len = 0; isdn->subaddress = NULL; } else { isdn->subaddress_len = uint8_fromregion(&r); isc_region_consume(&r, 1); isdn->subaddress = mem_maybedup(mctx, r.base, isdn->subaddress_len); if (isdn->subaddress == NULL) goto cleanup; } isdn->mctx = mctx; return (ISC_R_SUCCESS); cleanup: if (mctx != NULL && isdn->isdn != NULL) isc_mem_free(mctx, isdn->isdn); return (ISC_R_NOMEMORY); }
static void manager_free(isc__taskmgr_t *manager) { isc_mem_t *mctx; #ifdef USE_WORKER_THREADS (void)isc_condition_destroy(&manager->exclusive_granted); (void)isc_condition_destroy(&manager->work_available); isc_mem_free(manager->mctx, manager->threads); #endif /* USE_WORKER_THREADS */ DESTROYLOCK(&manager->lock); manager->common.impmagic = 0; manager->common.magic = 0; mctx = manager->mctx; isc_mem_put(mctx, manager, sizeof(*manager)); isc_mem_detach(&mctx); #ifdef USE_SHARED_MANAGER taskmgr = NULL; #endif /* USE_SHARED_MANAGER */ }
static void destroy(dns_acl_t *dacl) { unsigned int i; for (i = 0; i < dacl->length; i++) { dns_aclelement_t *de = &dacl->elements[i]; if (de->type == dns_aclelementtype_keyname) { dns_name_free(&de->keyname, dacl->mctx); } else if (de->type == dns_aclelementtype_nestedacl) { dns_acl_detach(&de->nestedacl); } } if (dacl->elements != NULL) isc_mem_put(dacl->mctx, dacl->elements, dacl->alloc * sizeof(dns_aclelement_t)); if (dacl->name != NULL) isc_mem_free(dacl->mctx, dacl->name); if (dacl->iptable != NULL) dns_iptable_detach(&dacl->iptable); isc_refcount_destroy(&dacl->refcount); dacl->magic = 0; isc_mem_put(dacl->mctx, dacl, sizeof(*dacl)); }
static isc_result_t controlkeylist_fromcfg(const cfg_obj_t *keylist, isc_mem_t *mctx, controlkeylist_t *keyids) { const cfg_listelt_t *element; char *newstr = NULL; const char *str; const cfg_obj_t *obj; controlkey_t *key; for (element = cfg_list_first(keylist); element != NULL; element = cfg_list_next(element)) { obj = cfg_listelt_value(element); str = cfg_obj_asstring(obj); newstr = isc_mem_strdup(mctx, str); if (newstr == NULL) goto cleanup; key = isc_mem_get(mctx, sizeof(*key)); if (key == NULL) goto cleanup; key->keyname = newstr; key->algorithm = DST_ALG_UNKNOWN; key->secret.base = NULL; key->secret.length = 0; ISC_LINK_INIT(key, link); ISC_LIST_APPEND(*keyids, key, link); newstr = NULL; } return (ISC_R_SUCCESS); cleanup: if (newstr != NULL) isc_mem_free(mctx, newstr); free_controlkeylist(keyids, mctx); return (ISC_R_NOMEMORY); }
/** * Un-set value in given set of settings (non-recursively, parent sets are * not affected in any way). Function will fail if setting with given name is * not a part of set of settings. * Mutual exclusion is ensured by isc_task_beginexclusive(). * * @warning * Failure in this function usually points to logic error. * Caller should always check return value. * * @retval ISC_R_SUCCESS Setting was un-set. * @retval ISC_R_IGNORE Setting wasn't changed because wasn't set. * @retval ISC_R_NOTFOUND Required setting was not found * in given set of settings. */ isc_result_t setting_unset(const char *const name, const settings_set_t *set) { isc_result_t result; setting_t *setting = NULL; CHECK(setting_find(name, set, ISC_FALSE, ISC_FALSE, &setting)); if (!setting->filled) return ISC_R_IGNORE; LOCK(set->lock); switch (setting->type) { case ST_STRING: if (setting->is_dynamic) isc_mem_free(set->mctx, setting->value.value_char); setting->is_dynamic = ISC_FALSE; break; case ST_UNSIGNED_INTEGER: case ST_BOOLEAN: break; default: UNEXPECTED_ERROR(__FILE__, __LINE__, "invalid setting_type_t value %u", setting->type); break; } setting->filled = 0; cleanup: UNLOCK(set->lock); if (result == ISC_R_NOTFOUND) log_bug("setting '%s' was not found in set of settings '%s'", name, set->name); return result; }
/* * Close the connection to the database. */ static void pgsqldb_destroy(const char *zone, void *driverdata, void **dbdata) { struct dbinfo *dbi = *dbdata; UNUSED(zone); UNUSED(driverdata); if (dbi->conn != NULL) PQfinish(dbi->conn); if (dbi->database != NULL) isc_mem_free(ns_g_mctx, dbi->database); if (dbi->table != NULL) isc_mem_free(ns_g_mctx, dbi->table); if (dbi->host != NULL) isc_mem_free(ns_g_mctx, dbi->host); if (dbi->user != NULL) isc_mem_free(ns_g_mctx, dbi->user); if (dbi->passwd != NULL) isc_mem_free(ns_g_mctx, dbi->passwd); if (dbi->database != NULL) isc_mem_free(ns_g_mctx, dbi->database); isc_mem_put(ns_g_mctx, dbi, sizeof(struct dbinfo)); }
/* * Called at startup for each dlopen zone in named.conf */ static isc_result_t dlopen_dlz_create(const char *dlzname, unsigned int argc, char *argv[], void *driverarg, void **dbdata) { dlopen_data_t *cd; isc_mem_t *mctx = NULL; isc_result_t result = ISC_R_FAILURE; int dlopen_flags = 0; UNUSED(driverarg); if (argc < 2) { dlopen_log(ISC_LOG_ERROR, "dlz_dlopen driver for '%s' needs a path to " "the shared library", dlzname); return (ISC_R_FAILURE); } result = isc_mem_create(0, 0, &mctx); if (result != ISC_R_SUCCESS) return (result); cd = isc_mem_get(mctx, sizeof(*cd)); if (cd == NULL) { isc_mem_destroy(&mctx); return (ISC_R_NOMEMORY); } memset(cd, 0, sizeof(*cd)); cd->mctx = mctx; cd->dl_path = isc_mem_strdup(cd->mctx, argv[1]); if (cd->dl_path == NULL) { result = ISC_R_NOMEMORY; goto failed; } cd->dlzname = isc_mem_strdup(cd->mctx, dlzname); if (cd->dlzname == NULL) { result = ISC_R_NOMEMORY; goto failed; } /* Initialize the lock */ result = isc_mutex_init(&cd->lock); if (result != ISC_R_SUCCESS) goto failed; /* Open the library */ dlopen_flags = RTLD_NOW|RTLD_GLOBAL; #ifdef RTLD_DEEPBIND /* * If RTLD_DEEPBIND is available then use it. This can avoid * issues with a module using a different version of a system * library than one that bind9 uses. For example, bind9 may link * to MIT kerberos, but the module may use Heimdal. If we don't * use RTLD_DEEPBIND then we could end up with Heimdal functions * calling MIT functions, which leads to bizarre results (usually * a segfault). */ dlopen_flags |= RTLD_DEEPBIND; #endif cd->dl_handle = dlopen(cd->dl_path, dlopen_flags); if (cd->dl_handle == NULL) { dlopen_log(ISC_LOG_ERROR, "dlz_dlopen failed to open library '%s' - %s", cd->dl_path, dlerror()); result = ISC_R_FAILURE; goto failed; } /* Find the symbols */ cd->dlz_version = (dlz_dlopen_version_t *) dl_load_symbol(cd, "dlz_version", ISC_TRUE); cd->dlz_create = (dlz_dlopen_create_t *) dl_load_symbol(cd, "dlz_create", ISC_TRUE); cd->dlz_lookup = (dlz_dlopen_lookup_t *) dl_load_symbol(cd, "dlz_lookup", ISC_TRUE); cd->dlz_findzonedb = (dlz_dlopen_findzonedb_t *) dl_load_symbol(cd, "dlz_findzonedb", ISC_TRUE); if (cd->dlz_create == NULL || cd->dlz_version == NULL || cd->dlz_lookup == NULL || cd->dlz_findzonedb == NULL) { /* We're missing a required symbol */ result = ISC_R_FAILURE; goto failed; } cd->dlz_allowzonexfr = (dlz_dlopen_allowzonexfr_t *) dl_load_symbol(cd, "dlz_allowzonexfr", ISC_FALSE); cd->dlz_allnodes = (dlz_dlopen_allnodes_t *) dl_load_symbol(cd, "dlz_allnodes", ISC_TF(cd->dlz_allowzonexfr != NULL)); cd->dlz_authority = (dlz_dlopen_authority_t *) dl_load_symbol(cd, "dlz_authority", ISC_FALSE); cd->dlz_newversion = (dlz_dlopen_newversion_t *) dl_load_symbol(cd, "dlz_newversion", ISC_FALSE); cd->dlz_closeversion = (dlz_dlopen_closeversion_t *) dl_load_symbol(cd, "dlz_closeversion", ISC_TF(cd->dlz_newversion != NULL)); cd->dlz_configure = (dlz_dlopen_configure_t *) dl_load_symbol(cd, "dlz_configure", ISC_FALSE); cd->dlz_ssumatch = (dlz_dlopen_ssumatch_t *) dl_load_symbol(cd, "dlz_ssumatch", ISC_FALSE); cd->dlz_addrdataset = (dlz_dlopen_addrdataset_t *) dl_load_symbol(cd, "dlz_addrdataset", ISC_FALSE); cd->dlz_subrdataset = (dlz_dlopen_subrdataset_t *) dl_load_symbol(cd, "dlz_subrdataset", ISC_FALSE); cd->dlz_delrdataset = (dlz_dlopen_delrdataset_t *) dl_load_symbol(cd, "dlz_delrdataset", ISC_FALSE); cd->dlz_destroy = (dlz_dlopen_destroy_t *) dl_load_symbol(cd, "dlz_destroy", ISC_FALSE); /* Check the version of the API is the same */ cd->version = cd->dlz_version(&cd->flags); if (cd->version < (DLZ_DLOPEN_VERSION - DLZ_DLOPEN_AGE) || cd->version > DLZ_DLOPEN_VERSION) { dlopen_log(ISC_LOG_ERROR, "dlz_dlopen: %s: incorrect driver API version %d, " "requires %d", cd->dl_path, cd->version, DLZ_DLOPEN_VERSION); result = ISC_R_FAILURE; goto failed; } /* * Call the library's create function. Note that this is an * extended version of dlz create, with the addition of * named function pointers for helper functions that the * driver will need. This avoids the need for the backend to * link the BIND9 libraries */ MAYBE_LOCK(cd); result = cd->dlz_create(dlzname, argc-1, argv+1, &cd->dbdata, "log", dlopen_log, "putrr", dns_sdlz_putrr, "putnamedrr", dns_sdlz_putnamedrr, "writeable_zone", dns_dlz_writeablezone, NULL); MAYBE_UNLOCK(cd); if (result != ISC_R_SUCCESS) goto failed; *dbdata = cd; return (ISC_R_SUCCESS); failed: dlopen_log(ISC_LOG_ERROR, "dlz_dlopen of '%s' failed", dlzname); if (cd->dl_path != NULL) isc_mem_free(mctx, cd->dl_path); if (cd->dlzname != NULL) isc_mem_free(mctx, cd->dlzname); if (dlopen_flags != 0) (void) isc_mutex_destroy(&cd->lock); #ifdef HAVE_DLCLOSE if (cd->dl_handle) dlclose(cd->dl_handle); #endif isc_mem_put(mctx, cd, sizeof(*cd)); isc_mem_destroy(&mctx); return (result); }
/*% * If the client is allowed to perform a zone transfer, the next order of * business is to get all the nodes in the zone, so bind can respond to the * query. */ static isc_result_t postgres_allnodes(const char *zone, void *driverarg, void *dbdata, dns_sdlzallnodes_t *allnodes) { isc_result_t result; PGresult *rs = NULL; unsigned int i; unsigned int rows; unsigned int fields; unsigned int j; unsigned int len; char *tmpString; char *endp; int ttl; UNUSED(driverarg); /* run the query and get the result set from the database. */ result = postgres_get_resultset(zone, NULL, NULL, ALLNODES, dbdata, &rs); /* if we get "not implemented", send it along */ if (result == ISC_R_NOTIMPLEMENTED) return result; /* if we didn't get a result set, log an err msg. */ if (result != ISC_R_SUCCESS) { if (rs != NULL) PQclear(rs); isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_ERROR, "Postgres driver unable to return " "result set for all nodes query"); return (ISC_R_FAILURE); } rows = PQntuples(rs); /* how many rows in result set */ fields = PQnfields(rs); /* how many columns in result set */ for (i=0; i < rows; i++) { if (fields < 4) { /* gotta have at least 4 columns */ isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_ERROR, "Postgres driver too few fields " "returned by all nodes query"); } /* convert text to int, make sure it worked right */ ttl = strtol(PQgetvalue(rs, i, 0), &endp, 10); if (*endp != '\0' || ttl < 0) { isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_ERROR, "Postgres driver ttl must be " "a postive number"); } if (fields == 4) { /* tell Bind about it. */ result = dns_sdlz_putnamedrr(allnodes, PQgetvalue(rs, i, 2), PQgetvalue(rs, i, 1), ttl, PQgetvalue(rs, i, 3)); } else { /* * more than 4 fields, concatonat the last * ones together. figure out how long to make * string */ for (j=3, len=0; j < fields; j++) { len += strlen(PQgetvalue(rs, i, j)) + 1; } /* allocate memory, allow for NULL to term string */ tmpString = isc_mem_allocate(ns_g_mctx, len + 1); if (tmpString == NULL) { /* we need more ram. */ isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_ERROR, "Postgres driver unable to " "allocate memory for " "temporary string"); PQclear(rs); return (ISC_R_FAILURE); } /* copy this field to tmpString */ strcpy(tmpString, PQgetvalue(rs, i, 3)); /* concatonate the rest, with spaces between */ for (j=4; j < fields; j++) { strcat(tmpString, " "); strcat(tmpString, PQgetvalue(rs, i, j)); } /* tell Bind about it. */ result = dns_sdlz_putnamedrr(allnodes, PQgetvalue(rs, i, 2), PQgetvalue(rs, i, 1), ttl, tmpString); isc_mem_free(ns_g_mctx, tmpString); } /* if we weren't successful, log err msg */ if (result != ISC_R_SUCCESS) { PQclear(rs); isc_log_write(dns_lctx, DNS_LOGCATEGORY_DATABASE, DNS_LOGMODULE_DLZ, ISC_LOG_ERROR, "dns_sdlz_putnamedrr returned error. " "Error code was: %s", isc_result_totext(result)); return (ISC_R_FAILURE); } } /* free result set memory */ PQclear(rs); /* if we did return results, we are successful */ if (rows > 0) return (ISC_R_SUCCESS); /* empty result set, no data found */ return (ISC_R_NOTFOUND); }