1 /***************************************************************************
2  * nmap_dns.h -- Handles parallel reverse DNS resolution for target IPs    *
3  *                                                                         *
4  ***********************IMPORTANT NMAP LICENSE TERMS************************
5  *                                                                         *
6  * The Nmap Security Scanner is (C) 1996-2020 Insecure.Com LLC ("The Nmap  *
7  * Project"). Nmap is also a registered trademark of the Nmap Project.     *
8  *                                                                         *
9  * This program is distributed under the terms of the Nmap Public Source   *
10  * License (NPSL). The exact license text applying to a particular Nmap    *
11  * release or source code control revision is contained in the LICENSE     *
12  * file distributed with that version of Nmap or source code control       *
13  * revision. More Nmap copyright/legal information is available from       *
14  * https://nmap.org/book/man-legal.html, and further information on the    *
15  * NPSL license itself can be found at https://nmap.org/npsl. This header  *
16  * summarizes some key points from the Nmap license, but is no substitute  *
17  * for the actual license text.                                            *
18  *                                                                         *
19  * Nmap is generally free for end users to download and use themselves,    *
20  * including commercial use. It is available from https://nmap.org.        *
21  *                                                                         *
22  * The Nmap license generally prohibits companies from using and           *
23  * redistributing Nmap in commercial products, but we sell a special Nmap  *
24  * OEM Edition with a more permissive license and special features for     *
25  * this purpose. See https://nmap.org/oem                                  *
26  *                                                                         *
27  * If you have received a written Nmap license agreement or contract       *
28  * stating terms other than these (such as an Nmap OEM license), you may   *
29  * choose to use and redistribute Nmap under those terms instead.          *
30  *                                                                         *
31  * The official Nmap Windows builds include the Npcap software             *
32  * (https://npcap.org) for packet capture and transmission. It is under    *
33  * separate license terms which forbid redistribution without special      *
34  * permission. So the official Nmap Windows builds may not be              *
35  * redistributed without special permission (such as an Nmap OEM           *
36  * license).                                                               *
37  *                                                                         *
38  * Source is provided to this software because we believe users have a     *
39  * right to know exactly what a program is going to do before they run it. *
40  * This also allows you to audit the software for security holes.          *
41  *                                                                         *
42  * Source code also allows you to port Nmap to new platforms, fix bugs,    *
43  * and add new features.  You are highly encouraged to submit your         *
44  * changes as a Github PR or by email to the dev@nmap.org mailing list     *
45  * for possible incorporation into the main distribution. Unless you       *
46  * specify otherwise, it is understood that you are offering us very       *
47  * broad rights to use your submissions as described in the Nmap Public    *
48  * Source License Contributor Agreement. This is important because we      *
49  * fund the project by selling licenses with various terms, and also       *
50  * because the inability to relicense code has caused devastating          *
51  * problems for other Free Software projects (such as KDE and NASM).       *
52  *                                                                         *
53  * The free version of Nmap is distributed in the hope that it will be     *
54  * useful, but WITHOUT ANY WARRANTY; without even the implied warranty of  *
55  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. Warranties,        *
56  * indemnification and commercial support are all available through the    *
57  * Npcap OEM program--see https://nmap.org/oem.                            *
58  *                                                                         *
59  ***************************************************************************/
60 
61 #ifndef NMAP_DNS_H
62 #define NMAP_DNS_H
63 
64 class Target;
65 
66 #include <nbase.h>
67 
68 #include <string>
69 #include <list>
70 
71 #include <algorithm>
72 #include <sstream>
73 
74 
75 namespace DNS
76 {
77 
78 #define DNS_CHECK_ACCUMLATE(accumulator, tmp, exp) \
79   do { tmp = exp; if(tmp < 1) return 0 ; accumulator += tmp;} while(0)
80 
81 #define DNS_CHECK_UPPER_BOUND(accumulator, max)\
82   do { if(accumulator > max) return 0; } while(0)
83 
84 #define DNS_HAS_FLAG(v,flag) ((v&flag)==flag)
85 
86 #define DNS_HAS_ERR(v, err) ((v&DNS::ERR_ALL)==err)
87 
88 typedef enum
89 {
90   ID = 0,
91   FLAGS_OFFSET = 2,
92   QDCOUNT = 4,
93   ANCOUNT = 6,
94   NSCOUNT = 8,
95   ARCOUNT = 10,
96   DATA = 12
97 } HEADER_OFFSET;
98 
99 typedef enum {
100   ERR_ALL = 0x0007,
101   CHECKING_DISABLED = 0x0010,
102   AUTHENTICATED_DATA = 0x0020,
103   ZERO = 0x0070,
104   RECURSION_AVAILABLE = 0x0080,
105   RECURSION_DESIRED = 0x0100,
106   TRUNCATED = 0x0200,
107   AUTHORITATIVE_ANSWER = 0x0400,
108   OP_STANDARD_QUERY = 0x0000,
109   OP_INVERSE_QUERY = 0x0800, // Obsoleted in RFC 3425
110   OP_SERVER_STATUS = 0x1000,
111   RESPONSE = 0x8000
112 } FLAGS;
113 
114 typedef enum {
115   ERR_NO = 0x0000,
116   ERR_FORMAT = 0x0001,
117   ERR_SERVFAIL = 0x0002,
118   ERR_NAME = 0x0003,
119   ERR_NOT_IMPLEMENTED = 0x0004,
120   ERR_REFUSED = 0x0005,
121 } ERRORS;
122 
123 typedef enum {
124   A = 1,
125   CNAME = 5,
126   PTR = 12,
127   AAAA = 28,
128 } RECORD_TYPE;
129 
130 typedef enum {
131   CLASS_IN = 1
132 } RECORD_CLASS;
133 
134 const u8 COMPRESSED_NAME = 0xc0;
135 
136 #define C_IPV4_PTR_DOMAIN ".in-addr.arpa"
137 #define C_IPV6_PTR_DOMAIN ".ip6.arpa"
138 const std::string IPV4_PTR_DOMAIN = C_IPV4_PTR_DOMAIN;
139 const std::string IPV6_PTR_DOMAIN = C_IPV6_PTR_DOMAIN;
140 
141 class Factory
142 {
143 public:
144   static u16 progressiveId;
145   static bool ipToPtr(const sockaddr_storage &ip, std::string &ptr);
146   static bool ptrToIp(const std::string &ptr, sockaddr_storage &ip);
147   static size_t buildSimpleRequest(const std::string &name, RECORD_TYPE rt, u8 *buf, size_t maxlen);
148   static size_t buildReverseRequest(const sockaddr_storage &ip, u8 *buf, size_t maxlen);
149   static size_t putUnsignedShort(u16 num, u8 *buf, size_t offset, size_t maxlen);
150   static size_t putDomainName(const std::string &name, u8 *buf, size_t offset, size_t maxlen);
151   static size_t parseUnsignedShort(u16 &num, const u8 *buf, size_t offset, size_t maxlen);
152   static size_t parseUnsignedInt(u32 &num, const u8 *buf, size_t offset, size_t maxlen);
153   static size_t parseDomainName(std::string &name, const u8 *buf, size_t offset, size_t maxlen);
154 };
155 
156 class Record
157 {
158 public:
159   virtual Record * clone() = 0;
~Record()160   virtual ~Record() {}
161   virtual size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen) = 0;
162 };
163 
164 class A_Record : public Record
165 {
166 public:
167   sockaddr_storage value;
clone()168   Record * clone() { return new A_Record(*this); }
~A_Record()169   ~A_Record() {}
170   size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen);
171 };
172 
173 class PTR_Record : public Record
174 {
175 public:
176   std::string value;
clone()177   Record * clone() { return new PTR_Record(*this); }
~PTR_Record()178   ~PTR_Record() {}
parseFromBuffer(const u8 * buf,size_t offset,size_t maxlen)179   size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen)
180   {
181     return Factory::parseDomainName(value, buf, offset, maxlen);
182   }
183 };
184 
185 class CNAME_Record : public Record
186 {
187 public:
188   std::string value;
clone()189   Record * clone() { return new CNAME_Record(*this); }
~CNAME_Record()190   ~CNAME_Record() {}
parseFromBuffer(const u8 * buf,size_t offset,size_t maxlen)191   size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen)
192   {
193     return Factory::parseDomainName(value, buf, offset, maxlen);
194   }
195 };
196 
197 class Query
198 {
199 public:
200   std::string name;
201   u16 record_type;
202   u16 record_class;
203 
204   size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen);
205 };
206 
207 class Answer
208 {
209 public:
Answer()210   Answer() : record(NULL) {}
Answer(const Answer & c)211   Answer(const Answer &c) : name(c.name), record_type(c.record_type),
212     record_class(c.record_class), ttl(c.ttl), length(c.length),
213     record(c.record->clone()) {}
~Answer()214   ~Answer() { delete record; }
215 
216   std::string name;
217   u16 record_type;
218   u16 record_class;
219   u32 ttl;
220   u16 length;
221   Record * record;
222 
223   // Populate the object reading from buffer and returns "consumed" bytes
224   size_t parseFromBuffer(const u8 *buf, size_t offset, size_t maxlen);
225   Answer& operator=(const Answer &r);
226 };
227 
228 class Packet
229 {
230 public:
Packet()231   Packet() : id(0), flags(0) {}
~Packet()232   ~Packet() {}
233 
addFlags(FLAGS fl)234   void addFlags(FLAGS fl){ flags |= fl; }
removeFlags(FLAGS fl)235   void removeFlags(FLAGS fl){ flags &= ~fl; }
resetFlags()236   void resetFlags() { flags = 0; }
237   size_t writeToBuffer(u8 *buf, size_t maxlen);
238   size_t parseFromBuffer(const u8 *buf, size_t maxlen);
239 
240   u16 id;
241   u16 flags;
242   std::list<Query> queries;
243   std::list<Answer> answers;
244 };
245 
246 }
247 
248 void nmap_mass_rdns(Target ** targets, int num_targets);
249 
250 std::list<std::string> get_dns_servers();
251 
252 #endif
253