/** @brief Parse the resource record in its components * * For not found values, default values will be used. * Default values are "origin" and "label". "Origin" always exists, but if * "label" does not exist, "origin" will be the "label" * * @param[in] rr_line * @param[in,out] label * @param[in,out] origin * @param[in] default_ttl * @param[in] default qclass * @param[out] rr * * @retval OK * @retval NOK */ ya_result rr_parse_line(char *src, const u8 *origin, u8 *label, u32 *ttl, resource_record *rr, int *bracket_status) { ya_result return_code = OK; char *needle = NULL; /* ------------------------------------------------------------ */ if(*bracket_status == BRACKET_CLOSED) { bool no_ttl = TRUE; if(FAIL(return_code = rr_check_qname(&src, rr->name, origin, label))) { return return_code; } while(*src) { if(rr->type != 0 ) { break; } needle = src; /* Search for word and cut */ CUT_WORD(needle); if(FAIL(return_code = parse_u32_check_range(src, &rr->ttl, 0, MAX_U32, /*BASE_*/10))) { if(FAIL(return_code = get_class_from_name(src, &rr->class))) { if(FAIL(return_code = get_type_from_name(src, &rr->type))) { return ZRE_NO_TYPE_FOUND; } } } else { no_ttl = FALSE; } // format("rr_parse_line 1: %s\n", src); src = needle; // format("rr_parse_line 2: %s\n", src); SKIP_WHSPACE(src); // format("rr_parse_line 3: %s\n", src); }
static ya_result config_zone_section_assign(config_data *config) { u32 port = 0; ya_result return_code; config_zone_section_register(config); if(FAIL(return_code = parse_u32_check_range(config->server_port, &port, 1, MAX_U16, 10))) { osformatln(termerr, "config: zone: wrong dns port set in main '%s': %r", config->server_port, return_code); return return_code; } zone_set_lock(&config->zones); treeset_avl_iterator iter; treeset_avl_iterator_init(&config->zones.set, &iter); while(treeset_avl_iterator_hasnext(&iter)) { treeset_node *zone_node = treeset_avl_iterator_next_node(&iter); zone_data *zone = (zone_data *)zone_node->data; zone_setdefaults(zone); if(!config_check_bounds_s32(SIGNATURE_VALIDITY_INTERVAL_MIN, SIGNATURE_VALIDITY_INTERVAL_MAX, zone->sig_validity_interval, "sig-validity-interval")) { return ERROR; } if(!config_check_bounds_s32(SIGNATURE_VALIDITY_REGENERATION_MIN, SIGNATURE_VALIDITY_REGENERATION_MAX, zone->sig_validity_regeneration, "sig-validity-regeneration")) { return ERROR; } if(!config_check_bounds_s32(SIGNATURE_VALIDITY_JITTER_MIN, SIGNATURE_VALIDITY_JITTER_MAX, zone->sig_validity_jitter, "sig-validity-jitter")) { return ERROR; } if(!config_check_bounds_s32(NOTIFY_RETRY_COUNT_MIN, NOTIFY_RETRY_COUNT_MAX, zone->notify.retry_count, "notify-retry-count")) { return ERROR; } if(!config_check_bounds_s32(NOTIFY_RETRY_PERIOD_MIN, NOTIFY_RETRY_PERIOD_MAX, zone->notify.retry_period, "notify-period-count")) { return ERROR; } if(!config_check_bounds_s32(NOTIFY_RETRY_PERIOD_INCREASE_MIN, NOTIFY_RETRY_PERIOD_INCREASE_MAX, zone->notify.retry_period_increase, "notify-period-increase")) { return ERROR; } zone->ctrl_flags |= ZONE_CTRL_FLAG_READ_FROM_CONF; } zone_set_unlock(&config->zones); return SUCCESS; }
static ya_result config_main_section_postprocess(struct config_section_descriptor_s *csd) { u32 port = 0; u32 cpu_per_core = (sys_has_hyperthreading())?2:1; int ret; char tmp[PATH_MAX]; if(FAIL(parse_u32_check_range(g_config->server_port, &port, 1, MAX_U16, 10))) { port = DNS_DEFAULT_PORT; ttylog_err("config: main: wrong dns port set in main '%s', defaulted to %d", g_config->server_port, port); } if(g_config->hostname_chaos == NULL) { #if _BSD_SOURCE || _XOPEN_SOURCE >= 500 || /* Since glibc 2.12: */ _POSIX_C_SOURCE >= 200112L if(gethostname(tmp, sizeof(tmp)) == 0) { g_config->hostname_chaos = strdup(tmp); } else { osformatln(termerr,"config: main: unable to get hostname: %r", ERRNO_ERROR); g_config->hostname_chaos = strdup("not disclosed"); } #else g_config->hostname_chaos = strdup("not disclosed"); #endif } if(g_config->thread_affinity_multiplier == 0) { g_config->thread_affinity_multiplier = cpu_per_core; } class_ch_set_hostname(g_config->hostname_chaos); class_ch_set_id_server(g_config->serverid_chaos); class_ch_set_version(g_config->version_chaos); host_set_default_port_value(g_config->listen, ntohs(port)); if(g_config->server_flags & SERVER_FL_CHROOT) { uid_t euid = geteuid(); if(euid != 0) { ttylog_err("config: main: chroot has been enabled but euid is not root (%i != 0)", (int)euid); return INVALID_STATE_ERROR; } } else // disables the base-path/chroot-path feature { if(strcmp(g_config->chroot_path, "/") != 0) { free(g_config->chroot_path); g_config->chroot_path = strdup("/"); chroot_set_path(g_config->chroot_path); } } message_edns0_setmaxsize(g_config->edns0_max_size); g_config->total_interfaces = host_address_count(g_config->listen); if(g_config->total_interfaces > MAX_INTERFACES) { ttylog_err("error: more than %d listening addresses defined.", MAX_INTERFACES); return CONFIG_TOO_MANY_HOSTS; } #ifndef SO_REUSEPORT if(g_config->network_model == 1) { ttylog_err("error: network-model 1 requires features not available on this system (SO_REUSEPORT)"); return FEATURE_NOT_SUPPORTED; } #endif g_config->axfr_retry_jitter = BOUND(AXFR_RETRY_JITTER_MIN, g_config->axfr_retry_jitter, g_config->axfr_retry_delay); g_config->dnssec_thread_count = BOUND(1, g_config->dnssec_thread_count, sys_get_cpu_count()); if(g_config->cpu_count_override > 0) { sys_set_cpu_count(g_config->cpu_count_override); } if(g_config->thread_count_by_address == 0) { ttylog_err("config: single thread engine has been removed, thread-count-by-address set to 1"); g_config->thread_count_by_address = 1; } if(g_config->thread_count_by_address < 0) { g_config->thread_count_by_address = MAX(sys_get_cpu_count() / cpu_per_core, 1); } else if((g_config->thread_count_by_address > sys_get_cpu_count())) { g_config->thread_count_by_address = MAX(sys_get_cpu_count() / cpu_per_core, 1); ttylog_err("config: bounding down thread-count-by-address to the number of physical CPUs (%d)", g_config->thread_count_by_address); } g_config->tcp_query_min_rate_us = g_config->tcp_query_min_rate * 0.000001; #if HAS_DNSSEC_SUPPORT g_config->dnssec_thread_count = BOUND(1, g_config->dnssec_thread_count, sys_get_cpu_count()); if(!IS_TYPE_PRIVATE(g_config->sig_signing_type)) { ttylog_err("error: signing type is not in the accepted range: %hx", g_config->sig_signing_type); return CONFIG_WRONG_SIG_TYPE; } if(g_config->sig_validity_interval > SIGNATURE_VALIDITY_INTERVAL_MAX) { ttylog_err("error: signature validity interval too high"); return CONFIG_WRONG_SIG_VALIDITY; } if(g_config->sig_validity_regeneration * SIGNATURE_VALIDITY_REGENERATION_S * 2 > g_config->sig_validity_interval * SIGNATURE_VALIDITY_INTERVAL_S) { ttylog_err("error: default signature regeneration is more than half the interval (%ds * 2 > %ds)", g_config->sig_validity_regeneration * SIGNATURE_VALIDITY_REGENERATION_S, g_config->sig_validity_interval * SIGNATURE_VALIDITY_INTERVAL_S); return CONFIG_WRONG_SIG_REGEN; } #endif /// @note config_main_verify_and_update_directory updates the folder with the base_path /** * * @note All base paths are updated with the chroot variable so it does not * need to be added all the time. * */ const char *base_path = g_config->chroot_path; if(FAIL(ret = config_main_verify_and_update_directory(base_path, &g_config->data_path))) { return ret; } if(FAIL(ret = config_main_verify_and_update_directory(base_path, &g_config->keys_path))) { return ret; } if(FAIL(ret = config_main_verify_and_update_directory(base_path, &g_config->log_path))) { return ret; } #if 0 /* fix */ #else if(FAIL(ret = config_main_verify_and_update_file(base_path, &g_config->pid_file))) { return ret; } #endif g_config->reloadable = TRUE; if((g_config->server_flags & SERVER_FL_CHROOT) != 0) { if(FAIL(chroot_manage_path(&g_config->config_file, g_config->config_file, FALSE))) { log_warn("config file '%s' will not be accessible within the chroot jail '%s' : config reload will not work", g_config->config_file, base_path); g_config->reloadable = FALSE; } } if(FAIL(ret = config_main_verify_and_update_directory(base_path, &g_config->xfr_path))) { return ret; } #if ZDB_HAS_DNSSEC_SUPPORT dnssec_keystore_setpath(g_config->keys_path); dnssec_set_xfr_path(g_config->xfr_path); journal_set_xfr_path(g_config->xfr_path); #endif if((logger_get_uid() != g_config->uid) || (logger_get_gid() != g_config->gid)) { logger_set_uid(g_config->uid); logger_set_gid(g_config->gid); logger_reopen(); } return SUCCESS; }