struct GeoIPDNSResourceRecord : DNSResourceRecord
{
- int weight;
- bool has_weight;
+ int weight{};
+ bool has_weight{};
};
struct GeoIPService
{
int id;
DNSName domain;
- int ttl;
+ int ttl{};
map<DNSName, GeoIPService> services;
map<DNSName, vector<GeoIPDNSResourceRecord>> records;
vector<string> mapping_lookup_formats;
GeoIPBackend::GeoIPBackend(const string& suffix)
{
- WriteLock wl(&s_state_lock);
- d_dnssec = false;
+ WriteLock writeLock(&s_state_lock);
setArgPrefix("geoip" + suffix);
- if (getArg("dnssec-keydir").empty() == false) {
- DIR* d = opendir(getArg("dnssec-keydir").c_str());
- if (d == nullptr) {
+ if (!getArg("dnssec-keydir").empty()) {
+ DIR* dir = opendir(getArg("dnssec-keydir").c_str());
+ if (dir == nullptr) {
throw PDNSException("dnssec-keydir " + getArg("dnssec-keydir") + " does not exist");
}
d_dnssec = true;
- closedir(d);
+ closedir(dir);
}
if (s_rc == 0) { // first instance gets to open everything
initialize();
// infinite recursion.
static bool validateMappingLookupFormats(const vector<string>& formats)
{
- string::size_type cur, last;
+ string::size_type cur = 0;
+ string::size_type last = 0;
+
for (const auto& lookupFormat : formats) {
last = 0;
while ((cur = lookupFormat.find("%", last)) != string::npos) {
- if (!lookupFormat.compare(cur, 3, "%mp")) {
+ if (lookupFormat.compare(cur, 3, "%mp") == 0) {
return false;
}
- else if (!lookupFormat.compare(cur, 2, "%%")) { // Ensure escaped % is also accepted
+
+ if (lookupFormat.compare(cur, 2, "%%") == 0) { // Ensure escaped % is also accepted
last = cur + 2;
continue;
}
dom.domain = DNSName(domain["domain"].as<string>());
dom.ttl = domain["ttl"].as<int>();
- for (YAML::const_iterator recs = domain["records"].begin(); recs != domain["records"].end(); recs++) {
+ for (auto recs = domain["records"].begin(); recs != domain["records"].end(); recs++) {
DNSName qname = DNSName(recs->first.as<string>());
vector<GeoIPDNSResourceRecord> rrs;
- for (YAML::const_iterator item = recs->second.begin(); item != recs->second.end(); item++) {
- YAML::const_iterator rec = item->begin();
+ for (auto item = recs->second.begin(); item != recs->second.end(); item++) {
+ auto rec = item->begin();
GeoIPDNSResourceRecord rr;
rr.domain_id = dom.id;
rr.ttl = dom.ttl;
}
else if (rec->second.IsMap()) {
for (YAML::const_iterator iter = rec->second.begin(); iter != rec->second.end(); iter++) {
- string attr = iter->first.as<string>();
+ auto attr = iter->first.as<string>();
if (attr == "content") {
- string content = iter->second.as<string>();
+ auto content = iter->second.as<string>();
rr.content = std::move(content);
}
else if (attr == "weight") {
}
}
else {
- string content = rec->second.as<string>();
+ auto content = rec->second.as<string>();
rr.content = std::move(content);
rr.weight = 100;
}
- rr.auth = 1;
+ rr.auth = true;
rrs.push_back(rr);
}
std::swap(dom.records[qname], rrs);
}
- for (YAML::const_iterator service = domain["services"].begin(); service != domain["services"].end(); service++) {
- unsigned int netmask4 = 0, netmask6 = 0;
+ for (auto service = domain["services"].begin(); service != domain["services"].end(); service++) {
+ unsigned int netmask4 = 0;
+ unsigned int netmask6 = 0;
DNSName srvName{service->first.as<string>()};
NetmaskTree<vector<string>> nmt;
// if it's an another map, we need to iterate it again, otherwise we just add two root entries.
if (service->second.IsMap()) {
- for (YAML::const_iterator net = service->second.begin(); net != service->second.end(); net++) {
+ for (auto net = service->second.begin(); net != service->second.end(); net++) {
vector<string> value;
if (net->second.IsSequence()) {
value = net->second.as<vector<string>>();
nmt.insert(Netmask("::/0")).second.swap(value);
}
else {
- Netmask nm{net->first.as<string>()};
- nmt.insert(nm).second.swap(value);
- if (nm.isIPv6() == true && netmask6 < nm.getBits())
- netmask6 = nm.getBits();
- if (nm.isIPv6() == false && netmask4 < nm.getBits())
- netmask4 = nm.getBits();
+ Netmask netmask{net->first.as<string>()};
+ nmt.insert(netmask).second.swap(value);
+ if (netmask.isIPv6() && netmask6 < netmask.getBits()) {
+ netmask6 = netmask.getBits();
+ }
+ if (!netmask.isIPv6() && netmask4 < netmask.getBits()) {
+ netmask4 = netmask.getBits();
+ }
}
}
}
// Allow per domain override of mapping_lookup_formats and custom_mapping.
// If not defined, the global values will be used.
if (YAML::Node formats = domain["mapping_lookup_formats"]) {
- vector<string> mapping_lookup_formats = formats.as<vector<string>>();
- if (!validateMappingLookupFormats(mapping_lookup_formats))
+ auto mapping_lookup_formats = formats.as<vector<string>>();
+ if (!validateMappingLookupFormats(mapping_lookup_formats)) {
throw PDNSException(string("%mp is not allowed in mapping lookup formats of domain ") + dom.domain.toLogString());
+ }
dom.mapping_lookup_formats = mapping_lookup_formats;
}
// ensure we have parent in records
DNSName name = item.first;
while (name.chopOff() && name.isPartOf(dom.domain)) {
- if (dom.records.find(name) == dom.records.end() && !dom.services.count(name)) { // don't ENT out a service!
GeoIPDNSResourceRecord rr;
+ if (dom.records.find(name) == dom.records.end() && (dom.services.count(name) == 0U)) { // don't ENT out a service!
vector<GeoIPDNSResourceRecord> rrs;
rr.domain_id = dom.id;
rr.ttl = dom.ttl;
map<uint16_t, GeoIPDNSResourceRecord*> lasts;
bool has_weight = false;
// first we look for used weight
- for (const auto& rr : item.second) {
- weights[rr.qtype.getCode()] += rr.weight;
- if (rr.has_weight)
+ for (const auto& resourceRecord : item.second) {
+ weights[resourceRecord.qtype.getCode()] += static_cast<float>(resourceRecord.weight);
+ if (resourceRecord.has_weight) {
has_weight = true;
+ }
}
if (has_weight) {
// put them back as probabilities and values..
- for (auto& rr : item.second) {
- uint16_t rr_type = rr.qtype.getCode();
- rr.weight = static_cast<int>((static_cast<float>(rr.weight) / weights[rr_type]) * 1000.0);
- sums[rr_type] += rr.weight;
- rr.has_weight = has_weight;
- lasts[rr_type] = &rr;
+ for (auto& resourceRecord : item.second) {
+ uint16_t rr_type = resourceRecord.qtype.getCode();
+ resourceRecord.weight = static_cast<int>((static_cast<float>(resourceRecord.weight) / weights[rr_type]) * 1000.0);
+ sums[rr_type] += static_cast<float>(resourceRecord.weight);
+ resourceRecord.has_weight = has_weight;
+ lasts[rr_type] = &resourceRecord;
}
// remove rounding gap
for (auto& x : lasts) {
float sum = sums[x.first];
- if (sum < 1000)
+ if (sum < 1000) {
x.second->weight += (1000 - sum);
+ }
}
}
}
void GeoIPBackend::loadDomainsFromDirectory(const std::string& dir, vector<GeoIPDomain>& domains)
{
vector<std::filesystem::path> paths;
- for (const std::filesystem::path& p : std::filesystem::directory_iterator(std::filesystem::path(dir)))
- if (std::filesystem::is_regular_file(p) && p.has_extension() && (p.extension() == ".yaml" || p.extension() == ".yml"))
+ for (const std::filesystem::path& p : std::filesystem::directory_iterator(std::filesystem::path(dir))) {
+ if (std::filesystem::is_regular_file(p) && p.has_extension() && (p.extension() == ".yaml" || p.extension() == ".yml")) {
paths.push_back(p);
+ }
+ }
std::sort(paths.begin(), paths.end());
for (const auto& p : paths) {
try {
const auto& zoneRoot = YAML::LoadFile(p.string());
// expect zone key
const auto& zone = zoneRoot["zone"];
- if (loadDomain(zone, domains.size(), dom))
+ if (loadDomain(zone, domains.size(), dom)) {
domains.push_back(dom);
+ }
}
catch (std::exception& ex) {
g_log << Logger::Warning << "Cannot load zone from " << p << ": " << ex.what() << endl;
}
}
- if (s_geoip_files.empty())
+ if (s_geoip_files.empty()) {
g_log << Logger::Warning << "No GeoIP database files loaded!" << endl;
+ }
if (!getArg("zones-file").empty()) {
try {
// if none defined at the domain level.
if (YAML::Node formats = config["mapping_lookup_formats"]) {
d_global_mapping_lookup_formats = formats.as<vector<string>>();
- if (!validateMappingLookupFormats(d_global_mapping_lookup_formats))
+ if (!validateMappingLookupFormats(d_global_mapping_lookup_formats)) {
throw PDNSException(string("%mp is not allowed in mapping lookup"));
+ }
}
if (YAML::Node mapping = config["custom_mapping"]) {
d_global_custom_mapping = mapping.as<map<std::string, std::string>>();
for (YAML::const_iterator _domain = config["domains"].begin(); _domain != config["domains"].end(); _domain++) {
GeoIPDomain dom;
auto id = tmp_domains.size();
- if (loadDomain(*_domain, id, dom))
+ if (loadDomain(*_domain, id, dom)) {
tmp_domains.push_back(std::move(dom));
+ }
}
- if (YAML::Node domain_dir = config["zones_dir"])
+ if (YAML::Node domain_dir = config["zones_dir"]) {
loadDomainsFromDirectory(domain_dir.as<string>(), tmp_domains);
+ }
s_domains.clear();
std::swap(s_domains, tmp_domains);
GeoIPBackend::~GeoIPBackend()
{
try {
- WriteLock wl(&s_state_lock);
+ WriteLock writeLock(&s_state_lock);
s_rc--;
if (s_rc == 0) { // last instance gets to cleanup
s_geoip_files.clear();