void DNSUpdate::deletePTRRecordFromRRSet(){ DnsRR rr; const int bufSize = 128; char destination[16]; char result[bufSize]; memset(result, 0, bufSize); inet_pton6(hostip, destination); doRevDnsAddress(destination,result); rr.NAME = result; rr.TYPE = qtype_getcode("PTR", false); rr.CLASS = QCLASS_NONE; rr.TTL = 0; string tmp = string(_hostname); string data = rr_fromstring(rr.TYPE, tmp.c_str()); rr.RDLENGTH = data.size(); rr.RDATA = (unsigned char*)memdup(data.c_str(), rr.RDLENGTH); message->authority.push_back(rr); Log(Debug) << "DDNR: PTR record created: " << result << " -> " << tmp << LogEnd; Log(Debug) << "DDNS: PTR record created: " << result << " -> " << tmp << LogEnd; }
/* the entry function which will handle all queries */ DnsMessage *my_handle_query(pending_query *query) { DnsMessage *a = new DnsMessage(); DnsQuestion q; DnsRR rr; /* set a as an answer to the query */ a->ID = query->message->ID; a->RD = query->message->RD; a->RA = false; if (query->message->questions.begin() == query->message->questions.end()) { /* query did not contain question */ a->RCODE = RCODE_QUERYERR; return a; } q = *query->message->questions.begin(); a->questions.push_back(q); a->QR = true; pos_log(context_server, log_info, "Query: [%s,%s]", q.QNAME.tocstr(), str_qtype(q.QTYPE).c_str()); if (q.QTYPE == DNS_TYPE_A && q.QNAME == dyndomain) { rr = DnsRR(dyndomain, DNS_TYPE_A, CLASS_IN, 3600); string data = rr_fromstring(DNS_TYPE_A, "200.200.200.200"); // Anything... rr.RDLENGTH = data.size(); rr.RDATA = (char *)memdup(data.c_str(), data.size()); a->answers.push_back(rr); rr = DnsRR("org", DNS_TYPE_NS, CLASS_IN, 3600); data = rr_fromstring(DNS_TYPE_NS, "fakedns.com"); rr.RDLENGTH = data.size(); rr.RDATA = (char *)memdup(data.c_str(), data.size()); a->authority.push_back(rr); rr = DnsRR("fakedns.com", DNS_TYPE_A, CLASS_IN, 3600); data = rr_fromstring(DNS_TYPE_A, "200.200.200.201"); // Anything... rr.RDLENGTH = data.size(); rr.RDATA = (char *)memdup(data.c_str(), data.size()); a->additional.push_back(rr); } else { /* we don't want this */ a->RCODE = RCODE_SRVFAIL; } return a; }
/** * insert a new-AAAA entry in message * */ void DNSUpdate::addinMsg_newAAAA(){ DnsRR rr; rr.NAME = domainname(_hostname, *zoneroot); rr.TYPE = qtype_getcode("AAAA", false); rr.TTL = txt_to_int(ttl); string data = rr_fromstring(rr.TYPE, hostip, *zoneroot); rr.RDLENGTH = data.size(); rr.RDATA = (unsigned char*)memdup(data.c_str(), rr.RDLENGTH); message->authority.push_back(rr); Log(Debug) << "DDNS: AAAA record created:" << rr.NAME.tostring() << " -> " << hostip << LogEnd; }
/** * delete a single rr from rrset. If no such RRs exist, then this Update RR will be * silently ignored by the primary master. * */ void DNSUpdate::deleteAAAARecordFromRRSet(){ DnsRR rr; rr.NAME = domainname(_hostname, *zoneroot); rr.TYPE = qtype_getcode("AAAA", false); rr.CLASS = QCLASS_NONE; /* 254 */ rr.TTL = 0; string data = rr_fromstring(rr.TYPE, hostip, *zoneroot); rr.RDLENGTH = data.size(); rr.RDATA = (unsigned char*)memdup(data.c_str(), rr.RDLENGTH); message->authority.push_back(rr); Log(Debug) << "DDNS: AAAA record created:" << rr.NAME.tostring() << " -> " << hostip << LogEnd; }
void read_master_file(const char *file, domainname &znroot, void *userdat, error_callback err, rr_callback rr_cb, rr_literal_callback rrl_cb, comment_callback comm_cb, int flags) { bool has_znroot = !(flags&POSLIB_MF_AUTOPROBE), has_soa = false; char buff[1024]; char *ptr, *p2; int c; bool ttl_given = false; stl_string ttl = "3600"; domainname origin, nam; int linenum = 1, linenum2; stl_string str, tmp, t2, t3, nm; DnsRR rr; rr_type *type = NULL; FILE *f = try_fopen_r(file); if (!f) throw PException(true, "Could not open %s", file); c = fgetc(f); if (c != EOF) ungetc(c, f); if (has_znroot) origin = znroot; try { begin: while (!feof(f)) { /* since the poslib functions will filter out comments, let's do them ourselves */ if (comm_cb) { c = fgetc(f); if (c == ';') { fgets(buff, 1024, f); ptr = buff + strlen(buff) - 1; while (ptr >= buff && (*ptr == '\n' || *ptr == '\r')) *ptr = '\0'; comm_cb(userdat, buff); continue; } ungetc(c, f); } try { read_line(buff, f, &linenum, &linenum2); } catch (PException p) { break; } if (buff[0] == 0) goto begin; ptr = buff; while (*ptr == ' ' || *ptr == '\t') ptr++; if (*ptr == '\0') continue; if (buff[0] == '$') { if (strncmpi(buff, "$ttl ", 4) == 0) { ttl = buff + 5; ttl_given = true; } else if (strncmpi(buff, "$origin ", 8) == 0) { /* origin */ origin = domainname(buff + 8, znroot); if (!has_znroot) { /* first entry. this is the zone root */ znroot = origin; has_znroot = true; } } else err(userdat, file, linenum2, PException(true, "Unknown directive %s", buff).message); continue; } if (!has_znroot) { znroot = guess_zone_name(file); origin = znroot; has_znroot = true; } if (buff[0] != ' ' && buff[0] != '\t') { nam = domainname(read_entry(ptr).c_str(), origin); } else if (!has_soa) { err(userdat, file, linenum2, "First record in zone should have a domain name! Using origin instead."); nam = origin; } /* can be class or ttl or rrtype */ while (1) { str = read_entry(ptr); if (str == "IN" || str == "HS" || str == "CH" || str == "HS" || str == "in" || str == "hs" || str == "ch" || str == "hs") { /* class */ continue; } else if ((type = rrtype_getinfo(str.c_str())) != NULL) { break; } else { try { txt_to_int(str.c_str()); ttl_given = true; } catch (PException p) { err(userdat, file, linenum2, PException(true, "Invalid TTL/RR type %s!", str.c_str()).message); goto begin; } ttl = str.c_str(); } } if (!has_soa) { if (type->type != DNS_TYPE_SOA) { if (!(flags & POSLIB_MF_NOSOA)) { err(userdat, file, linenum2, "First record was no SOA record; using default SOA record instead."); if (rr_cb) { rr.NAME = znroot; rr.TYPE = DNS_TYPE_SOA; rr.TTL = 3600; tmp = rr_fromstring(DNS_TYPE_SOA, "ns1 hostmaster 1 2h 1h 1d 2h", znroot); rr.RDLENGTH = tmp.size(); rr.RDATA = (unsigned char *)memdup(tmp.c_str(), tmp.size()); rr_cb(userdat, &rr); } if (rrl_cb) rrl_cb(userdat, "@", "1h", "SOA", "ns1 hostmaster 1 2h 1h 1d 2h", znroot); } else if (!ttl_given) { err(userdat, file, linenum2, "First record should have TTL value; using 1h for now."); ttl = "3600"; ttl_given = true; } } else { if (!ttl_given) { p2 = ptr; read_entry(p2); read_entry(p2); read_entry(p2); read_entry(p2); read_entry(p2); read_entry(p2); t3 = read_entry(p2); if (strlen(t3.c_str()) < 32) ttl = t3; } } has_soa = true; } else if (type->type == DNS_TYPE_SOA && !(flags & POSLIB_MF_NOSOA)) { err(userdat, file, linenum2, "Non-initial SOA record ignored"); continue; } if (!(nam >= znroot)) { err(userdat, file, linenum2, PException(true, "Ignoring domain name %s outside of zone %s!", nam.tocstr(), znroot.tocstr()).message); continue; } if (rr_cb) { try { rr.NAME = nam; rr.TYPE = type->type; rr.TTL = txt_to_int(ttl.c_str()); tmp = rr_fromstring(type->type, ptr, origin); rr.RDLENGTH = tmp.size(); rr.RDATA = (unsigned char *)memdup(tmp.c_str(), tmp.size()); rr_cb(userdat, &rr); } catch (PException p) { err(userdat, file, linenum2, p.message); } } if (rrl_cb) { try { t2 = ptr; nm = nam.torelstring(znroot); tmp = rr_fromstring(type->type, ptr, origin); if (origin != znroot) t2 = rrdata_convertdoms(type, znroot, origin, ptr); } catch (PException p) { err(userdat, file, linenum2, p.message); } rrl_cb(userdat, nm.c_str(), ttl.c_str(), type->name, t2.c_str(), znroot); } } } catch (PException p) { fclose(f); throw p; } fclose(f); }