dns.h 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553
  1. #include <thread.h> /* for Ref */
  2. #define NS2MS(ns) ((ns) / 1000000L)
  3. #define S2MS(s) ((s) * 1000LL)
  4. #define timems() NS2MS(nsec())
  5. typedef struct Ndbtuple Ndbtuple;
  6. enum
  7. {
  8. /* RR types; see: http://www.iana.org/assignments/dns-parameters */
  9. Ta= 1,
  10. Tns= 2,
  11. Tmd= 3,
  12. Tmf= 4,
  13. Tcname= 5,
  14. Tsoa= 6,
  15. Tmb= 7,
  16. Tmg= 8,
  17. Tmr= 9,
  18. Tnull= 10,
  19. Twks= 11,
  20. Tptr= 12,
  21. Thinfo= 13,
  22. Tminfo= 14,
  23. Tmx= 15,
  24. Ttxt= 16,
  25. Trp= 17,
  26. Tafsdb= 18,
  27. Tx25= 19,
  28. Tisdn= 20,
  29. Trt= 21,
  30. Tnsap= 22,
  31. Tnsapptr= 23,
  32. Tsig= 24,
  33. Tkey= 25,
  34. Tpx= 26,
  35. Tgpos= 27,
  36. Taaaa= 28,
  37. Tloc= 29,
  38. Tnxt= 30,
  39. Teid= 31,
  40. Tnimloc= 32,
  41. Tsrv= 33,
  42. Tatma= 34,
  43. Tnaptr= 35,
  44. Tkx= 36,
  45. Tcert= 37,
  46. Ta6= 38,
  47. Tdname= 39,
  48. Tsink= 40,
  49. Topt= 41,
  50. Tapl= 42,
  51. Tds= 43,
  52. Tsshfp= 44,
  53. Tipseckey= 45,
  54. Trrsig= 46,
  55. Tnsec= 47,
  56. Tdnskey= 48,
  57. Tspf= 99,
  58. Tuinfo= 100,
  59. Tuid= 101,
  60. Tgid= 102,
  61. Tunspec= 103,
  62. /* query types (all RR types are also queries) */
  63. Ttkey= 249, /* transaction key */
  64. Ttsig= 250, /* transaction signature */
  65. Tixfr= 251, /* incremental zone transfer */
  66. Taxfr= 252, /* zone transfer */
  67. Tmailb= 253, /* { Tmb, Tmg, Tmr } */
  68. Tmaila= 254, /* obsolete */
  69. Tall= 255, /* all records */
  70. /* classes */
  71. Csym= 0, /* internal symbols */
  72. Cin= 1, /* internet */
  73. Ccs, /* CSNET (obsolete) */
  74. Cch, /* Chaos net */
  75. Chs, /* Hesiod (?) */
  76. /* class queries (all class types are also queries) */
  77. Call= 255, /* all classes */
  78. /* opcodes */
  79. Oquery= 0<<11, /* normal query */
  80. Oinverse= 1<<11, /* inverse query (retired) */
  81. Ostatus= 2<<11, /* status request */
  82. Onotify= 4<<11, /* notify slaves of updates */
  83. Oupdate= 5<<11,
  84. Omask= 0xf<<11, /* mask for opcode */
  85. /* response codes */
  86. Rok= 0,
  87. Rformat= 1, /* format error */
  88. Rserver= 2, /* server failure (e.g. no answer from something) */
  89. Rname= 3, /* bad name */
  90. Runimplimented= 4, /* unimplemented */
  91. Rrefused= 5, /* we don't like you */
  92. Ryxdomain= 6, /* name exists when it should not */
  93. Ryxrrset= 7, /* rr set exists when it should not */
  94. Rnxrrset= 8, /* rr set that should exist does not */
  95. Rnotauth= 9, /* not authoritative */
  96. Rnotzone= 10, /* name not in zone */
  97. Rbadvers= 16, /* bad opt version */
  98. /* Rbadsig= 16, */ /* also tsig signature failure */
  99. Rbadkey= 17, /* key not recognized */
  100. Rbadtime= 18, /* signature out of time window */
  101. Rbadmode= 19, /* bad tkey mode */
  102. Rbadname= 20, /* duplicate key name */
  103. Rbadalg= 21, /* algorithm not supported */
  104. Rmask= 0x1f, /* mask for response */
  105. Rtimeout= 1<<5, /* timeout sending (for internal use only) */
  106. /* bits in flag word (other than opcode and response) */
  107. Fresp= 1<<15, /* message is a response */
  108. Fauth= 1<<10, /* true if an authoritative response */
  109. Ftrunc= 1<<9, /* truncated message */
  110. Frecurse= 1<<8, /* request recursion */
  111. Fcanrec= 1<<7, /* server can recurse */
  112. Domlen= 256, /* max domain name length (with NULL) */
  113. Labellen= 64, /* max domain label length (with NULL) */
  114. Strlen= 256, /* max string length (with NULL) */
  115. /* time to live values (in seconds) */
  116. Min= 60,
  117. Hour= 60*Min, /* */
  118. Day= 24*Hour, /* Ta, Tmx */
  119. Week= 7*Day, /* Tsoa, Tns */
  120. Year= 52*Week,
  121. DEFTTL= Day,
  122. /* reserved time (can't be timed out earlier) */
  123. Reserved= 5*Min,
  124. /* packet sizes */
  125. Maxudp= 512, /* maximum bytes per udp message sent */
  126. Maxudpin= 2048, /* maximum bytes per udp message rcv'd */
  127. /* length of domain name hash table */
  128. HTLEN= 4*1024,
  129. Maxpath= 128, /* size of mntpt */
  130. Maxlcks= 10, /* max. query-type locks per domain name */
  131. RRmagic= 0xdeadbabe,
  132. DNmagic= 0xa110a110,
  133. /* parallelism: tune; was 32; allow lots */
  134. Maxactive= 250,
  135. /* tune; was 60*1000; keep it short */
  136. Maxreqtm= 8*1000, /* max. ms to process a request */
  137. Notauthoritative = 0,
  138. Authoritative,
  139. };
  140. typedef struct Area Area;
  141. typedef struct Block Block;
  142. typedef struct Cert Cert;
  143. typedef struct DN DN;
  144. typedef struct DNSmsg DNSmsg;
  145. typedef struct Key Key;
  146. typedef struct Null Null;
  147. typedef struct RR RR;
  148. typedef struct Request Request;
  149. typedef struct SOA SOA;
  150. typedef struct Server Server;
  151. typedef struct Sig Sig;
  152. typedef struct Srv Srv;
  153. typedef struct Txt Txt;
  154. /*
  155. * a structure to track a request and any slave process handling it
  156. */
  157. struct Request
  158. {
  159. int isslave; /* pid of slave */
  160. uvlong aborttime; /* time in ms at which we give up */
  161. jmp_buf mret; /* where master jumps to after starting a slave */
  162. int id;
  163. char *from; /* who asked us? */
  164. };
  165. typedef struct Querylck Querylck;
  166. struct Querylck
  167. {
  168. QLock;
  169. // Rendez;
  170. Ref;
  171. };
  172. /*
  173. * a domain name
  174. */
  175. struct DN
  176. {
  177. DN *next; /* hash collision list */
  178. ulong magic;
  179. char *name; /* owner */
  180. RR *rr; /* resource records off this name */
  181. ulong referenced; /* time last referenced */
  182. ulong lookuptime; /* last time we tried to get a better value */
  183. /* refs was `char' but we've seen refs > 120, so go whole hog */
  184. ulong refs; /* for mark and sweep */
  185. ulong ordinal;
  186. ushort class; /* RR class */
  187. uchar keep; /* flag: never age this name */
  188. uchar respcode; /* response code */
  189. /* was: char nonexistent; /* true if we get an authoritative nx for this domain */
  190. /* permit only 1 query per (domain name, type) at a time */
  191. Querylck querylck[Maxlcks];
  192. };
  193. /*
  194. * security info
  195. */
  196. struct Block
  197. {
  198. int dlen;
  199. uchar *data;
  200. };
  201. struct Key
  202. {
  203. int flags;
  204. int proto;
  205. int alg;
  206. Block;
  207. };
  208. struct Cert
  209. {
  210. int type;
  211. int tag;
  212. int alg;
  213. Block;
  214. };
  215. struct Sig
  216. {
  217. Cert;
  218. int labels;
  219. ulong ttl;
  220. ulong exp;
  221. ulong incep;
  222. DN *signer;
  223. };
  224. struct Null
  225. {
  226. Block;
  227. };
  228. /*
  229. * text strings
  230. */
  231. struct Txt
  232. {
  233. Txt *next;
  234. char *p;
  235. };
  236. /*
  237. * an unpacked resource record
  238. */
  239. struct RR
  240. {
  241. RR *next;
  242. ulong magic;
  243. DN *owner; /* domain that owns this resource record */
  244. uintptr pc; /* for tracking memory allocation */
  245. ulong ttl; /* time to live to be passed on */
  246. ulong expire; /* time this entry expires locally */
  247. ulong marker; /* used locally when scanning rrlists */
  248. ushort type; /* RR type */
  249. ushort query; /* query type is in response to */
  250. uchar auth; /* flag: authoritative */
  251. uchar db; /* flag: from database */
  252. uchar cached; /* flag: rr in cache */
  253. uchar negative; /* flag: this is a cached negative response */
  254. union { /* discriminated by negative & type */
  255. DN *negsoaowner; /* soa for cached negative response */
  256. DN *host; /* hostname - soa, cname, mb, md, mf, mx, ns, srv */
  257. DN *cpu; /* cpu type - hinfo */
  258. DN *mb; /* mailbox - mg, minfo */
  259. DN *ip; /* ip address - a, aaaa */
  260. DN *rp; /* rp arg - rp */
  261. uintptr arg0; /* arg[01] are compared to find dups in dn.c */
  262. };
  263. union { /* discriminated by negative & type */
  264. int negrcode; /* response code for cached negative resp. */
  265. DN *rmb; /* responsible maibox - minfo, soa, rp */
  266. DN *ptr; /* pointer to domain name - ptr */
  267. DN *os; /* operating system - hinfo */
  268. ulong pref; /* preference value - mx */
  269. ulong local; /* ns served from local database - ns */
  270. ushort port; /* - srv */
  271. uintptr arg1; /* arg[01] are compared to find dups in dn.c */
  272. };
  273. union { /* discriminated by type */
  274. SOA *soa; /* soa timers - soa */
  275. Key *key;
  276. Cert *cert;
  277. Sig *sig;
  278. Null *null;
  279. Txt *txt;
  280. Srv *srv;
  281. };
  282. };
  283. /*
  284. * list of servers
  285. */
  286. struct Server
  287. {
  288. Server *next;
  289. char *name;
  290. };
  291. /*
  292. * timers for a start-of-authority record. all ulongs are in seconds.
  293. */
  294. struct SOA
  295. {
  296. ulong serial; /* zone serial # */
  297. ulong refresh; /* zone refresh interval */
  298. ulong retry; /* zone retry interval */
  299. ulong expire; /* time to expiration */
  300. ulong minttl; /* min. time to live for any entry */
  301. Server *slaves; /* slave servers */
  302. };
  303. /*
  304. * srv (service location) record (rfc2782):
  305. * _service._proto.name ttl class(IN) 'SRV' priority weight port target
  306. */
  307. struct Srv
  308. {
  309. ushort pri;
  310. ushort weight;
  311. };
  312. typedef struct Rrlist Rrlist;
  313. struct Rrlist
  314. {
  315. int count;
  316. RR *rrs;
  317. };
  318. /*
  319. * domain messages
  320. */
  321. struct DNSmsg
  322. {
  323. ushort id;
  324. int flags;
  325. int qdcount; /* questions */
  326. RR *qd;
  327. int ancount; /* answers */
  328. RR *an;
  329. int nscount; /* name servers */
  330. RR *ns;
  331. int arcount; /* hints */
  332. RR *ar;
  333. };
  334. /*
  335. * definition of local area for dblookup
  336. */
  337. struct Area
  338. {
  339. Area *next;
  340. int len; /* strlen(area->soarr->owner->name) */
  341. RR *soarr; /* soa defining this area */
  342. int neednotify;
  343. int needrefresh;
  344. };
  345. typedef struct Cfg Cfg;
  346. struct Cfg {
  347. int cachedb;
  348. int resolver;
  349. int justforw; /* flag: pure resolver, just forward queries */
  350. int serve; /* flag: serve udp queries */
  351. int inside;
  352. int straddle;
  353. };
  354. /* (udp) query stats */
  355. typedef struct {
  356. QLock;
  357. ulong slavehiwat; /* procs */
  358. ulong qrecvd9p; /* query counts */
  359. ulong qrecvdudp;
  360. ulong qsent;
  361. ulong qrecvd9prpc; /* packet count */
  362. ulong alarms;
  363. /* reply times by count */
  364. ulong under10ths[3*10+2]; /* under n*0.1 seconds, n is index */
  365. ulong tmout;
  366. ulong tmoutcname;
  367. ulong tmoutv6;
  368. ulong answinmem; /* answers in memory */
  369. ulong negans; /* negative answers received */
  370. ulong negserver; /* neg ans with Rserver set */
  371. ulong negbaddeleg; /* neg ans with bad delegations */
  372. ulong negbdnoans; /* ⋯ and no answers */
  373. ulong negnorname; /* neg ans with no Rname set */
  374. ulong negcached; /* neg ans cached */
  375. } Stats;
  376. Stats stats;
  377. enum
  378. {
  379. Recurse,
  380. Dontrecurse,
  381. NOneg,
  382. OKneg,
  383. };
  384. extern Cfg cfg;
  385. extern char *dbfile;
  386. extern int debug;
  387. extern Area *delegated;
  388. extern char *logfile;
  389. extern int maxage; /* age of oldest entry in cache (secs) */
  390. extern char mntpt[];
  391. extern int needrefresh;
  392. extern int norecursion;
  393. extern ulong now; /* time base */
  394. extern vlong nowns;
  395. extern Area *owned;
  396. extern int sendnotifies;
  397. extern ulong target;
  398. extern int testing; /* test cache whenever removing a DN */
  399. extern char *trace;
  400. extern int traceactivity;
  401. extern char *zonerefreshprogram;
  402. #pragma varargck type "R" RR*
  403. #pragma varargck type "Q" RR*
  404. /* dn.c */
  405. extern char *rrtname[];
  406. extern char *rname[];
  407. extern unsigned nrname;
  408. extern char *opname[];
  409. extern Lock dnlock;
  410. void abort(); /* char*, ... */;
  411. void addserver(Server**, char*);
  412. Server* copyserverlist(Server*);
  413. void db2cache(int);
  414. void dnage(DN*);
  415. void dnageall(int);
  416. void dnagedb(void);
  417. void dnageallnever(void);
  418. void dnagenever(DN *, int);
  419. void dnauthdb(void);
  420. void dncheck(void*, int);
  421. void dndump(char*);
  422. void dnget(void);
  423. void dninit(void);
  424. DN* dnlookup(char*, int, int);
  425. void dnptr(uchar*, uchar*, char*, int, int, int);
  426. void dnpurge(void);
  427. void dnput(void);
  428. void dnslog(char*, ...);
  429. void dnstats(char *file);
  430. void* emalloc(int);
  431. char* estrdup(char*);
  432. void freeanswers(DNSmsg *mp);
  433. void freeserverlist(Server*);
  434. int getactivity(Request*, int);
  435. Area* inmyarea(char*);
  436. void putactivity(int);
  437. RR* randomize(RR*);
  438. RR* rralloc(int);
  439. void rrattach(RR*, int);
  440. int rravfmt(Fmt*);
  441. RR* rrcat(RR**, RR*);
  442. RR** rrcopy(RR*, RR**);
  443. int rrfmt(Fmt*);
  444. void rrfree(RR*);
  445. void rrfreelist(RR*);
  446. RR* rrlookup(DN*, int, int);
  447. char* rrname(int, char*, int);
  448. RR* rrremneg(RR**);
  449. RR* rrremtype(RR**, int);
  450. int rrsupported(int);
  451. int rrtype(char*);
  452. void slave(Request*);
  453. int subsume(char*, char*);
  454. int tsame(int, int);
  455. void unique(RR*);
  456. void warning(char*, ...);
  457. /* dnarea.c */
  458. void refresh_areas(Area*);
  459. void freearea(Area**);
  460. void addarea(DN *dp, RR *rp, Ndbtuple *t);
  461. /* dblookup.c */
  462. int baddelegation(RR*, RR*, uchar*);
  463. RR* dbinaddr(DN*, int);
  464. RR* dblookup(char*, int, int, int, int);
  465. void dnforceage(void);
  466. RR* dnsservers(int);
  467. RR* domainlist(int);
  468. int insideaddr(char *dom);
  469. int insidens(uchar *ip);
  470. int myaddr(char *addr);
  471. int opendatabase(void);
  472. uchar* outsidens(int);
  473. /* dns.c */
  474. char* walkup(char*);
  475. RR* getdnsservers(int);
  476. void logreply(int, uchar*, DNSmsg*);
  477. void logsend(int, int, uchar*, char*, char*, int);
  478. void procsetname(char *fmt, ...);
  479. /* dnresolve.c */
  480. RR* dnresolve(char*, int, int, Request*, RR**, int, int, int, int*);
  481. int udpport(char *);
  482. int mkreq(DN *dp, int type, uchar *buf, int flags, ushort reqno);
  483. int seerootns(void);
  484. void initdnsmsg(DNSmsg *mp, RR *rp, int flags, ushort reqno);
  485. DNSmsg* newdnsmsg(RR *rp, int flags, ushort reqno);
  486. /* dnserver.c */
  487. void dnserver(DNSmsg*, DNSmsg*, Request*, uchar *, int);
  488. void dnudpserver(char*);
  489. void dntcpserver(char*);
  490. /* dnnotify.c */
  491. void dnnotify(DNSmsg*, DNSmsg*, Request*);
  492. void notifyproc(void);
  493. /* convDNS2M.c */
  494. int convDNS2M(DNSmsg*, uchar*, int);
  495. /* convM2DNS.c */
  496. char* convM2DNS(uchar*, int, DNSmsg*, int*);
  497. #pragma varargck argpos dnslog 1