ares-test-parse-aaaa.cc (9201B)
1 /* MIT License 2 * 3 * Copyright (c) The c-ares project and its contributors 4 * 5 * Permission is hereby granted, free of charge, to any person obtaining a copy 6 * of this software and associated documentation files (the "Software"), to deal 7 * in the Software without restriction, including without limitation the rights 8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 * copies of the Software, and to permit persons to whom the Software is 10 * furnished to do so, subject to the following conditions: 11 * 12 * The above copyright notice and this permission notice (including the next 13 * paragraph) shall be included in all copies or substantial portions of the 14 * Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 * SOFTWARE. 23 * 24 * SPDX-License-Identifier: MIT 25 */ 26 #include "ares-test.h" 27 #include "dns-proto.h" 28 29 #include <sstream> 30 #include <vector> 31 32 namespace ares { 33 namespace test { 34 35 TEST_F(LibraryTest, ParseAaaaReplyOK) { 36 DNSPacket pkt; 37 pkt.set_qid(0x1234).set_response().set_aa() 38 .add_question(new DNSQuestion("example.com", T_AAAA)) 39 .add_answer(new DNSAaaaRR("example.com", 100, 40 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 41 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})) 42 .add_answer(new DNSARR("example.com", 0x01020304, {2,3,4,5})); 43 std::vector<byte> data = pkt.data(); 44 struct hostent *host = nullptr; 45 struct ares_addr6ttl info[5]; 46 int count = 5; 47 EXPECT_EQ(ARES_SUCCESS, ares_parse_aaaa_reply(data.data(), (int)data.size(), 48 &host, info, &count)); 49 EXPECT_EQ(1, count); 50 EXPECT_EQ(100, info[0].ttl); 51 EXPECT_EQ(0x01, info[0].ip6addr._S6_un._S6_u8[0]); 52 EXPECT_EQ(0x02, info[0].ip6addr._S6_un._S6_u8[4]); 53 ASSERT_NE(nullptr, host); 54 std::stringstream ss; 55 ss << HostEnt(host); 56 EXPECT_EQ("{'example.com' aliases=[] addrs=[0101:0101:0202:0202:0303:0303:0404:0404]}", ss.str()); 57 ares_free_hostent(host); 58 59 // Repeat without providing places to put the results 60 count = 0; 61 EXPECT_EQ(ARES_SUCCESS, ares_parse_aaaa_reply(data.data(), (int)data.size(), 62 nullptr, info, &count)); 63 } 64 65 TEST_F(LibraryTest, ParseAaaaReplyCname) { 66 DNSPacket pkt; 67 pkt.set_qid(0x1234).set_response().set_aa() 68 .add_question(new DNSQuestion("example.com", T_AAAA)) 69 .add_answer(new DNSCnameRR("example.com", 50, "c.example.com")) 70 .add_answer(new DNSAaaaRR("c.example.com", 100, 71 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 72 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})); 73 std::vector<byte> data = pkt.data(); 74 struct hostent *host = nullptr; 75 struct ares_addr6ttl info[5]; 76 int count = 5; 77 EXPECT_EQ(ARES_SUCCESS, ares_parse_aaaa_reply(data.data(), (int)data.size(), 78 &host, info, &count)); 79 EXPECT_EQ(1, count); 80 // CNAME TTL overrides AAAA TTL. 81 EXPECT_EQ(50, info[0].ttl); 82 EXPECT_EQ(0x01, info[0].ip6addr._S6_un._S6_u8[0]); 83 EXPECT_EQ(0x02, info[0].ip6addr._S6_un._S6_u8[4]); 84 ASSERT_NE(nullptr, host); 85 std::stringstream ss; 86 ss << HostEnt(host); 87 EXPECT_EQ("{'c.example.com' aliases=[example.com] addrs=[0101:0101:0202:0202:0303:0303:0404:0404]}", ss.str()); 88 ares_free_hostent(host); 89 90 // Repeat without providing a hostent 91 count = 5; 92 EXPECT_EQ(ARES_SUCCESS, ares_parse_aaaa_reply(data.data(), (int)data.size(), 93 nullptr, info, &count)); 94 EXPECT_EQ(1, count); 95 EXPECT_EQ(50, info[0].ttl); 96 EXPECT_EQ(0x01, info[0].ip6addr._S6_un._S6_u8[0]); 97 EXPECT_EQ(0x02, info[0].ip6addr._S6_un._S6_u8[4]); 98 } 99 100 TEST_F(LibraryTest, ParseAaaaReplyNoData) { 101 DNSPacket pkt; 102 pkt.set_qid(0x1234).set_response().set_aa() 103 .add_question(new DNSQuestion("example.com", T_AAAA)); 104 std::vector<byte> data = pkt.data(); 105 struct hostent *host = nullptr; 106 struct ares_addr6ttl info[2]; 107 int count = 2; 108 EXPECT_EQ(ARES_ENODATA, ares_parse_aaaa_reply(data.data(), (int)data.size(), 109 &host, info, &count)); 110 EXPECT_EQ(0, count); 111 EXPECT_EQ(nullptr, host); 112 113 // Again but with a CNAME. 114 pkt.add_answer(new DNSCnameRR("example.com", 200, "c.example.com")); 115 EXPECT_EQ(ARES_ENODATA, ares_parse_aaaa_reply(data.data(), (int)data.size(), 116 &host, info, &count)); 117 EXPECT_EQ(0, count); 118 EXPECT_EQ(nullptr, host); 119 } 120 121 TEST_F(LibraryTest, ParseAaaaReplyErrors) { 122 DNSPacket pkt; 123 pkt.set_qid(0x1234).set_response().set_aa() 124 .add_question(new DNSQuestion("example.com", T_AAAA)) 125 .add_answer(new DNSAaaaRR("example.com", 100, 126 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 127 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})); 128 std::vector<byte> data; 129 130 struct hostent *host = nullptr; 131 struct ares_addr6ttl info[2]; 132 int count = 2; 133 134 // No question. 135 pkt.questions_.clear(); 136 data = pkt.data(); 137 EXPECT_EQ(ARES_EBADRESP, ares_parse_aaaa_reply(data.data(), (int)data.size(), 138 &host, info, &count)); 139 EXPECT_EQ(nullptr, host); 140 pkt.add_question(new DNSQuestion("example.com", T_AAAA)); 141 142 // Question != answer, this is ok as of Issue #683 143 pkt.questions_.clear(); 144 pkt.add_question(new DNSQuestion("Axample.com", T_AAAA)); 145 data = pkt.data(); 146 EXPECT_EQ(ARES_SUCCESS, ares_parse_aaaa_reply(data.data(), (int)data.size(), 147 &host, info, &count)); 148 ASSERT_NE(nullptr, host); 149 std::stringstream ss; 150 ss << HostEnt(host); 151 EXPECT_EQ("{'axample.com' aliases=[] addrs=[0101:0101:0202:0202:0303:0303:0404:0404]}", ss.str()); 152 ares_free_hostent(host); 153 154 host = nullptr; 155 pkt.questions_.clear(); 156 pkt.add_question(new DNSQuestion("example.com", T_AAAA)); 157 158 // Two questions. 159 pkt.add_question(new DNSQuestion("example.com", T_AAAA)); 160 data = pkt.data(); 161 EXPECT_EQ(ARES_EBADRESP, ares_parse_aaaa_reply(data.data(), (int)data.size(), 162 &host, info, &count)); 163 EXPECT_EQ(nullptr, host); 164 pkt.questions_.clear(); 165 pkt.add_question(new DNSQuestion("example.com", T_AAAA)); 166 167 // Wrong sort of answer. 168 pkt.answers_.clear(); 169 pkt.add_answer(new DNSMxRR("example.com", 100, 100, "mx1.example.com")); 170 data = pkt.data(); 171 EXPECT_EQ(ARES_ENODATA, ares_parse_aaaa_reply(data.data(), (int)data.size(), 172 &host, info, &count)); 173 EXPECT_EQ(nullptr, host); 174 pkt.answers_.clear(); 175 pkt.add_answer(new DNSAaaaRR("example.com", 100, 176 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 177 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})); 178 179 // No answer. 180 pkt.answers_.clear(); 181 data = pkt.data(); 182 EXPECT_EQ(ARES_ENODATA, ares_parse_aaaa_reply(data.data(), (int)data.size(), 183 &host, info, &count)); 184 EXPECT_EQ(nullptr, host); 185 pkt.add_answer(new DNSAaaaRR("example.com", 100, 186 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 187 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})); 188 189 // Truncated packets. 190 data = pkt.data(); 191 for (size_t len = 1; len < data.size(); len++) { 192 EXPECT_EQ(ARES_EBADRESP, ares_parse_aaaa_reply(data.data(), (int)len, 193 &host, info, &count)); 194 EXPECT_EQ(nullptr, host); 195 EXPECT_EQ(ARES_EBADRESP, ares_parse_aaaa_reply(data.data(), (int)len, 196 nullptr, info, &count)); 197 } 198 199 // Negative length 200 EXPECT_EQ(ARES_EBADRESP, ares_parse_aaaa_reply(data.data(), -1, 201 &host, info, &count)); 202 } 203 204 TEST_F(LibraryTest, ParseAaaaReplyAllocFail) { 205 DNSPacket pkt; 206 pkt.set_qid(0x1234).set_response().set_aa() 207 .add_question(new DNSQuestion("example.com", T_AAAA)) 208 .add_answer(new DNSCnameRR("example.com", 300, "c.example.com")) 209 .add_answer(new DNSAaaaRR("c.example.com", 100, 210 {0x01, 0x01, 0x01, 0x01, 0x02, 0x02, 0x02, 0x02, 211 0x03, 0x03, 0x03, 0x03, 0x04, 0x04, 0x04, 0x04})); 212 std::vector<byte> data = pkt.data(); 213 struct hostent *host = nullptr; 214 struct ares_addr6ttl info[2]; 215 int count = 2; 216 217 for (int ii = 1; ii <= 8; ii++) { 218 ClearFails(); 219 SetAllocFail(ii); 220 EXPECT_EQ(ARES_ENOMEM, ares_parse_aaaa_reply(data.data(), (int)data.size(), 221 &host, info, &count)) << ii; 222 EXPECT_EQ(nullptr, host); 223 } 224 } 225 226 } // namespace test 227 } // namespace ares