ares-test.cc
Go to the documentation of this file.
1 #include "ares_setup.h"
2 #include "ares.h"
3 #include "ares_nameser.h"
4 #include "ares-test.h"
5 #include "ares-test-ai.h"
6 #include "dns-proto.h"
7 
8 // Include ares internal files for DNS protocol details
9 #include "ares_dns.h"
10 
11 #ifdef HAVE_NETDB_H
12 #include <netdb.h>
13 #endif
14 #ifdef HAVE_NETINET_TCP_H
15 #include <netinet/tcp.h>
16 #endif
17 #include <stdio.h>
18 #include <stdlib.h>
19 
20 #include <functional>
21 #include <sstream>
22 
23 #ifdef WIN32
24 #define BYTE_CAST (char *)
25 #define mkdir_(d, p) mkdir(d)
26 #else
27 #define BYTE_CAST
28 #define mkdir_(d, p) mkdir(d, p)
29 #endif
30 
31 namespace ares {
32 namespace test {
33 
34 bool verbose = false;
35 static constexpr int dynamic_port = 0;
37 
38 const std::vector<int> both_families = {AF_INET, AF_INET6};
39 const std::vector<int> ipv4_family = {AF_INET};
40 const std::vector<int> ipv6_family = {AF_INET6};
41 
42 const std::vector<std::pair<int, bool>> both_families_both_modes = {
43  std::make_pair<int, bool>(AF_INET, false),
44  std::make_pair<int, bool>(AF_INET, true),
45  std::make_pair<int, bool>(AF_INET6, false),
46  std::make_pair<int, bool>(AF_INET6, true)
47 };
48 const std::vector<std::pair<int, bool>> ipv4_family_both_modes = {
49  std::make_pair<int, bool>(AF_INET, false),
50  std::make_pair<int, bool>(AF_INET, true)
51 };
52 const std::vector<std::pair<int, bool>> ipv6_family_both_modes = {
53  std::make_pair<int, bool>(AF_INET6, false),
54  std::make_pair<int, bool>(AF_INET6, true)
55 };
56 
57 // Which parameters to use in tests
58 std::vector<int> families = both_families;
59 std::vector<std::pair<int, bool>> families_modes = both_families_both_modes;
60 
61 unsigned long long LibraryTest::fails_ = 0;
62 std::map<size_t, int> LibraryTest::size_fails_;
63 
65  std::function<std::set<int>()> get_extrafds,
66  std::function<void(int)> process_extra) {
67  int nfds, count;
68  fd_set readers, writers;
69  struct timeval tv;
70  while (true) {
71  // Retrieve the set of file descriptors that the library wants us to monitor.
72  FD_ZERO(&readers);
73  FD_ZERO(&writers);
74  nfds = ares_fds(channel, &readers, &writers);
75  if (nfds == 0) // no work left to do in the library
76  return;
77 
78  // Add in the extra FDs if present.
79  std::set<int> extrafds = get_extrafds();
80  for (int extrafd : extrafds) {
81  FD_SET(extrafd, &readers);
82  if (extrafd >= nfds) {
83  nfds = extrafd + 1;
84  }
85  }
86 
87  // Wait for activity or timeout.
88  tv.tv_sec = 0;
89  tv.tv_usec = 100000; // 100ms
90  count = select(nfds, &readers, &writers, nullptr, &tv);
91  if (count < 0) {
92  fprintf(stderr, "select() failed, errno %d\n", errno);
93  return;
94  }
95 
96  // Let the library process any activity.
97  ares_process(channel, &readers, &writers);
98 
99  // Let the provided callback process any activity on the extra FD.
100  for (int extrafd : extrafds) {
101  if (FD_ISSET(extrafd, &readers)) {
102  process_extra(extrafd);
103  }
104  }
105  }
106 }
107 
108 // static
110  assert(nth > 0);
111  assert(nth <= (int)(8 * sizeof(fails_)));
112  fails_ |= (1LL << (nth - 1));
113 }
114 
115 // static
117  size_fails_[size]++;
118 }
119 
120 // static
122  fails_ = 0;
123  size_fails_.clear();
124 }
125 
126 
127 // static
129  bool fail = (fails_ & 0x01);
130  fails_ >>= 1;
131  if (size_fails_[size] > 0) {
132  size_fails_[size]--;
133  fail = true;
134  }
135  return fail;
136 }
137 
138 // static
139 void* LibraryTest::amalloc(size_t size) {
140  if (ShouldAllocFail(size) || size == 0) {
141  if (verbose) std::cerr << "Failing malloc(" << size << ") request" << std::endl;
142  return nullptr;
143  } else {
144  return malloc(size);
145  }
146 }
147 
148 // static
149 void* LibraryTest::arealloc(void *ptr, size_t size) {
150  if (ShouldAllocFail(size)) {
151  if (verbose) std::cerr << "Failing realloc(" << ptr << ", " << size << ") request" << std::endl;
152  return nullptr;
153  } else {
154  return realloc(ptr, size);
155  }
156 }
157 
158 // static
159 void LibraryTest::afree(void *ptr) {
160  free(ptr);
161 }
162 
163 std::set<int> NoExtraFDs() {
164  return std::set<int>();
165 }
166 
168  ProcessWork(channel_, NoExtraFDs, nullptr);
169 }
170 
172  ProcessWork(channel_, NoExtraFDs, nullptr);
173 }
174 
175 MockServer::MockServer(int family, int port)
176  : udpport_(port), tcpport_(port), qid_(-1) {
177  // Create a TCP socket to receive data on.
178  tcpfd_ = socket(family, SOCK_STREAM, 0);
179  EXPECT_NE(-1, tcpfd_);
180  int optval = 1;
181  setsockopt(tcpfd_, SOL_SOCKET, SO_REUSEADDR,
182  BYTE_CAST &optval , sizeof(int));
183  // Send TCP data right away.
184  setsockopt(tcpfd_, IPPROTO_TCP, TCP_NODELAY,
185  BYTE_CAST &optval , sizeof(int));
186 
187  // Create a UDP socket to receive data on.
188  udpfd_ = socket(family, SOCK_DGRAM, 0);
189  EXPECT_NE(-1, udpfd_);
190 
191  // Bind the sockets to the given port.
192  if (family == AF_INET) {
193  struct sockaddr_in addr;
194  memset(&addr, 0, sizeof(addr));
195  addr.sin_family = AF_INET;
196  addr.sin_addr.s_addr = htonl(INADDR_ANY);
197  addr.sin_port = htons(tcpport_);
198  int tcprc = bind(tcpfd_, (struct sockaddr*)&addr, sizeof(addr));
199  EXPECT_EQ(0, tcprc) << "Failed to bind AF_INET to TCP port " << tcpport_;
200  addr.sin_port = htons(udpport_);
201  int udprc = bind(udpfd_, (struct sockaddr*)&addr, sizeof(addr));
202  EXPECT_EQ(0, udprc) << "Failed to bind AF_INET to UDP port " << udpport_;
203  // retrieve system-assigned port
204  if (udpport_ == dynamic_port) {
205  ares_socklen_t len = sizeof(addr);
206  auto result = getsockname(udpfd_, (struct sockaddr*)&addr, &len);
207  EXPECT_EQ(0, result);
208  udpport_ = ntohs(addr.sin_port);
210  }
211  if (tcpport_ == dynamic_port) {
212  ares_socklen_t len = sizeof(addr);
213  auto result = getsockname(tcpfd_, (struct sockaddr*)&addr, &len);
214  EXPECT_EQ(0, result);
215  tcpport_ = ntohs(addr.sin_port);
217  }
218  } else {
219  EXPECT_EQ(AF_INET6, family);
220  struct sockaddr_in6 addr;
221  memset(&addr, 0, sizeof(addr));
222  addr.sin6_family = AF_INET6;
223  memset(&addr.sin6_addr, 0, sizeof(addr.sin6_addr)); // in6addr_any
224  addr.sin6_port = htons(tcpport_);
225  int tcprc = bind(tcpfd_, (struct sockaddr*)&addr, sizeof(addr));
226  EXPECT_EQ(0, tcprc) << "Failed to bind AF_INET6 to TCP port " << tcpport_;
227  addr.sin6_port = htons(udpport_);
228  int udprc = bind(udpfd_, (struct sockaddr*)&addr, sizeof(addr));
229  EXPECT_EQ(0, udprc) << "Failed to bind AF_INET6 to UDP port " << udpport_;
230  // retrieve system-assigned port
231  if (udpport_ == dynamic_port) {
232  ares_socklen_t len = sizeof(addr);
233  auto result = getsockname(udpfd_, (struct sockaddr*)&addr, &len);
234  EXPECT_EQ(0, result);
235  udpport_ = ntohs(addr.sin6_port);
237  }
238  if (tcpport_ == dynamic_port) {
239  ares_socklen_t len = sizeof(addr);
240  auto result = getsockname(tcpfd_, (struct sockaddr*)&addr, &len);
241  EXPECT_EQ(0, result);
242  tcpport_ = ntohs(addr.sin6_port);
244  }
245  }
246  if (verbose) std::cerr << "Configured "
247  << (family == AF_INET ? "IPv4" : "IPv6")
248  << " mock server with TCP socket " << tcpfd_
249  << " on port " << tcpport_
250  << " and UDP socket " << udpfd_
251  << " on port " << udpport_ << std::endl;
252 
253  // For TCP, also need to listen for connections.
254  EXPECT_EQ(0, listen(tcpfd_, 5)) << "Failed to listen for TCP connections";
255 }
256 
258  for (int fd : connfds_) {
259  sclose(fd);
260  }
261  sclose(tcpfd_);
262  sclose(udpfd_);
263 }
264 
265 void MockServer::ProcessFD(int fd) {
266  if (fd != tcpfd_ && fd != udpfd_ && connfds_.find(fd) == connfds_.end()) {
267  // Not one of our FDs.
268  return;
269  }
270  if (fd == tcpfd_) {
271  int connfd = accept(tcpfd_, NULL, NULL);
272  if (connfd < 0) {
273  std::cerr << "Error accepting connection on fd " << fd << std::endl;
274  } else {
275  connfds_.insert(connfd);
276  }
277  return;
278  }
279 
280  // Activity on a data-bearing file descriptor.
281  struct sockaddr_storage addr;
282  socklen_t addrlen = sizeof(addr);
283  byte buffer[2048];
284  int len = recvfrom(fd, BYTE_CAST buffer, sizeof(buffer), 0,
285  (struct sockaddr *)&addr, &addrlen);
286  byte* data = buffer;
287  if (fd != udpfd_) {
288  if (len == 0) {
289  connfds_.erase(std::find(connfds_.begin(), connfds_.end(), fd));
290  sclose(fd);
291  return;
292  }
293  if (len < 2) {
294  std::cerr << "Packet too short (" << len << ")" << std::endl;
295  return;
296  }
297  int tcplen = (data[0] << 8) + data[1];
298  data += 2;
299  len -= 2;
300  if (tcplen != len) {
301  std::cerr << "Warning: TCP length " << tcplen
302  << " doesn't match remaining data length " << len << std::endl;
303  }
304  }
305 
306  // Assume the packet is a well-formed DNS request and extract the request
307  // details.
308  if (len < NS_HFIXEDSZ) {
309  std::cerr << "Packet too short (" << len << ")" << std::endl;
310  return;
311  }
312  int qid = DNS_HEADER_QID(data);
313  if (DNS_HEADER_QR(data) != 0) {
314  std::cerr << "Not a request" << std::endl;
315  return;
316  }
317  if (DNS_HEADER_OPCODE(data) != O_QUERY) {
318  std::cerr << "Not a query (opcode " << DNS_HEADER_OPCODE(data)
319  << ")" << std::endl;
320  return;
321  }
322  if (DNS_HEADER_QDCOUNT(data) != 1) {
323  std::cerr << "Unexpected question count (" << DNS_HEADER_QDCOUNT(data)
324  << ")" << std::endl;
325  return;
326  }
327  byte* question = data + 12;
328  int qlen = len - 12;
329 
330  char *name = nullptr;
331  long enclen;
332  ares_expand_name(question, data, len, &name, &enclen);
333  if (!name) {
334  std::cerr << "Failed to retrieve name" << std::endl;
335  return;
336  }
337  qlen -= enclen;
338  question += enclen;
339  std::string namestr(name);
341 
342  if (qlen < 4) {
343  std::cerr << "Unexpected question size (" << qlen
344  << " bytes after name)" << std::endl;
345  return;
346  }
347  if (DNS_QUESTION_CLASS(question) != C_IN) {
348  std::cerr << "Unexpected question class (" << DNS_QUESTION_CLASS(question)
349  << ")" << std::endl;
350  return;
351  }
352  int rrtype = DNS_QUESTION_TYPE(question);
353 
354  if (verbose) {
355  std::vector<byte> req(data, data + len);
356  std::cerr << "received " << (fd == udpfd_ ? "UDP" : "TCP") << " request " << PacketToString(req)
357  << " on port " << (fd == udpfd_ ? udpport_ : tcpport_) << std::endl;
358  std::cerr << "ProcessRequest(" << qid << ", '" << namestr
359  << "', " << RRTypeToString(rrtype) << ")" << std::endl;
360  }
361  ProcessRequest(fd, &addr, addrlen, qid, namestr, rrtype);
362 }
363 
364 std::set<int> MockServer::fds() const {
365  std::set<int> result = connfds_;
366  result.insert(tcpfd_);
367  result.insert(udpfd_);
368  return result;
369 }
370 
371 void MockServer::ProcessRequest(int fd, struct sockaddr_storage* addr, int addrlen,
372  int qid, const std::string& name, int rrtype) {
373  // Before processing, let gMock know the request is happening.
374  OnRequest(name, rrtype);
375 
376  if (reply_.size() == 0) {
377  return;
378  }
379 
380  // Make a local copy of the current pending reply.
381  std::vector<byte> reply = reply_;
382 
383  if (qid_ >= 0) {
384  // Use the explicitly specified query ID.
385  qid = qid_;
386  }
387  if (reply.size() >= 2) {
388  // Overwrite the query ID if space to do so.
389  reply[0] = (byte)((qid >> 8) & 0xff);
390  reply[1] = (byte)(qid & 0xff);
391  }
392  if (verbose) std::cerr << "sending reply " << PacketToString(reply)
393  << " on port " << ((fd == udpfd_) ? udpport_ : tcpport_) << std::endl;
394 
395  // Prefix with 2-byte length if TCP.
396  if (fd != udpfd_) {
397  int len = reply.size();
398  std::vector<byte> vlen = {(byte)((len & 0xFF00) >> 8), (byte)(len & 0xFF)};
399  reply.insert(reply.begin(), vlen.begin(), vlen.end());
400  // Also, don't bother with the destination address.
401  addr = nullptr;
402  addrlen = 0;
403  }
404 
405  int rc = sendto(fd, BYTE_CAST reply.data(), reply.size(), 0,
406  (struct sockaddr *)addr, addrlen);
407  if (rc < static_cast<int>(reply.size())) {
408  std::cerr << "Failed to send full reply, rc=" << rc << std::endl;
409  }
410 }
411 
412 // static
415  assert(count > 0);
416  for (int ii = 0; ii < count; ii++) {
417  int port = base_port == dynamic_port ? dynamic_port : base_port + ii;
418  std::unique_ptr<NiceMockServer> server(new NiceMockServer(family, port));
419  servers.push_back(std::move(server));
420  }
421  return servers;
422 }
423 
425  int family,
426  bool force_tcp,
427  struct ares_options* givenopts,
428  int optmask)
429  : servers_(BuildServers(count, family, mock_port)),
430  server_(*servers_[0].get()), channel_(nullptr) {
431  // Set up channel options.
432  struct ares_options opts;
433  if (givenopts) {
434  memcpy(&opts, givenopts, sizeof(opts));
435  } else {
436  memset(&opts, 0, sizeof(opts));
437  }
438 
439  // Point the library at the first mock server by default (overridden below).
440  opts.udp_port = server_.udpport();
441  optmask |= ARES_OPT_UDP_PORT;
442  opts.tcp_port = server_.tcpport();
443  optmask |= ARES_OPT_TCP_PORT;
444 
445  // If not already overridden, set short-ish timeouts.
446  if (!(optmask & (ARES_OPT_TIMEOUTMS|ARES_OPT_TIMEOUT))) {
447  opts.timeout = 1500;
448  optmask |= ARES_OPT_TIMEOUTMS;
449  }
450  // If not already overridden, set 3 retries.
451  if (!(optmask & ARES_OPT_TRIES)) {
452  opts.tries = 3;
453  optmask |= ARES_OPT_TRIES;
454  }
455  // If not already overridden, set search domains.
456  const char *domains[3] = {"first.com", "second.org", "third.gov"};
457  if (!(optmask & ARES_OPT_DOMAINS)) {
458  opts.ndomains = 3;
459  opts.domains = (char**)domains;
460  optmask |= ARES_OPT_DOMAINS;
461  }
462  if (force_tcp) {
463  opts.flags |= ARES_FLAG_USEVC;
464  optmask |= ARES_OPT_FLAGS;
465  }
466 
468  EXPECT_NE(nullptr, channel_);
469 
470  // Set up servers after construction so we can set individual ports
471  struct ares_addr_port_node* prev = nullptr;
472  struct ares_addr_port_node* first = nullptr;
473  for (const auto& server : servers_) {
474  struct ares_addr_port_node* node = (struct ares_addr_port_node*)malloc(sizeof(*node));
475  if (prev) {
476  prev->next = node;
477  } else {
478  first = node;
479  }
480  node->next = nullptr;
481  node->family = family;
482  node->udp_port = server->udpport();
483  node->tcp_port = server->tcpport();
484  if (family == AF_INET) {
485  node->addr.addr4.s_addr = htonl(0x7F000001);
486  } else {
487  memset(&node->addr.addr6, 0, sizeof(node->addr.addr6));
488  node->addr.addr6._S6_un._S6_u8[15] = 1;
489  }
490  prev = node;
491  }
493 
494  while (first) {
495  prev = first;
496  first = first->next;
497  free(prev);
498  }
499  if (verbose) {
500  std::cerr << "Configured library with servers:";
501  std::vector<std::string> servers = GetNameServers(channel_);
502  for (const auto& server : servers) {
503  std::cerr << " " << server;
504  }
505  std::cerr << std::endl;
506  }
507 }
508 
510  if (channel_) {
512  }
513  channel_ = nullptr;
514 }
515 
516 std::set<int> MockChannelOptsTest::fds() const {
517  std::set<int> fds;
518  for (const auto& server : servers_) {
519  std::set<int> serverfds = server->fds();
520  fds.insert(serverfds.begin(), serverfds.end());
521  }
522  return fds;
523 }
524 
526  for (auto& server : servers_) {
527  server->ProcessFD(fd);
528  }
529 }
530 
532  using namespace std::placeholders;
534  std::bind(&MockChannelOptsTest::fds, this),
535  std::bind(&MockChannelOptsTest::ProcessFD, this, _1));
536 }
537 
538 std::ostream& operator<<(std::ostream& os, const HostResult& result) {
539  os << '{';
540  if (result.done_) {
541  os << StatusToString(result.status_) << " " << result.host_;
542  } else {
543  os << "(incomplete)";
544  }
545  os << '}';
546  return os;
547 }
548 
549 HostEnt::HostEnt(const struct hostent *hostent) : addrtype_(-1) {
550  if (!hostent)
551  return;
552  if (hostent->h_name)
553  name_ = hostent->h_name;
554  if (hostent->h_aliases) {
555  char** palias = hostent->h_aliases;
556  while (*palias != nullptr) {
557  aliases_.push_back(*palias);
558  palias++;
559  }
560  }
561  addrtype_ = hostent->h_addrtype;
562  if (hostent->h_addr_list) {
563  char** paddr = hostent->h_addr_list;
564  while (*paddr != nullptr) {
565  std::string addr = AddressToString(*paddr, hostent->h_length);
566  addrs_.push_back(addr);
567  paddr++;
568  }
569  }
570 }
571 
572 std::ostream& operator<<(std::ostream& os, const HostEnt& host) {
573  os << '{';
574  os << "'" << host.name_ << "' "
575  << "aliases=[";
576  for (size_t ii = 0; ii < host.aliases_.size(); ii++) {
577  if (ii > 0) os << ", ";
578  os << host.aliases_[ii];
579  }
580  os << "] ";
581  os << "addrs=[";
582  for (size_t ii = 0; ii < host.addrs_.size(); ii++) {
583  if (ii > 0) os << ", ";
584  os << host.addrs_[ii];
585  }
586  os << "]";
587  os << '}';
588  return os;
589 }
590 
591 void HostCallback(void *data, int status, int timeouts,
592  struct hostent *hostent) {
593  EXPECT_NE(nullptr, data);
594  HostResult* result = reinterpret_cast<HostResult*>(data);
595  result->done_ = true;
596  result->status_ = status;
597  result->timeouts_ = timeouts;
598  result->host_ = HostEnt(hostent);
599  if (verbose) std::cerr << "HostCallback(" << *result << ")" << std::endl;
600 }
601 
602 std::ostream& operator<<(std::ostream& os, const AddrInfoResult& result) {
603  os << '{';
604  if (result.done_ && result.ai_) {
605  os << StatusToString(result.status_) << " " << result.ai_;
606  } else {
607  os << "(incomplete)";
608  }
609  os << '}';
610  return os;
611 }
612 
613 std::ostream& operator<<(std::ostream& os, const AddrInfo& ai) {
614  os << '{';
615  if (ai == nullptr) {
616  os << "nullptr}";
617  return os;
618  }
619 
620  struct ares_addrinfo_cname *next_cname = ai->cnames;
621  while(next_cname) {
622  if(next_cname->alias) {
623  os << next_cname->alias << "->";
624  }
625  if(next_cname->name) {
626  os << next_cname->name;
627  }
628  if((next_cname = next_cname->next))
629  os << ", ";
630  else
631  os << " ";
632  }
633 
634  struct ares_addrinfo_node *next = ai->nodes;
635  while(next) {
636  //if(next->ai_canonname) {
637  //os << "'" << next->ai_canonname << "' ";
638  //}
639  unsigned short port = 0;
640  os << "addr=[";
641  if(next->ai_family == AF_INET) {
642  sockaddr_in* sin = (sockaddr_in*)next->ai_addr;
643  port = ntohs(sin->sin_port);
644  os << AddressToString(&sin->sin_addr, 4);
645  }
646  else if (next->ai_family == AF_INET6) {
647  sockaddr_in6* sin = (sockaddr_in6*)next->ai_addr;
648  port = ntohs(sin->sin6_port);
649  os << "[" << AddressToString(&sin->sin6_addr, 16) << "]";
650  }
651  else
652  os << "unknown family";
653  if(port) {
654  os << ":" << port;
655  }
656  os << "]";
657  if((next = next->ai_next))
658  os << ", ";
659  }
660  os << '}';
661  return os;
662 }
663 
664 void AddrInfoCallback(void *data, int status, int timeouts,
665  struct ares_addrinfo *ai) {
666  EXPECT_NE(nullptr, data);
667  AddrInfoResult* result = reinterpret_cast<AddrInfoResult*>(data);
668  result->done_ = true;
669  result->status_ = status;
670  result->timeouts_= timeouts;
671  result->ai_ = AddrInfo(ai);
672  if (verbose) std::cerr << "AddrInfoCallback(" << *result << ")" << std::endl;
673 }
674 
675 std::ostream& operator<<(std::ostream& os, const SearchResult& result) {
676  os << '{';
677  if (result.done_) {
678  os << StatusToString(result.status_) << " " << PacketToString(result.data_);
679  } else {
680  os << "(incomplete)";
681  }
682  os << '}';
683  return os;
684 }
685 
686 void SearchCallback(void *data, int status, int timeouts,
687  unsigned char *abuf, int alen) {
688  EXPECT_NE(nullptr, data);
689  SearchResult* result = reinterpret_cast<SearchResult*>(data);
690  result->done_ = true;
691  result->status_ = status;
692  result->timeouts_ = timeouts;
693  result->data_.assign(abuf, abuf + alen);
694  if (verbose) std::cerr << "SearchCallback(" << *result << ")" << std::endl;
695 }
696 
697 std::ostream& operator<<(std::ostream& os, const NameInfoResult& result) {
698  os << '{';
699  if (result.done_) {
700  os << StatusToString(result.status_) << " " << result.node_ << " " << result.service_;
701  } else {
702  os << "(incomplete)";
703  }
704  os << '}';
705  return os;
706 }
707 
708 void NameInfoCallback(void *data, int status, int timeouts,
709  char *node, char *service) {
710  EXPECT_NE(nullptr, data);
711  NameInfoResult* result = reinterpret_cast<NameInfoResult*>(data);
712  result->done_ = true;
713  result->status_ = status;
714  result->timeouts_ = timeouts;
715  result->node_ = std::string(node ? node : "");
716  result->service_ = std::string(service ? service : "");
717  if (verbose) std::cerr << "NameInfoCallback(" << *result << ")" << std::endl;
718 }
719 
720 std::vector<std::string> GetNameServers(ares_channel channel) {
721  struct ares_addr_port_node* servers = nullptr;
724  std::vector<std::string> results;
725  while (server) {
726  std::stringstream ss;
727  switch (server->family) {
728  case AF_INET:
729  ss << AddressToString((char*)&server->addr.addr4, 4);
730  break;
731  case AF_INET6:
732  if (server->udp_port != 0) {
733  ss << '[';
734  }
735  ss << AddressToString((char*)&server->addr.addr6, 16);
736  if (server->udp_port != 0) {
737  ss << ']';
738  }
739  break;
740  default:
741  results.push_back("<unknown family>");
742  break;
743  }
744  if (server->udp_port != 0) {
745  ss << ":" << server->udp_port;
746  }
747  results.push_back(ss.str());
748  server = server->next;
749  }
751  return results;
752 }
753 
754 TransientDir::TransientDir(const std::string& dirname) : dirname_(dirname) {
755  if (mkdir_(dirname_.c_str(), 0755) != 0) {
756  std::cerr << "Failed to create subdirectory '" << dirname_ << "'" << std::endl;
757  }
758 }
759 
761  rmdir(dirname_.c_str());
762 }
763 
765  const std::string& contents)
766  : filename_(filename) {
767  FILE *f = fopen(filename.c_str(), "w");
768  if (f == nullptr) {
769  std::cerr << "Error: failed to create '" << filename << "'" << std::endl;
770  return;
771  }
772  int rc = fwrite(contents.data(), 1, contents.size(), f);
773  if (rc != (int)contents.size()) {
774  std::cerr << "Error: failed to write contents of '" << filename << "'" << std::endl;
775  }
776  fclose(f);
777 }
778 
780  unlink(filename_.c_str());
781 }
782 
783 std::string TempNam(const char *dir, const char *prefix) {
784  char *p = tempnam(dir, prefix);
786  free(p);
787  return result;
788 }
789 
791  : TransientFile(TempNam(nullptr, "ares"), contents) {
792 
793 }
794 
796  : channel_(c)
797 {
799 }
800 
803 }
804 
805 } // namespace test
806 } // namespace ares
ptr
char * ptr
Definition: abseil-cpp/absl/base/internal/low_level_alloc_test.cc:45
ares::test::LibraryTest::ClearFails
static void ClearFails()
Definition: ares-test.cc:121
_gevent_test_main.result
result
Definition: _gevent_test_main.py:96
filename
const char * filename
Definition: bloaty/third_party/zlib/contrib/minizip/ioapi.h:135
ares_addrinfo_node
Definition: ares.h:593
ares::test::both_families
const std::vector< int > both_families
Definition: ares-test.cc:38
ares::test::DefaultChannelTest::Process
void Process()
Definition: ares-test.cc:167
get
absl::string_view get(const Cont &c)
Definition: abseil-cpp/absl/strings/str_replace_test.cc:185
ares::test::VirtualizeIO::default_functions
static const ares_socket_functions default_functions
Definition: ares-test.h:457
ares::test::MockChannelOptsTest::fds
std::set< int > fds() const
Definition: ares-test.cc:516
AF_INET6
#define AF_INET6
Definition: ares_setup.h:208
ares_options
Definition: ares.h:259
ares_process
CARES_EXTERN void ares_process(ares_channel channel, fd_set *read_fds, fd_set *write_fds)
Definition: ares_process.c:134
ares::test::AddrInfoResult
Definition: ares-test.h:294
ares::test::LibraryTest::afree
static void afree(void *ptr)
Definition: ares-test.cc:159
rmdir
#define rmdir
Definition: test-fs.c:45
find
static void ** find(grpc_chttp2_stream_map *map, uint32_t key)
Definition: stream_map.cc:99
ares_addrinfo
Definition: ares.h:616
memset
return memset(p, 0, total)
ares::test::AddrInfo
std::unique_ptr< ares_addrinfo, AddrInfoDeleter > AddrInfo
Definition: ares-test.h:289
ares::test::VirtualizeIO::channel_
ares_channel channel_
Definition: ares-test.h:459
ares::test::LibraryTest::SetAllocFail
static void SetAllocFail(int nth)
Definition: ares-test.cc:109
ares.h
ares::test::ipv6_family
const std::vector< int > ipv6_family
Definition: ares-test.cc:40
ares::test::both_families_both_modes
const std::vector< std::pair< int, bool > > both_families_both_modes
Definition: ares-test.cc:42
test
Definition: spinlock_test.cc:36
ares_addr_port_node
Definition: ares.h:704
ARES_FLAG_USEVC
#define ARES_FLAG_USEVC
Definition: ares.h:142
ares_free_string
CARES_EXTERN void ares_free_string(void *str)
Definition: ares_free_string.c:22
ares::test::LibraryTest::SetAllocSizeFail
static void SetAllocSizeFail(size_t size)
Definition: ares-test.cc:116
ares::test::MockChannelOptsTest::NiceMockServers
std::vector< std::unique_ptr< NiceMockServer > > NiceMockServers
Definition: ares-test.h:187
testing::internal::string
::std::string string
Definition: bloaty/third_party/protobuf/third_party/googletest/googletest/include/gtest/internal/gtest-port.h:881
ares_addr_port_node::addr
union ares_addr_port_node::@383 addr
ares_addrinfo_cname::alias
char * alias
Definition: ares.h:611
ares_fds
CARES_EXTERN int ares_fds(ares_channel channel, fd_set *read_fds, fd_set *write_fds)
Definition: ares_fds.c:23
cstest_report.opts
opts
Definition: cstest_report.py:81
ares::test::MockServer::udpfd_
int udpfd_
Definition: ares-test.h:168
ARES_OPT_UDP_PORT
#define ARES_OPT_UDP_PORT
Definition: ares.h:157
ares_dns.h
ares_in6_addr::_S6_u8
unsigned char _S6_u8[16]
Definition: ares.h:516
status
absl::Status status
Definition: rls.cc:251
setup.name
name
Definition: setup.py:542
ARES_OPT_DOMAINS
#define ARES_OPT_DOMAINS
Definition: ares.h:160
DNS_HEADER_OPCODE
#define DNS_HEADER_OPCODE(h)
Definition: ares_dns.h:65
ARES_OPT_TIMEOUT
#define ARES_OPT_TIMEOUT
Definition: ares.h:154
xds_manager.p
p
Definition: xds_manager.py:60
ares::test::MockChannelOptsTest::servers_
NiceMockServers servers_
Definition: ares-test.h:194
ares::RRTypeToString
std::string RRTypeToString(int rrtype)
Definition: dns-proto.cc:84
ARES_OPT_TIMEOUTMS
#define ARES_OPT_TIMEOUTMS
Definition: ares.h:166
ares::test::MockServer::tcpfd_
int tcpfd_
Definition: ares-test.h:169
DNS_HEADER_QID
#define DNS_HEADER_QID(h)
Definition: ares_dns.h:63
ARES_OPT_FLAGS
#define ARES_OPT_FLAGS
Definition: ares.h:153
ares::test::dynamic_port
static constexpr int dynamic_port
Definition: ares-test.cc:35
ares::test::DefaultChannelModeTest::Process
void Process()
Definition: ares-test.cc:171
server_
Server *const server_
Definition: chttp2_server.cc:260
ares::test::MockServer::ProcessRequest
void ProcessRequest(int fd, struct sockaddr_storage *addr, int addrlen, int qid, const std::string &name, int rrtype)
Definition: ares-test.cc:371
ares::test::families
std::vector< int > families
Definition: ares-test.cc:58
python_utils.port_server.stderr
stderr
Definition: port_server.py:51
ares::test::MockChannelOptsTest::MockChannelOptsTest
MockChannelOptsTest(int count, int family, bool force_tcp, struct ares_options *givenopts, int optmask)
Definition: ares-test.cc:424
mkdir_
#define mkdir_(d, p)
Definition: ares-test.cc:28
EXPECT_EQ
#define EXPECT_EQ(a, b)
Definition: iomgr/time_averaged_stats_test.cc:27
ares::test::TempFile::TempFile
TempFile(const std::string &contents)
Definition: ares-test.cc:790
ares::test::MockChannelOptsTest::~MockChannelOptsTest
~MockChannelOptsTest()
Definition: ares-test.cc:509
ares::test::MockServer::udpport_
int udpport_
Definition: ares-test.h:166
ares_expand_name
CARES_EXTERN int ares_expand_name(const unsigned char *encoded, const unsigned char *abuf, int alen, char **s, long *enclen)
Definition: ares_expand_name.c:203
server
std::unique_ptr< Server > server
Definition: channelz_service_test.cc:330
memcpy
memcpy(mem, inblock.get(), min(CONTAINING_RECORD(inblock.get(), MEMBLOCK, data) ->size, size))
ares::test::mock_port
int mock_port
Definition: ares-test.cc:36
ares_set_socket_functions
CARES_EXTERN void ares_set_socket_functions(ares_channel channel, const struct ares_socket_functions *funcs, void *user_data)
Definition: ares_init.c:2606
DNS_QUESTION_CLASS
#define DNS_QUESTION_CLASS(q)
Definition: ares_dns.h:94
ares_addr_port_node::addr4
struct in_addr addr4
Definition: ares.h:708
c
void c(T a)
Definition: miscompile_with_no_unique_address_test.cc:40
channel
wrapped_grpc_channel * channel
Definition: src/php/ext/grpc/call.h:33
autogen_x86imm.f
f
Definition: autogen_x86imm.py:9
BYTE_CAST
#define BYTE_CAST
Definition: ares-test.cc:27
sclose
#define sclose(x)
Definition: setup_once.h:266
ares::AddressToString
std::string AddressToString(const void *vaddr, int len)
Definition: dns-proto.cc:157
absl::move
constexpr absl::remove_reference_t< T > && move(T &&t) noexcept
Definition: abseil-cpp/absl/utility/utility.h:221
sockaddr_in6
Definition: ares_ipv6.h:25
ares::test::MockChannelOptsTest::Process
void Process()
Definition: ares-test.cc:531
ares::test::TransientFile::filename_
std::string filename_
Definition: ares-test.h:341
absl::string_view::size
constexpr size_type size() const noexcept
Definition: abseil-cpp/absl/strings/string_view.h:277
sockaddr_in6::sin6_port
unsigned short sin6_port
Definition: ares_ipv6.h:28
O_QUERY
#define O_QUERY
Definition: ares_nameser.h:225
EXPECT_NE
#define EXPECT_NE(val1, val2)
Definition: bloaty/third_party/googletest/googletest/include/gtest/gtest.h:2028
DNS_HEADER_QR
#define DNS_HEADER_QR(h)
Definition: ares_dns.h:64
req
static uv_connect_t req
Definition: test-connection-fail.c:30
DNS_QUESTION_TYPE
#define DNS_QUESTION_TYPE(q)
Definition: ares_dns.h:93
ares::test::MockChannelOptsTest::server_
NiceMockServer & server_
Definition: ares-test.h:196
benchmarks.python.py_benchmark.results
list results
Definition: bloaty/third_party/protobuf/benchmarks/python/py_benchmark.py:145
ares::PacketToString
std::string PacketToString(const std::vector< byte > &packet)
Definition: dns-proto.cc:181
ares::test::TransientDir::~TransientDir
~TransientDir()
Definition: ares-test.cc:760
grpc_core::fail
Poll< absl::StatusOr< std::tuple< T... > > > fail()
Definition: try_join_test.cc:45
ares::test::MockServer::reply_
std::vector< byte > reply_
Definition: ares-test.h:171
ares::test::MockChannelOptsTest::NiceMockServer
testing::NiceMock< MockServer > NiceMockServer
Definition: ares-test.h:186
ares_addr_port_node::addr6
struct ares_in6_addr addr6
Definition: ares.h:709
ares::test::MockChannelOptsTest::BuildServers
static NiceMockServers BuildServers(int count, int family, int base_port)
Definition: ares-test.cc:413
ares::test::verbose
bool verbose
Definition: ares-test.cc:34
ares::test::SearchCallback
void SearchCallback(void *data, int status, int timeouts, unsigned char *abuf, int alen)
Definition: ares-test.cc:686
ares::test::NameInfoResult
Definition: ares-test.h:271
channel_
RefCountedPtr< Channel > channel_
Definition: channel_connectivity.cc:209
ares::test::DefaultChannelModeTest::channel_
ares_channel channel_
Definition: ares-test.h:133
ares::test::TempNam
std::string TempNam(const char *dir, const char *prefix)
Definition: ares-test.cc:783
data
char data[kBufferLength]
Definition: abseil-cpp/absl/strings/internal/str_format/float_conversion.cc:1006
buffer
char buffer[1024]
Definition: libuv/docs/code/idle-compute/main.c:8
ares-test-ai.h
ares::test::operator<<
std::ostream & operator<<(std::ostream &os, const HostResult &result)
Definition: ares-test.cc:538
ARES_OPT_TCP_PORT
#define ARES_OPT_TCP_PORT
Definition: ares.h:158
ares_addr_port_node::family
int family
Definition: ares.h:706
ares::test::HostEnt::name_
std::string name_
Definition: ares-test.h:240
ares-test.h
ARES_SUCCESS
#define ARES_SUCCESS
Definition: ares.h:98
DNS_HEADER_QDCOUNT
#define DNS_HEADER_QDCOUNT(h)
Definition: ares_dns.h:72
ares_setup.h
tests.unit._exit_scenarios.port
port
Definition: _exit_scenarios.py:179
ares_addrinfo_cname::next
struct ares_addrinfo_cname * next
Definition: ares.h:613
ares::test::LibraryTest::fails_
static unsigned long long fails_
Definition: ares-test.h:86
ares::test::MockServer::connfds_
std::set< int > connfds_
Definition: ares-test.h:170
ares::test::HostEnt
Definition: ares-test.h:237
ares::test::HostEnt::HostEnt
HostEnt()
Definition: ares-test.h:238
ares::test::HostEnt::aliases_
std::vector< std::string > aliases_
Definition: ares-test.h:241
ARES_OPT_TRIES
#define ARES_OPT_TRIES
Definition: ares.h:155
ares::byte
unsigned char byte
Definition: ares-test.h:33
contents
string_view contents
Definition: elf.cc:597
ares_channeldata
Definition: ares_private.h:266
ares_addrinfo_cname
Definition: ares.h:609
timeval::tv_sec
long tv_sec
Definition: setup_once.h:121
ares_free_data
CARES_EXTERN void ares_free_data(void *dataptr)
Definition: ares_data.c:41
ares_set_servers_ports
CARES_EXTERN int ares_set_servers_ports(ares_channel channel, struct ares_addr_port_node *servers)
Definition: ares_options.c:195
benchmark.FILE
FILE
Definition: benchmark.py:21
ares_get_servers_ports
CARES_EXTERN int ares_get_servers_ports(ares_channel channel, struct ares_addr_port_node **servers)
Definition: ares_options.c:86
ares::test::HostCallback
void HostCallback(void *data, int status, int timeouts, struct hostent *hostent)
Definition: ares-test.cc:591
timeval::tv_usec
long tv_usec
Definition: setup_once.h:122
C_IN
#define C_IN
Definition: ares_nameser.h:292
ares::test::LibraryTest::ShouldAllocFail
static bool ShouldAllocFail(size_t size)
Definition: ares-test.cc:128
ares::test::MockServer::~MockServer
~MockServer()
Definition: ares-test.cc:257
server
Definition: examples/python/async_streaming/server.py:1
NS_HFIXEDSZ
#define NS_HFIXEDSZ
Definition: ares_nameser.h:35
ares::test::VirtualizeIO::~VirtualizeIO
~VirtualizeIO()
Definition: ares-test.cc:801
count
int * count
Definition: bloaty/third_party/googletest/googlemock/test/gmock_stress_test.cc:96
http2_test_server.listen
def listen(endpoint, test_case)
Definition: http2_test_server.py:87
grpc::fclose
fclose(creds_file)
ares::test::families_modes
std::vector< std::pair< int, bool > > families_modes
Definition: ares-test.cc:59
timeval
Definition: setup_once.h:113
ares::test::ipv4_family
const std::vector< int > ipv4_family
Definition: ares-test.cc:39
ares::test::NameInfoCallback
void NameInfoCallback(void *data, int status, int timeouts, char *node, char *service)
Definition: ares-test.cc:708
ares_addr_port_node::next
struct ares_addr_port_node * next
Definition: ares.h:705
ares_destroy
CARES_EXTERN void ares_destroy(ares_channel channel)
Definition: ares_destroy.c:43
ares::test::TransientDir::TransientDir
TransientDir(const std::string &dirname)
Definition: ares-test.cc:754
ares::test::DefaultChannelTest::channel_
ares_channel channel_
Definition: ares-test.h:107
next
AllocList * next[kMaxLevel]
Definition: abseil-cpp/absl/base/internal/low_level_alloc.cc:100
ares::test::MockServer::MockServer
MockServer(int family, int port)
Definition: ares-test.cc:175
first
StrT first
Definition: cxa_demangle.cpp:4884
ares::test::ipv4_family_both_modes
const std::vector< std::pair< int, bool > > ipv4_family_both_modes
Definition: ares-test.cc:48
ares::test::LibraryTest::arealloc
static void * arealloc(void *ptr, size_t size)
Definition: ares-test.cc:149
prefix
static const char prefix[]
Definition: head_of_line_blocking.cc:28
ares::test::HostEnt::addrtype_
int addrtype_
Definition: ares-test.h:242
ares_addr_port_node::tcp_port
int tcp_port
Definition: ares.h:712
ares::test::VirtualizeIO::VirtualizeIO
VirtualizeIO(ares_channel)
Definition: ares-test.cc:795
ares::test::SearchResult
Definition: ares-test.h:260
ares::test::NoExtraFDs
std::set< int > NoExtraFDs()
Definition: ares-test.cc:163
unlink
#define unlink
Definition: test-fs-copyfile.c:33
ares::test::MockServer::tcpport_
int tcpport_
Definition: ares-test.h:167
ares::test::ProcessWork
void ProcessWork(ares_channel channel, std::function< std::set< int >()> get_extrafds, std::function< void(int)> process_extra)
Definition: ares-test.cc:64
sockaddr_in6::sin6_addr
struct ares_in6_addr sin6_addr
Definition: ares_ipv6.h:30
ares::test::HostResult
Definition: ares-test.h:248
ares::test::TransientFile
Definition: ares-test.h:335
ares::StatusToString
std::string StatusToString(int status)
Definition: dns-proto.cc:33
ares::test::MockChannelOptsTest::channel_
ares_channel channel_
Definition: ares-test.h:197
ares::test::LibraryTest::amalloc
static void * amalloc(size_t size)
Definition: ares-test.cc:139
ares::test::LibraryTest::size_fails_
static std::map< size_t, int > size_fails_
Definition: ares-test.h:87
test_server.socket
socket
Definition: test_server.py:65
ares_init_options
CARES_EXTERN int ares_init_options(ares_channel *channelptr, struct ares_options *options, int optmask)
Definition: ares_init.c:103
ares::test::MockServer::fds
std::set< int > fds() const
Definition: ares-test.cc:364
len
int len
Definition: abseil-cpp/absl/base/internal/low_level_alloc_test.cc:46
service
__attribute__((deprecated("Please use GRPCProtoMethod."))) @interface ProtoMethod NSString * service
Definition: ProtoMethod.h:25
ares_nameser.h
function
std::function< bool(GrpcTool *, int, const char **, const CliCredentials &, GrpcToolOutputCallback)> function
Definition: grpc_tool.cc:250
size
voidpf void uLong size
Definition: bloaty/third_party/zlib/contrib/minizip/ioapi.h:136
ares::test::MockServer::ProcessFD
void ProcessFD(int fd)
Definition: ares-test.cc:265
domains
std::vector< std::string > domains
Definition: xds_server_config_fetcher.cc:337
ares_addrinfo_cname::name
char * name
Definition: ares.h:612
ares::test::HostEnt::addrs_
std::vector< std::string > addrs_
Definition: ares-test.h:243
ares::test::MockServer::qid_
int qid_
Definition: ares-test.h:172
absl::string_view::data
constexpr const_pointer data() const noexcept
Definition: abseil-cpp/absl/strings/string_view.h:336
ares::test::AddrInfoCallback
void AddrInfoCallback(void *data, int status, int timeouts, struct ares_addrinfo *ai)
Definition: ares-test.cc:664
ares::test::GetNameServers
std::vector< std::string > GetNameServers(ares_channel channel)
Definition: ares-test.cc:720
ares::test::TransientFile::TransientFile
TransientFile(const std::string &filename, const std::string &contents)
Definition: ares-test.cc:764
ares::test::TransientDir::dirname_
std::string dirname_
Definition: ares-test.h:328
addr
struct sockaddr_in addr
Definition: libuv/docs/code/tcp-echo-server/main.c:10
ares::test::TransientFile::~TransientFile
~TransientFile()
Definition: ares-test.cc:779
ares
Definition: ares-test-ai.h:9
run_interop_tests.servers
servers
Definition: run_interop_tests.py:1288
ares_addr_port_node::udp_port
int udp_port
Definition: ares.h:711
LL
#define LL(x)
ares::test::ipv6_family_both_modes
const std::vector< std::pair< int, bool > > ipv6_family_both_modes
Definition: ares-test.cc:52
ares::test::MockChannelOptsTest::ProcessFD
void ProcessFD(int fd)
Definition: ares-test.cc:525
servers_
std::vector< std::unique_ptr< ServerData > > servers_
Definition: client_lb_end2end_test.cc:522
ares_in6_addr::_S6_un
union ares_in6_addr::@381 _S6_un
dns-proto.h


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