ares-test-parse-srv.cc
Go to the documentation of this file.
1 #include "ares-test.h"
2 #include "dns-proto.h"
3 
4 #include <sstream>
5 #include <vector>
6 
7 namespace ares {
8 namespace test {
9 
10 TEST_F(LibraryTest, ParseSrvReplyOK) {
11  DNSPacket pkt;
12  pkt.set_qid(0x1234).set_response().set_aa()
13  .add_question(new DNSQuestion("example.com", T_SRV))
14  .add_answer(new DNSSrvRR("example.com", 100, 10, 20, 30, "srv.example.com"))
15  .add_answer(new DNSSrvRR("example.com", 100, 11, 21, 31, "srv2.example.com"));
16  std::vector<byte> data = pkt.data();
17 
18  struct ares_srv_reply* srv = nullptr;
19  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv));
20  ASSERT_NE(nullptr, srv);
21 
22  EXPECT_EQ("srv.example.com", std::string(srv->host));
23  EXPECT_EQ(10, srv->priority);
24  EXPECT_EQ(20, srv->weight);
25  EXPECT_EQ(30, srv->port);
26 
27  struct ares_srv_reply* srv2 = srv->next;
28  ASSERT_NE(nullptr, srv2);
29  EXPECT_EQ("srv2.example.com", std::string(srv2->host));
30  EXPECT_EQ(11, srv2->priority);
31  EXPECT_EQ(21, srv2->weight);
32  EXPECT_EQ(31, srv2->port);
33  EXPECT_EQ(nullptr, srv2->next);
34 
35  ares_free_data(srv);
36 }
37 
38 TEST_F(LibraryTest, ParseSrvReplySingle) {
39  DNSPacket pkt;
40  pkt.set_qid(0x1234).set_response().set_aa()
41  .add_question(new DNSQuestion("example.abc.def.com", T_SRV))
42  .add_answer(new DNSSrvRR("example.abc.def.com", 180, 0, 10, 8160, "example.abc.def.com"))
43  .add_auth(new DNSNsRR("abc.def.com", 44, "else1.where.com"))
44  .add_auth(new DNSNsRR("abc.def.com", 44, "else2.where.com"))
45  .add_auth(new DNSNsRR("abc.def.com", 44, "else3.where.com"))
46  .add_auth(new DNSNsRR("abc.def.com", 44, "else4.where.com"))
47  .add_auth(new DNSNsRR("abc.def.com", 44, "else5.where.com"))
48  .add_additional(new DNSARR("else2.where.com", 42, {172,19,0,1}))
49  .add_additional(new DNSARR("else5.where.com", 42, {172,19,0,2}));
50  std::vector<byte> data = pkt.data();
51 
52  struct ares_srv_reply* srv = nullptr;
53  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv));
54  ASSERT_NE(nullptr, srv);
55 
56  EXPECT_EQ("example.abc.def.com", std::string(srv->host));
57  EXPECT_EQ(0, srv->priority);
58  EXPECT_EQ(10, srv->weight);
59  EXPECT_EQ(8160, srv->port);
60  EXPECT_EQ(nullptr, srv->next);
61 
62  ares_free_data(srv);
63 }
64 
65 TEST_F(LibraryTest, ParseSrvReplyMalformed) {
66  std::vector<byte> data = {
67  0x12, 0x34, // qid
68  0x84, // response + query + AA + not-TC + not-RD
69  0x00, // not-RA + not-Z + not-AD + not-CD + rc=NoError
70  0x00, 0x01, // num questions
71  0x00, 0x01, // num answer RRs
72  0x00, 0x00, // num authority RRs
73  0x00, 0x00, // num additional RRs
74  // Question
75  0x07, 'e', 'x', 'a', 'm', 'p', 'l', 'e',
76  0x03, 'c', 'o', 'm',
77  0x00,
78  0x00, 0x21, // type SRV
79  0x00, 0x01, // class IN
80  // Answer 1
81  0x07, 'e', 'x', 'a', 'm', 'p', 'l', 'e',
82  0x03, 'c', 'o', 'm',
83  0x00,
84  0x00, 0x21, // RR type
85  0x00, 0x01, // class IN
86  0x01, 0x02, 0x03, 0x04, // TTL
87  0x00, 0x04, // rdata length -- too short
88  0x02, 0x03, 0x04, 0x05,
89  };
90 
91  struct ares_srv_reply* srv = nullptr;
92  EXPECT_EQ(ARES_EBADRESP, ares_parse_srv_reply(data.data(), data.size(), &srv));
93  ASSERT_EQ(nullptr, srv);
94 }
95 
96 TEST_F(LibraryTest, ParseSrvReplyMultiple) {
97  DNSPacket pkt;
98  pkt.set_qid(0x1234).set_response().set_ra().set_rd()
99  .add_question(new DNSQuestion("srv.example.com", T_SRV))
100  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 6789, "a1.srv.example.com"))
101  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 4567, "a2.srv.example.com"))
102  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 5678, "a3.srv.example.com"))
103  .add_auth(new DNSNsRR("example.com", 300, "ns1.example.com"))
104  .add_auth(new DNSNsRR("example.com", 300, "ns2.example.com"))
105  .add_auth(new DNSNsRR("example.com", 300, "ns3.example.com"))
106  .add_additional(new DNSARR("a1.srv.example.com", 300, {172,19,1,1}))
107  .add_additional(new DNSARR("a2.srv.example.com", 300, {172,19,1,2}))
108  .add_additional(new DNSARR("a3.srv.example.com", 300, {172,19,1,3}))
109  .add_additional(new DNSARR("n1.example.com", 300, {172,19,0,1}))
110  .add_additional(new DNSARR("n2.example.com", 300, {172,19,0,2}))
111  .add_additional(new DNSARR("n3.example.com", 300, {172,19,0,3}));
112  std::vector<byte> data = pkt.data();
113 
114  struct ares_srv_reply* srv0 = nullptr;
115  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv0));
116  ASSERT_NE(nullptr, srv0);
117  struct ares_srv_reply* srv = srv0;
118 
119  EXPECT_EQ("a1.srv.example.com", std::string(srv->host));
120  EXPECT_EQ(0, srv->priority);
121  EXPECT_EQ(5, srv->weight);
122  EXPECT_EQ(6789, srv->port);
123  EXPECT_NE(nullptr, srv->next);
124  srv = srv->next;
125 
126  EXPECT_EQ("a2.srv.example.com", std::string(srv->host));
127  EXPECT_EQ(0, srv->priority);
128  EXPECT_EQ(5, srv->weight);
129  EXPECT_EQ(4567, srv->port);
130  EXPECT_NE(nullptr, srv->next);
131  srv = srv->next;
132 
133  EXPECT_EQ("a3.srv.example.com", std::string(srv->host));
134  EXPECT_EQ(0, srv->priority);
135  EXPECT_EQ(5, srv->weight);
136  EXPECT_EQ(5678, srv->port);
137  EXPECT_EQ(nullptr, srv->next);
138 
139  ares_free_data(srv0);
140 }
141 
142 TEST_F(LibraryTest, ParseSrvReplyCname) {
143  DNSPacket pkt;
144  pkt.set_qid(0x1234).set_response().set_aa()
145  .add_question(new DNSQuestion("example.abc.def.com", T_SRV))
146  .add_answer(new DNSCnameRR("example.abc.def.com", 300, "cname.abc.def.com"))
147  .add_answer(new DNSSrvRR("cname.abc.def.com", 300, 0, 10, 1234, "srv.abc.def.com"))
148  .add_auth(new DNSNsRR("abc.def.com", 44, "else1.where.com"))
149  .add_auth(new DNSNsRR("abc.def.com", 44, "else2.where.com"))
150  .add_auth(new DNSNsRR("abc.def.com", 44, "else3.where.com"))
151  .add_additional(new DNSARR("example.abc.def.com", 300, {172,19,0,1}))
152  .add_additional(new DNSARR("else1.where.com", 42, {172,19,0,1}))
153  .add_additional(new DNSARR("else2.where.com", 42, {172,19,0,2}))
154  .add_additional(new DNSARR("else3.where.com", 42, {172,19,0,3}));
155  std::vector<byte> data = pkt.data();
156 
157  struct ares_srv_reply* srv = nullptr;
158  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv));
159  ASSERT_NE(nullptr, srv);
160 
161  EXPECT_EQ("srv.abc.def.com", std::string(srv->host));
162  EXPECT_EQ(0, srv->priority);
163  EXPECT_EQ(10, srv->weight);
164  EXPECT_EQ(1234, srv->port);
165  EXPECT_EQ(nullptr, srv->next);
166 
167  ares_free_data(srv);
168 }
169 
170 TEST_F(LibraryTest, ParseSrvReplyCnameMultiple) {
171  DNSPacket pkt;
172  pkt.set_qid(0x1234).set_response().set_ra().set_rd()
173  .add_question(new DNSQuestion("query.example.com", T_SRV))
174  .add_answer(new DNSCnameRR("query.example.com", 300, "srv.example.com"))
175  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 6789, "a1.srv.example.com"))
176  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 4567, "a2.srv.example.com"))
177  .add_answer(new DNSSrvRR("srv.example.com", 300, 0, 5, 5678, "a3.srv.example.com"))
178  .add_auth(new DNSNsRR("example.com", 300, "ns1.example.com"))
179  .add_auth(new DNSNsRR("example.com", 300, "ns2.example.com"))
180  .add_auth(new DNSNsRR("example.com", 300, "ns3.example.com"))
181  .add_additional(new DNSARR("a1.srv.example.com", 300, {172,19,1,1}))
182  .add_additional(new DNSARR("a2.srv.example.com", 300, {172,19,1,2}))
183  .add_additional(new DNSARR("a3.srv.example.com", 300, {172,19,1,3}))
184  .add_additional(new DNSARR("n1.example.com", 300, {172,19,0,1}))
185  .add_additional(new DNSARR("n2.example.com", 300, {172,19,0,2}))
186  .add_additional(new DNSARR("n3.example.com", 300, {172,19,0,3}));
187  std::vector<byte> data = pkt.data();
188 
189  struct ares_srv_reply* srv0 = nullptr;
190  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv0));
191  ASSERT_NE(nullptr, srv0);
192  struct ares_srv_reply* srv = srv0;
193 
194  EXPECT_EQ("a1.srv.example.com", std::string(srv->host));
195  EXPECT_EQ(0, srv->priority);
196  EXPECT_EQ(5, srv->weight);
197  EXPECT_EQ(6789, srv->port);
198  EXPECT_NE(nullptr, srv->next);
199  srv = srv->next;
200 
201  EXPECT_EQ("a2.srv.example.com", std::string(srv->host));
202  EXPECT_EQ(0, srv->priority);
203  EXPECT_EQ(5, srv->weight);
204  EXPECT_EQ(4567, srv->port);
205  EXPECT_NE(nullptr, srv->next);
206  srv = srv->next;
207 
208  EXPECT_EQ("a3.srv.example.com", std::string(srv->host));
209  EXPECT_EQ(0, srv->priority);
210  EXPECT_EQ(5, srv->weight);
211  EXPECT_EQ(5678, srv->port);
212  EXPECT_EQ(nullptr, srv->next);
213 
214  ares_free_data(srv0);
215 }
216 
217 TEST_F(LibraryTest, ParseSrvReplyErrors) {
218  DNSPacket pkt;
219  pkt.set_qid(0x1234).set_response().set_aa()
220  .add_question(new DNSQuestion("example.abc.def.com", T_SRV))
221  .add_answer(new DNSSrvRR("example.abc.def.com", 180, 0, 10, 8160, "example.abc.def.com"));
222  std::vector<byte> data;
223  struct ares_srv_reply* srv = nullptr;
224 
225  // No question.
226  pkt.questions_.clear();
227  data = pkt.data();
228  EXPECT_EQ(ARES_EBADRESP, ares_parse_srv_reply(data.data(), data.size(), &srv));
229  pkt.add_question(new DNSQuestion("example.abc.def.com", T_SRV));
230 
231 #ifdef DISABLED
232  // Question != answer
233  pkt.questions_.clear();
234  pkt.add_question(new DNSQuestion("Axample.com", T_SRV));
235  data = pkt.data();
236  EXPECT_EQ(ARES_ENODATA, ares_parse_srv_reply(data.data(), data.size(), &srv));
237  pkt.questions_.clear();
238  pkt.add_question(new DNSQuestion("example.com", T_SRV));
239 #endif
240 
241  // Two questions.
242  pkt.add_question(new DNSQuestion("example.abc.def.com", T_SRV));
243  data = pkt.data();
244  EXPECT_EQ(ARES_EBADRESP, ares_parse_srv_reply(data.data(), data.size(), &srv));
245  pkt.questions_.clear();
246  pkt.add_question(new DNSQuestion("64.48.32.16.in-addr.arpa", T_PTR));
247 
248  // Wrong sort of answer.
249  pkt.answers_.clear();
250  pkt.add_answer(new DNSMxRR("example.com", 100, 100, "mx1.example.com"));
251  data = pkt.data();
252  EXPECT_EQ(ARES_SUCCESS, ares_parse_srv_reply(data.data(), data.size(), &srv));
253  EXPECT_EQ(nullptr, srv);
254  pkt.answers_.clear();
255  pkt.add_answer(new DNSSrvRR("example.abc.def.com", 180, 0, 10, 8160, "example.abc.def.com"));
256 
257  // No answer.
258  pkt.answers_.clear();
259  data = pkt.data();
260  EXPECT_EQ(ARES_ENODATA, ares_parse_srv_reply(data.data(), data.size(), &srv));
261  pkt.add_answer(new DNSSrvRR("example.abc.def.com", 180, 0, 10, 8160, "example.abc.def.com"));
262 
263  // Truncated packets.
264  data = pkt.data();
265  for (size_t len = 1; len < data.size(); len++) {
266  int rc = ares_parse_srv_reply(data.data(), len, &srv);
267  EXPECT_TRUE(rc == ARES_EBADRESP || rc == ARES_EBADNAME);
268  }
269 }
270 
271 TEST_F(LibraryTest, ParseSrvReplyAllocFail) {
272  DNSPacket pkt;
273  pkt.set_qid(0x1234).set_response().set_aa()
274  .add_question(new DNSQuestion("example.abc.def.com", T_SRV))
275  .add_answer(new DNSCnameRR("example.com", 300, "c.example.com"))
276  .add_answer(new DNSSrvRR("example.abc.def.com", 180, 0, 10, 8160, "example.abc.def.com"));
277  std::vector<byte> data = pkt.data();
278  struct ares_srv_reply* srv = nullptr;
279 
280  for (int ii = 1; ii <= 5; ii++) {
281  ClearFails();
282  SetAllocFail(ii);
283  EXPECT_EQ(ARES_ENOMEM, ares_parse_srv_reply(data.data(), data.size(), &srv)) << ii;
284  }
285 }
286 
287 } // namespace test
288 } // namespace ares
ASSERT_NE
#define ASSERT_NE(val1, val2)
Definition: bloaty/third_party/googletest/googletest/include/gtest/gtest.h:2060
ARES_ENOMEM
#define ARES_ENOMEM
Definition: ares.h:117
ares::DNSPacket
Definition: dns-proto.h:188
ares::DNSPacket::set_aa
DNSPacket & set_aa(bool v=true)
Definition: dns-proto.h:213
T_SRV
#define T_SRV
Definition: ares_nameser.h:406
ares_srv_reply::weight
unsigned short weight
Definition: ares.h:543
test
Definition: spinlock_test.cc:36
testing::internal::string
::std::string string
Definition: bloaty/third_party/protobuf/third_party/googletest/googletest/include/gtest/internal/gtest-port.h:881
ares::DNSPacket::set_qid
DNSPacket & set_qid(int qid)
Definition: dns-proto.h:211
ares::DNSPacket::add_auth
DNSPacket & add_auth(DNSRR *q)
Definition: dns-proto.h:202
ares::DNSPacket::answers_
std::vector< std::unique_ptr< DNSRR > > answers_
Definition: dns-proto.h:237
ares_srv_reply::port
unsigned short port
Definition: ares.h:544
ares_srv_reply
Definition: ares.h:539
EXPECT_EQ
#define EXPECT_EQ(a, b)
Definition: iomgr/time_averaged_stats_test.cc:27
ares::DNSPacket::add_question
DNSPacket & add_question(DNSQuestion *q)
Definition: dns-proto.h:194
ares_srv_reply::host
char * host
Definition: ares.h:541
ares::DNSPacket::set_rd
DNSPacket & set_rd(bool v=true)
Definition: dns-proto.h:215
ARES_EBADRESP
#define ARES_EBADRESP
Definition: ares.h:112
ares::DNSCnameRR
Definition: dns-proto.h:100
EXPECT_NE
#define EXPECT_NE(val1, val2)
Definition: bloaty/third_party/googletest/googletest/include/gtest/gtest.h:2028
ARES_ENODATA
#define ARES_ENODATA
Definition: ares.h:101
ares::DNSPacket::set_ra
DNSPacket & set_ra(bool v=true)
Definition: dns-proto.h:216
ares::DNSPacket::add_additional
DNSPacket & add_additional(DNSRR *q)
Definition: dns-proto.h:206
ares::DNSSrvRR
Definition: dns-proto.h:130
ares_srv_reply::priority
unsigned short priority
Definition: ares.h:542
ares::DNSPacket::data
std::vector< byte > data() const
Definition: dns-proto.cc:592
data
char data[kBufferLength]
Definition: abseil-cpp/absl/strings/internal/str_format/float_conversion.cc:1006
ARES_EBADNAME
#define ARES_EBADNAME
Definition: ares.h:110
ares-test.h
ARES_SUCCESS
#define ARES_SUCCESS
Definition: ares.h:98
ares_srv_reply::next
struct ares_srv_reply * next
Definition: ares.h:540
ares::DNSPacket::add_answer
DNSPacket & add_answer(DNSRR *q)
Definition: dns-proto.h:198
ares::DNSPacket::questions_
std::vector< std::unique_ptr< DNSQuestion > > questions_
Definition: dns-proto.h:236
ares_free_data
CARES_EXTERN void ares_free_data(void *dataptr)
Definition: ares_data.c:41
ares::DNSPacket::set_response
DNSPacket & set_response(bool v=true)
Definition: dns-proto.h:212
ares_parse_srv_reply
CARES_EXTERN int ares_parse_srv_reply(const unsigned char *abuf, int alen, struct ares_srv_reply **srv_out)
Definition: ares_parse_srv_reply.c:38
ares::DNSARR
Definition: dns-proto.h:78
EXPECT_TRUE
#define EXPECT_TRUE(condition)
Definition: bloaty/third_party/googletest/googletest/include/gtest/gtest.h:1967
ares::DNSNsRR
Definition: dns-proto.h:105
ares::DNSMxRR
Definition: dns-proto.h:122
len
int len
Definition: abseil-cpp/absl/base/internal/low_level_alloc_test.cc:46
ares::test::TEST_F
TEST_F(LibraryTest, OptionsChannelInit)
Definition: ares-test-init.cc:55
T_PTR
#define T_PTR
Definition: ares_nameser.h:343
ares::DNSQuestion
Definition: dns-proto.h:45
ares
Definition: ares-test-ai.h:9
ares::test::LibraryTest
Definition: ares-test.h:60
ASSERT_EQ
#define ASSERT_EQ(val1, val2)
Definition: bloaty/third_party/googletest/googletest/include/gtest/gtest.h:2056
dns-proto.h


grpc
Author(s):
autogenerated on Fri May 16 2025 02:57:43