1 1.1 christos /* 2 1.1 christos * testcode/unitmain.c - unit test main program for unbound. 3 1.1 christos * 4 1.1 christos * Copyright (c) 2007, NLnet Labs. All rights reserved. 5 1.1 christos * 6 1.1 christos * This software is open source. 7 1.1 christos * 8 1.1 christos * Redistribution and use in source and binary forms, with or without 9 1.1 christos * modification, are permitted provided that the following conditions 10 1.1 christos * are met: 11 1.1 christos * 12 1.1 christos * Redistributions of source code must retain the above copyright notice, 13 1.1 christos * this list of conditions and the following disclaimer. 14 1.1 christos * 15 1.1 christos * Redistributions in binary form must reproduce the above copyright notice, 16 1.1 christos * this list of conditions and the following disclaimer in the documentation 17 1.1 christos * and/or other materials provided with the distribution. 18 1.1 christos * 19 1.1 christos * Neither the name of the NLNET LABS nor the names of its contributors may 20 1.1 christos * be used to endorse or promote products derived from this software without 21 1.1 christos * specific prior written permission. 22 1.1 christos * 23 1.1 christos * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 1.1 christos * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 1.1 christos * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 1.1 christos * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 1.1 christos * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 1.1 christos * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 1.1 christos * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 1.1 christos * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 1.1 christos * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 1.1 christos * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 1.1 christos * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 1.1 christos * 35 1.1 christos */ 36 1.1 christos /** 37 1.1 christos * \file 38 1.1 christos * Unit test main program. Calls all the other unit tests. 39 1.1 christos * Exits with code 1 on a failure. 0 if all unit tests are successful. 40 1.1 christos */ 41 1.1 christos 42 1.1 christos #include "config.h" 43 1.1 christos #ifdef HAVE_OPENSSL_ERR_H 44 1.1 christos #include <openssl/err.h> 45 1.1 christos #endif 46 1.1 christos 47 1.1 christos #ifdef HAVE_OPENSSL_RAND_H 48 1.1 christos #include <openssl/rand.h> 49 1.1 christos #endif 50 1.1 christos 51 1.1 christos #ifdef HAVE_OPENSSL_CONF_H 52 1.1 christos #include <openssl/conf.h> 53 1.1 christos #endif 54 1.1 christos 55 1.1 christos #ifdef HAVE_OPENSSL_ENGINE_H 56 1.1 christos #include <openssl/engine.h> 57 1.1 christos #endif 58 1.1 christos 59 1.1 christos #ifdef HAVE_NSS 60 1.1 christos /* nss3 */ 61 1.1 christos #include "nss.h" 62 1.1 christos #endif 63 1.1 christos 64 1.1 christos #include "sldns/rrdef.h" 65 1.1 christos #include "sldns/keyraw.h" 66 1.1 christos #include "util/log.h" 67 1.1 christos #include "testcode/unitmain.h" 68 1.1 christos 69 1.1 christos /** number of tests done */ 70 1.1 christos int testcount = 0; 71 1.1 christos 72 1.1 christos #include "util/alloc.h" 73 1.1 christos /** test alloc code */ 74 1.1 christos static void 75 1.1 christos alloc_test(void) { 76 1.1.1.2 christos alloc_special_type *t1, *t2; 77 1.1 christos struct alloc_cache major, minor1, minor2; 78 1.1 christos int i; 79 1.1 christos 80 1.1 christos unit_show_feature("alloc_special_obtain"); 81 1.1 christos alloc_init(&major, NULL, 0); 82 1.1 christos alloc_init(&minor1, &major, 0); 83 1.1 christos alloc_init(&minor2, &major, 1); 84 1.1 christos 85 1.1 christos t1 = alloc_special_obtain(&minor1); 86 1.1 christos alloc_clear(&minor1); 87 1.1 christos 88 1.1 christos alloc_special_release(&minor2, t1); 89 1.1 christos t2 = alloc_special_obtain(&minor2); 90 1.1 christos unit_assert( t1 == t2 ); /* reused */ 91 1.1 christos alloc_special_release(&minor2, t1); 92 1.1 christos 93 1.1 christos for(i=0; i<100; i++) { 94 1.1 christos t1 = alloc_special_obtain(&minor1); 95 1.1 christos alloc_special_release(&minor2, t1); 96 1.1 christos } 97 1.1 christos if(0) { 98 1.1 christos alloc_stats(&minor1); 99 1.1 christos alloc_stats(&minor2); 100 1.1 christos alloc_stats(&major); 101 1.1 christos } 102 1.1 christos /* reuse happened */ 103 1.1 christos unit_assert(minor1.num_quar + minor2.num_quar + major.num_quar == 11); 104 1.1 christos 105 1.1 christos alloc_clear(&minor1); 106 1.1 christos alloc_clear(&minor2); 107 1.1 christos unit_assert(major.num_quar == 11); 108 1.1 christos alloc_clear(&major); 109 1.1 christos } 110 1.1 christos 111 1.1 christos #include "util/net_help.h" 112 1.1 christos /** test net code */ 113 1.1 christos static void 114 1.1 christos net_test(void) 115 1.1 christos { 116 1.1 christos const char* t4[] = {"\000\000\000\000", 117 1.1 christos "\200\000\000\000", 118 1.1 christos "\300\000\000\000", 119 1.1 christos "\340\000\000\000", 120 1.1 christos "\360\000\000\000", 121 1.1 christos "\370\000\000\000", 122 1.1 christos "\374\000\000\000", 123 1.1 christos "\376\000\000\000", 124 1.1 christos "\377\000\000\000", 125 1.1 christos "\377\200\000\000", 126 1.1 christos "\377\300\000\000", 127 1.1 christos "\377\340\000\000", 128 1.1 christos "\377\360\000\000", 129 1.1 christos "\377\370\000\000", 130 1.1 christos "\377\374\000\000", 131 1.1 christos "\377\376\000\000", 132 1.1 christos "\377\377\000\000", 133 1.1 christos "\377\377\200\000", 134 1.1 christos "\377\377\300\000", 135 1.1 christos "\377\377\340\000", 136 1.1 christos "\377\377\360\000", 137 1.1 christos "\377\377\370\000", 138 1.1 christos "\377\377\374\000", 139 1.1 christos "\377\377\376\000", 140 1.1 christos "\377\377\377\000", 141 1.1 christos "\377\377\377\200", 142 1.1 christos "\377\377\377\300", 143 1.1 christos "\377\377\377\340", 144 1.1 christos "\377\377\377\360", 145 1.1 christos "\377\377\377\370", 146 1.1 christos "\377\377\377\374", 147 1.1 christos "\377\377\377\376", 148 1.1 christos "\377\377\377\377", 149 1.1 christos "\377\377\377\377", 150 1.1 christos "\377\377\377\377", 151 1.1 christos }; 152 1.1 christos unit_show_func("util/net_help.c", "str_is_ip6"); 153 1.1 christos unit_assert( str_is_ip6("::") ); 154 1.1 christos unit_assert( str_is_ip6("::1") ); 155 1.1 christos unit_assert( str_is_ip6("2001:7b8:206:1:240:f4ff:fe37:8810") ); 156 1.1 christos unit_assert( str_is_ip6("fe80::240:f4ff:fe37:8810") ); 157 1.1 christos unit_assert( !str_is_ip6("0.0.0.0") ); 158 1.1 christos unit_assert( !str_is_ip6("213.154.224.12") ); 159 1.1 christos unit_assert( !str_is_ip6("213.154.224.255") ); 160 1.1 christos unit_assert( !str_is_ip6("255.255.255.0") ); 161 1.1 christos unit_show_func("util/net_help.c", "is_pow2"); 162 1.1 christos unit_assert( is_pow2(0) ); 163 1.1 christos unit_assert( is_pow2(1) ); 164 1.1 christos unit_assert( is_pow2(2) ); 165 1.1 christos unit_assert( is_pow2(4) ); 166 1.1 christos unit_assert( is_pow2(8) ); 167 1.1 christos unit_assert( is_pow2(16) ); 168 1.1 christos unit_assert( is_pow2(1024) ); 169 1.1 christos unit_assert( is_pow2(1024*1024) ); 170 1.1 christos unit_assert( is_pow2(1024*1024*1024) ); 171 1.1 christos unit_assert( !is_pow2(3) ); 172 1.1 christos unit_assert( !is_pow2(5) ); 173 1.1 christos unit_assert( !is_pow2(6) ); 174 1.1 christos unit_assert( !is_pow2(7) ); 175 1.1 christos unit_assert( !is_pow2(9) ); 176 1.1 christos unit_assert( !is_pow2(10) ); 177 1.1 christos unit_assert( !is_pow2(11) ); 178 1.1 christos unit_assert( !is_pow2(17) ); 179 1.1 christos unit_assert( !is_pow2(23) ); 180 1.1 christos unit_assert( !is_pow2(257) ); 181 1.1 christos unit_assert( !is_pow2(259) ); 182 1.1 christos 183 1.1 christos /* test addr_mask */ 184 1.1 christos unit_show_func("util/net_help.c", "addr_mask"); 185 1.1 christos if(1) { 186 1.1 christos struct sockaddr_in a4; 187 1.1 christos struct sockaddr_in6 a6; 188 1.1 christos socklen_t l4 = (socklen_t)sizeof(a4); 189 1.1 christos socklen_t l6 = (socklen_t)sizeof(a6); 190 1.1 christos int i; 191 1.1 christos a4.sin_family = AF_INET; 192 1.1 christos a6.sin6_family = AF_INET6; 193 1.1 christos for(i=0; i<35; i++) { 194 1.1 christos /* address 255.255.255.255 */ 195 1.1 christos memcpy(&a4.sin_addr, "\377\377\377\377", 4); 196 1.1 christos addr_mask((struct sockaddr_storage*)&a4, l4, i); 197 1.1 christos unit_assert(memcmp(&a4.sin_addr, t4[i], 4) == 0); 198 1.1 christos } 199 1.1 christos memcpy(&a6.sin6_addr, "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377", 16); 200 1.1 christos addr_mask((struct sockaddr_storage*)&a6, l6, 128); 201 1.1 christos unit_assert(memcmp(&a6.sin6_addr, "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377", 16) == 0); 202 1.1 christos addr_mask((struct sockaddr_storage*)&a6, l6, 122); 203 1.1 christos unit_assert(memcmp(&a6.sin6_addr, "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\300", 16) == 0); 204 1.1 christos addr_mask((struct sockaddr_storage*)&a6, l6, 120); 205 1.1 christos unit_assert(memcmp(&a6.sin6_addr, "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\000", 16) == 0); 206 1.1 christos addr_mask((struct sockaddr_storage*)&a6, l6, 64); 207 1.1 christos unit_assert(memcmp(&a6.sin6_addr, "\377\377\377\377\377\377\377\377\000\000\000\000\000\000\000\000", 16) == 0); 208 1.1.1.10 christos /* Check that negative value in net is not problematic. */ 209 1.1.1.10 christos addr_mask((struct sockaddr_storage*)&a6, l6, -100); 210 1.1 christos addr_mask((struct sockaddr_storage*)&a6, l6, 0); 211 1.1 christos unit_assert(memcmp(&a6.sin6_addr, "\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000", 16) == 0); 212 1.1 christos } 213 1.1 christos 214 1.1 christos /* test addr_in_common */ 215 1.1 christos unit_show_func("util/net_help.c", "addr_in_common"); 216 1.1 christos if(1) { 217 1.1 christos struct sockaddr_in a4, b4; 218 1.1 christos struct sockaddr_in6 a6, b6; 219 1.1 christos socklen_t l4 = (socklen_t)sizeof(a4); 220 1.1 christos socklen_t l6 = (socklen_t)sizeof(a6); 221 1.1 christos int i; 222 1.1 christos a4.sin_family = AF_INET; 223 1.1 christos b4.sin_family = AF_INET; 224 1.1 christos a6.sin6_family = AF_INET6; 225 1.1 christos b6.sin6_family = AF_INET6; 226 1.1 christos memcpy(&a4.sin_addr, "abcd", 4); 227 1.1 christos memcpy(&b4.sin_addr, "abcd", 4); 228 1.1 christos unit_assert(addr_in_common((struct sockaddr_storage*)&a4, 32, 229 1.1 christos (struct sockaddr_storage*)&b4, 32, l4) == 32); 230 1.1 christos unit_assert(addr_in_common((struct sockaddr_storage*)&a4, 34, 231 1.1 christos (struct sockaddr_storage*)&b4, 32, l4) == 32); 232 1.1 christos for(i=0; i<=32; i++) { 233 1.1 christos unit_assert(addr_in_common( 234 1.1 christos (struct sockaddr_storage*)&a4, 32, 235 1.1 christos (struct sockaddr_storage*)&b4, i, l4) == i); 236 1.1 christos unit_assert(addr_in_common( 237 1.1 christos (struct sockaddr_storage*)&a4, i, 238 1.1 christos (struct sockaddr_storage*)&b4, 32, l4) == i); 239 1.1 christos unit_assert(addr_in_common( 240 1.1 christos (struct sockaddr_storage*)&a4, i, 241 1.1 christos (struct sockaddr_storage*)&b4, i, l4) == i); 242 1.1 christos } 243 1.1 christos for(i=0; i<=32; i++) { 244 1.1 christos memcpy(&a4.sin_addr, "\377\377\377\377", 4); 245 1.1 christos memcpy(&b4.sin_addr, t4[i], 4); 246 1.1 christos unit_assert(addr_in_common( 247 1.1 christos (struct sockaddr_storage*)&a4, 32, 248 1.1 christos (struct sockaddr_storage*)&b4, 32, l4) == i); 249 1.1 christos unit_assert(addr_in_common( 250 1.1 christos (struct sockaddr_storage*)&b4, 32, 251 1.1 christos (struct sockaddr_storage*)&a4, 32, l4) == i); 252 1.1 christos } 253 1.1 christos memcpy(&a6.sin6_addr, "abcdefghabcdefgh", 16); 254 1.1 christos memcpy(&b6.sin6_addr, "abcdefghabcdefgh", 16); 255 1.1 christos unit_assert(addr_in_common((struct sockaddr_storage*)&a6, 128, 256 1.1 christos (struct sockaddr_storage*)&b6, 128, l6) == 128); 257 1.1 christos unit_assert(addr_in_common((struct sockaddr_storage*)&a6, 129, 258 1.1 christos (struct sockaddr_storage*)&b6, 128, l6) == 128); 259 1.1 christos for(i=0; i<=128; i++) { 260 1.1 christos unit_assert(addr_in_common( 261 1.1 christos (struct sockaddr_storage*)&a6, 128, 262 1.1 christos (struct sockaddr_storage*)&b6, i, l6) == i); 263 1.1 christos unit_assert(addr_in_common( 264 1.1 christos (struct sockaddr_storage*)&a6, i, 265 1.1 christos (struct sockaddr_storage*)&b6, 128, l6) == i); 266 1.1 christos unit_assert(addr_in_common( 267 1.1 christos (struct sockaddr_storage*)&a6, i, 268 1.1 christos (struct sockaddr_storage*)&b6, i, l6) == i); 269 1.1 christos } 270 1.1 christos } 271 1.1.1.10 christos /* test netblockstrtoaddr */ 272 1.1.1.10 christos unit_show_func("util/net_help.c", "netblockstrtoaddr"); 273 1.1.1.10 christos if(1) { 274 1.1.1.10 christos struct sockaddr_storage a; 275 1.1.1.10 christos socklen_t alen = 0; 276 1.1.1.10 christos int net = 0, res; 277 1.1.1.10 christos char astr[128]; 278 1.1.1.10 christos memset(&a, 0, sizeof(a)); 279 1.1.1.10 christos 280 1.1.1.10 christos res = netblockstrtoaddr("1.2.3.0/24", 53, &a, &alen, &net); 281 1.1.1.10 christos unit_assert(res!=0 && net == 24); 282 1.1.1.10 christos addr_to_str(&a, alen, astr, sizeof(astr)); 283 1.1.1.10 christos unit_assert(strcmp(astr, "1.2.3.0") == 0); 284 1.1.1.10 christos unit_assert(ntohs(((struct sockaddr_in*)&a)->sin_port)==53); 285 1.1.1.10 christos 286 1.1.1.10 christos res = netblockstrtoaddr("2001:DB8:33:44::/64", 53, 287 1.1.1.10 christos &a, &alen, &net); 288 1.1.1.10 christos unit_assert(res!=0 && net == 64); 289 1.1.1.10 christos addr_to_str(&a, alen, astr, sizeof(astr)); 290 1.1.1.10 christos unit_assert(strcmp(astr, "2001:db8:33:44::") == 0); 291 1.1.1.10 christos unit_assert(ntohs(((struct sockaddr_in6*)&a)->sin6_port)==53); 292 1.1.1.10 christos } 293 1.1 christos /* test sockaddr_cmp_addr */ 294 1.1 christos unit_show_func("util/net_help.c", "sockaddr_cmp_addr"); 295 1.1 christos if(1) { 296 1.1 christos struct sockaddr_storage a, b; 297 1.1 christos socklen_t alen = (socklen_t)sizeof(a); 298 1.1 christos socklen_t blen = (socklen_t)sizeof(b); 299 1.1 christos unit_assert(ipstrtoaddr("127.0.0.0", 53, &a, &alen)); 300 1.1 christos unit_assert(ipstrtoaddr("127.255.255.255", 53, &b, &blen)); 301 1.1 christos unit_assert(sockaddr_cmp_addr(&a, alen, &b, blen) < 0); 302 1.1 christos unit_assert(sockaddr_cmp_addr(&b, blen, &a, alen) > 0); 303 1.1 christos unit_assert(sockaddr_cmp_addr(&a, alen, &a, alen) == 0); 304 1.1 christos unit_assert(sockaddr_cmp_addr(&b, blen, &b, blen) == 0); 305 1.1 christos unit_assert(ipstrtoaddr("192.168.121.5", 53, &a, &alen)); 306 1.1 christos unit_assert(sockaddr_cmp_addr(&a, alen, &b, blen) > 0); 307 1.1 christos unit_assert(sockaddr_cmp_addr(&b, blen, &a, alen) < 0); 308 1.1 christos unit_assert(sockaddr_cmp_addr(&a, alen, &a, alen) == 0); 309 1.1 christos unit_assert(ipstrtoaddr("2001:3578:ffeb::99", 53, &b, &blen)); 310 1.1 christos unit_assert(sockaddr_cmp_addr(&b, blen, &b, blen) == 0); 311 1.1 christos unit_assert(sockaddr_cmp_addr(&a, alen, &b, blen) < 0); 312 1.1 christos unit_assert(sockaddr_cmp_addr(&b, blen, &a, alen) > 0); 313 1.1 christos } 314 1.1 christos /* test addr_is_ip4mapped */ 315 1.1 christos unit_show_func("util/net_help.c", "addr_is_ip4mapped"); 316 1.1 christos if(1) { 317 1.1 christos struct sockaddr_storage a; 318 1.1 christos socklen_t l = (socklen_t)sizeof(a); 319 1.1 christos unit_assert(ipstrtoaddr("12.13.14.15", 53, &a, &l)); 320 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 321 1.1 christos unit_assert(ipstrtoaddr("fe80::217:31ff:fe91:df", 53, &a, &l)); 322 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 323 1.1 christos unit_assert(ipstrtoaddr("ffff::217:31ff:fe91:df", 53, &a, &l)); 324 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 325 1.1 christos unit_assert(ipstrtoaddr("::ffff:31ff:fe91:df", 53, &a, &l)); 326 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 327 1.1 christos unit_assert(ipstrtoaddr("::fffe:fe91:df", 53, &a, &l)); 328 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 329 1.1 christos unit_assert(ipstrtoaddr("::ffff:127.0.0.1", 53, &a, &l)); 330 1.1 christos unit_assert(addr_is_ip4mapped(&a, l)); 331 1.1 christos unit_assert(ipstrtoaddr("::ffff:127.0.0.2", 53, &a, &l)); 332 1.1 christos unit_assert(addr_is_ip4mapped(&a, l)); 333 1.1 christos unit_assert(ipstrtoaddr("::ffff:192.168.0.2", 53, &a, &l)); 334 1.1 christos unit_assert(addr_is_ip4mapped(&a, l)); 335 1.1 christos unit_assert(ipstrtoaddr("2::ffff:192.168.0.2", 53, &a, &l)); 336 1.1 christos unit_assert(!addr_is_ip4mapped(&a, l)); 337 1.1 christos } 338 1.1 christos /* test addr_is_any */ 339 1.1 christos unit_show_func("util/net_help.c", "addr_is_any"); 340 1.1 christos if(1) { 341 1.1 christos struct sockaddr_storage a; 342 1.1 christos socklen_t l = (socklen_t)sizeof(a); 343 1.1 christos unit_assert(ipstrtoaddr("0.0.0.0", 53, &a, &l)); 344 1.1 christos unit_assert(addr_is_any(&a, l)); 345 1.1 christos unit_assert(ipstrtoaddr("0.0.0.0", 10053, &a, &l)); 346 1.1 christos unit_assert(addr_is_any(&a, l)); 347 1.1 christos unit_assert(ipstrtoaddr("0.0.0.0", 0, &a, &l)); 348 1.1 christos unit_assert(addr_is_any(&a, l)); 349 1.1 christos unit_assert(ipstrtoaddr("::0", 0, &a, &l)); 350 1.1 christos unit_assert(addr_is_any(&a, l)); 351 1.1 christos unit_assert(ipstrtoaddr("::0", 53, &a, &l)); 352 1.1 christos unit_assert(addr_is_any(&a, l)); 353 1.1 christos unit_assert(ipstrtoaddr("::1", 53, &a, &l)); 354 1.1 christos unit_assert(!addr_is_any(&a, l)); 355 1.1 christos unit_assert(ipstrtoaddr("2001:1667::1", 0, &a, &l)); 356 1.1 christos unit_assert(!addr_is_any(&a, l)); 357 1.1 christos unit_assert(ipstrtoaddr("2001::0", 0, &a, &l)); 358 1.1 christos unit_assert(!addr_is_any(&a, l)); 359 1.1 christos unit_assert(ipstrtoaddr("10.0.0.0", 0, &a, &l)); 360 1.1 christos unit_assert(!addr_is_any(&a, l)); 361 1.1 christos unit_assert(ipstrtoaddr("0.0.0.10", 0, &a, &l)); 362 1.1 christos unit_assert(!addr_is_any(&a, l)); 363 1.1 christos unit_assert(ipstrtoaddr("192.0.2.1", 0, &a, &l)); 364 1.1 christos unit_assert(!addr_is_any(&a, l)); 365 1.1 christos } 366 1.1 christos } 367 1.1 christos 368 1.1 christos #include "util/config_file.h" 369 1.1 christos /** test config_file: cfg_parse_memsize */ 370 1.1 christos static void 371 1.1 christos config_memsize_test(void) 372 1.1 christos { 373 1.1 christos size_t v = 0; 374 1.1 christos unit_show_func("util/config_file.c", "cfg_parse_memsize"); 375 1.1 christos if(0) { 376 1.1 christos /* these emit errors */ 377 1.1 christos unit_assert( cfg_parse_memsize("", &v) == 0); 378 1.1 christos unit_assert( cfg_parse_memsize("bla", &v) == 0); 379 1.1 christos unit_assert( cfg_parse_memsize("nop", &v) == 0); 380 1.1 christos unit_assert( cfg_parse_memsize("n0b", &v) == 0); 381 1.1 christos unit_assert( cfg_parse_memsize("gb", &v) == 0); 382 1.1 christos unit_assert( cfg_parse_memsize("b", &v) == 0); 383 1.1 christos unit_assert( cfg_parse_memsize("kb", &v) == 0); 384 1.1 christos unit_assert( cfg_parse_memsize("kk kb", &v) == 0); 385 1.1 christos } 386 1.1 christos unit_assert( cfg_parse_memsize("0", &v) && v==0); 387 1.1 christos unit_assert( cfg_parse_memsize("1", &v) && v==1); 388 1.1 christos unit_assert( cfg_parse_memsize("10", &v) && v==10); 389 1.1 christos unit_assert( cfg_parse_memsize("10b", &v) && v==10); 390 1.1 christos unit_assert( cfg_parse_memsize("5b", &v) && v==5); 391 1.1 christos unit_assert( cfg_parse_memsize("1024", &v) && v==1024); 392 1.1 christos unit_assert( cfg_parse_memsize("1k", &v) && v==1024); 393 1.1 christos unit_assert( cfg_parse_memsize("1K", &v) && v==1024); 394 1.1 christos unit_assert( cfg_parse_memsize("1Kb", &v) && v==1024); 395 1.1 christos unit_assert( cfg_parse_memsize("1kb", &v) && v==1024); 396 1.1 christos unit_assert( cfg_parse_memsize("1 kb", &v) && v==1024); 397 1.1 christos unit_assert( cfg_parse_memsize("10 kb", &v) && v==10240); 398 1.1 christos unit_assert( cfg_parse_memsize("2k", &v) && v==2048); 399 1.1 christos unit_assert( cfg_parse_memsize("2m", &v) && v==2048*1024); 400 1.1 christos unit_assert( cfg_parse_memsize("3M", &v) && v==3072*1024); 401 1.1 christos unit_assert( cfg_parse_memsize("40m", &v) && v==40960*1024); 402 1.1 christos unit_assert( cfg_parse_memsize("1G", &v) && v==1024*1024*1024); 403 1.1 christos unit_assert( cfg_parse_memsize("1 Gb", &v) && v==1024*1024*1024); 404 1.1 christos unit_assert( cfg_parse_memsize("0 Gb", &v) && v==0*1024*1024); 405 1.1 christos } 406 1.1 christos 407 1.1 christos /** test config_file: test tag code */ 408 1.1 christos static void 409 1.1 christos config_tag_test(void) 410 1.1 christos { 411 1.1 christos unit_show_func("util/config_file.c", "taglist_intersect"); 412 1.1 christos unit_assert( taglist_intersect( 413 1.1 christos (uint8_t*)"\000\000\000", 3, (uint8_t*)"\001\000\001", 3 414 1.1 christos ) == 0); 415 1.1 christos unit_assert( taglist_intersect( 416 1.1 christos (uint8_t*)"\000\000\001", 3, (uint8_t*)"\001\000\001", 3 417 1.1 christos ) == 1); 418 1.1 christos unit_assert( taglist_intersect( 419 1.1 christos (uint8_t*)"\001\000\000", 3, (uint8_t*)"\001\000\001", 3 420 1.1 christos ) == 1); 421 1.1 christos unit_assert( taglist_intersect( 422 1.1 christos (uint8_t*)"\001", 1, (uint8_t*)"\001\000\001", 3 423 1.1 christos ) == 1); 424 1.1 christos unit_assert( taglist_intersect( 425 1.1 christos (uint8_t*)"\001\000\001", 3, (uint8_t*)"\001", 1 426 1.1 christos ) == 1); 427 1.1 christos } 428 1.1 christos 429 1.1 christos #include "util/rtt.h" 430 1.1.1.2 christos #include "util/timehist.h" 431 1.1.1.4 christos #include "iterator/iterator.h" 432 1.1.1.2 christos #include "libunbound/unbound.h" 433 1.1 christos /** test RTT code */ 434 1.1 christos static void 435 1.1 christos rtt_test(void) 436 1.1 christos { 437 1.1.1.4 christos int init = UNKNOWN_SERVER_NICENESS; 438 1.1 christos int i; 439 1.1 christos struct rtt_info r; 440 1.1 christos unit_show_func("util/rtt.c", "rtt_timeout"); 441 1.1 christos rtt_init(&r); 442 1.1 christos /* initial value sensible */ 443 1.1 christos unit_assert( rtt_timeout(&r) == init ); 444 1.1 christos rtt_lost(&r, init); 445 1.1 christos unit_assert( rtt_timeout(&r) == init*2 ); 446 1.1 christos rtt_lost(&r, init*2); 447 1.1 christos unit_assert( rtt_timeout(&r) == init*4 ); 448 1.1 christos rtt_update(&r, 4000); 449 1.1 christos unit_assert( rtt_timeout(&r) >= 2000 ); 450 1.1 christos rtt_lost(&r, rtt_timeout(&r) ); 451 1.1 christos for(i=0; i<100; i++) { 452 1.1 christos rtt_lost(&r, rtt_timeout(&r) ); 453 1.1 christos unit_assert( rtt_timeout(&r) > RTT_MIN_TIMEOUT-1); 454 1.1 christos unit_assert( rtt_timeout(&r) < RTT_MAX_TIMEOUT+1); 455 1.1 christos } 456 1.1.1.2 christos /* must be the same, timehist bucket is used in stats */ 457 1.1.1.2 christos unit_assert(UB_STATS_BUCKET_NUM == NUM_BUCKETS_HIST); 458 1.1 christos } 459 1.1 christos 460 1.1.1.8 christos #include "util/edns.h" 461 1.1.1.8 christos /* Complete version-invalid client cookie; needs a new one. 462 1.1.1.8 christos * Based on edns_cookie_rfc9018_a2 */ 463 1.1.1.8 christos static void 464 1.1.1.8 christos edns_cookie_invalid_version(void) 465 1.1.1.8 christos { 466 1.1.1.8 christos uint32_t timestamp = 1559734385; 467 1.1.1.8 christos uint8_t client_cookie[] = { 468 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57, 469 1.1.1.8 christos 0x99, 0x00, 0x00, 0x00, 470 1.1.1.8 christos 0x5c, 0xf7, 0x9f, 0x11, 471 1.1.1.8 christos 0x1f, 0x81, 0x30, 0xc3, 0xee, 0xe2, 0x94, 0x80 }; 472 1.1.1.8 christos uint8_t server_cookie[] = { 473 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57, 474 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 475 1.1.1.8 christos 0x5c, 0xf7, 0xa8, 0x71, 476 1.1.1.8 christos 0xd4, 0xa5, 0x64, 0xa1, 0x44, 0x2a, 0xca, 0x77 }; 477 1.1.1.8 christos uint8_t server_secret[] = { 478 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 479 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 480 1.1.1.8 christos uint8_t buf[32]; 481 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 482 1.1.1.8 christos memcpy(buf, client_cookie, 8 + 4 + 4); 483 1.1.1.8 christos /* copy ip 198.51.100.100 */ 484 1.1.1.8 christos memcpy(buf + 16, "\306\063\144\144", 4); 485 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 486 1.1.1.8 christos sizeof(client_cookie), server_secret, sizeof(server_secret), 1, 487 1.1.1.8 christos buf, timestamp) == COOKIE_STATUS_INVALID); 488 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 489 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 490 1.1.1.8 christos } 491 1.1.1.8 christos 492 1.1.1.8 christos /* Complete hash-invalid client cookie; needs a new one. */ 493 1.1.1.8 christos static void 494 1.1.1.8 christos edns_cookie_invalid_hash(void) 495 1.1.1.8 christos { 496 1.1.1.8 christos uint32_t timestamp = 0; 497 1.1.1.8 christos uint8_t client_cookie[] = { 498 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 499 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 500 1.1.1.8 christos 0x00, 0x00, 0x00, 0x00, 501 1.1.1.8 christos 0x32, 0xF2, 0x43, 0xB9, 0xBC, 0xFE, 0xC4, 0x06 }; 502 1.1.1.8 christos uint8_t server_cookie[] = { 503 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 504 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 505 1.1.1.8 christos 0x00, 0x00, 0x00, 0x00, 506 1.1.1.8 christos 0xBA, 0x0D, 0x82, 0x90, 0x8F, 0xAA, 0xEB, 0xBD }; 507 1.1.1.8 christos uint8_t server_secret[] = { 508 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 509 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 510 1.1.1.8 christos uint8_t buf[32]; 511 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 512 1.1.1.8 christos memcpy(buf, client_cookie, 8 + 4 + 4); 513 1.1.1.8 christos /* copy ip 203.0.113.203 */ 514 1.1.1.8 christos memcpy(buf + 16, "\313\000\161\313", 4); 515 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 516 1.1.1.8 christos sizeof(client_cookie), server_secret, sizeof(server_secret), 1, 517 1.1.1.8 christos buf, timestamp) == COOKIE_STATUS_INVALID); 518 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 519 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 520 1.1.1.8 christos } 521 1.1.1.8 christos 522 1.1.1.8 christos /* Complete hash-valid client cookie; more than 30 minutes old; needs a 523 1.1.1.8 christos * refreshed server cookie. 524 1.1.1.8 christos * A slightly better variation of edns_cookie_rfc9018_a3 for Unbound to check 525 1.1.1.8 christos * that RESERVED bits do not influence cookie validation. */ 526 1.1.1.8 christos static void 527 1.1.1.8 christos edns_cookie_rfc9018_a3_better(void) 528 1.1.1.8 christos { 529 1.1.1.8 christos uint32_t timestamp = 1800 + 1; 530 1.1.1.8 christos uint8_t client_cookie[] = { 531 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 532 1.1.1.8 christos 0x01, 0xab, 0xcd, 0xef, 533 1.1.1.8 christos 0x00, 0x00, 0x00, 0x00, 534 1.1.1.8 christos 0x32, 0xF2, 0x43, 0xB9, 0xBC, 0xFE, 0xC4, 0x06 }; 535 1.1.1.8 christos uint8_t server_cookie[] = { 536 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 537 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 538 1.1.1.8 christos 0x00, 0x00, 0x07, 0x09, 539 1.1.1.8 christos 0x62, 0xD5, 0x93, 0x09, 0x14, 0x5C, 0x23, 0x9D }; 540 1.1.1.8 christos uint8_t server_secret[] = { 541 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 542 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 543 1.1.1.8 christos uint8_t buf[32]; 544 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 545 1.1.1.8 christos memcpy(buf, client_cookie, 8 + 4 + 4); 546 1.1.1.8 christos /* copy ip 203.0.113.203 */ 547 1.1.1.8 christos memcpy(buf + 16, "\313\000\161\313", 4); 548 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 549 1.1.1.8 christos sizeof(client_cookie), server_secret, sizeof(server_secret), 1, 550 1.1.1.8 christos buf, timestamp) == COOKIE_STATUS_VALID_RENEW); 551 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 552 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 553 1.1.1.8 christos } 554 1.1.1.8 christos 555 1.1.1.8 christos /* Complete hash-valid client cookie; more than 60 minutes old (expired); 556 1.1.1.8 christos * needs a refreshed server cookie. */ 557 1.1.1.8 christos static void 558 1.1.1.8 christos edns_cookie_rfc9018_a3(void) 559 1.1.1.8 christos { 560 1.1.1.8 christos uint32_t timestamp = 1559734700; 561 1.1.1.8 christos uint8_t client_cookie[] = { 562 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 563 1.1.1.8 christos 0x01, 0xab, 0xcd, 0xef, 564 1.1.1.8 christos 0x5c, 0xf7, 0x8f, 0x71, 565 1.1.1.8 christos 0xa3, 0x14, 0x22, 0x7b, 0x66, 0x79, 0xeb, 0xf5 }; 566 1.1.1.8 christos uint8_t server_cookie[] = { 567 1.1.1.8 christos 0xfc, 0x93, 0xfc, 0x62, 0x80, 0x7d, 0xdb, 0x86, 568 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 569 1.1.1.8 christos 0x5c, 0xf7, 0xa9, 0xac, 570 1.1.1.8 christos 0xf7, 0x3a, 0x78, 0x10, 0xac, 0xa2, 0x38, 0x1e }; 571 1.1.1.8 christos uint8_t server_secret[] = { 572 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 573 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 574 1.1.1.8 christos uint8_t buf[32]; 575 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 576 1.1.1.8 christos memcpy(buf, client_cookie, 8 + 4 + 4); 577 1.1.1.8 christos /* copy ip 203.0.113.203 */ 578 1.1.1.8 christos memcpy(buf + 16, "\313\000\161\313", 4); 579 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 580 1.1.1.8 christos sizeof(client_cookie), server_secret, sizeof(server_secret), 1, 581 1.1.1.8 christos buf, timestamp) == COOKIE_STATUS_EXPIRED); 582 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 583 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 584 1.1.1.8 christos } 585 1.1.1.8 christos 586 1.1.1.8 christos /* Complete hash-valid client cookie; more than 30 minutes old; needs a 587 1.1.1.8 christos * refreshed server cookie. */ 588 1.1.1.8 christos static void 589 1.1.1.8 christos edns_cookie_rfc9018_a2(void) 590 1.1.1.8 christos { 591 1.1.1.8 christos uint32_t timestamp = 1559734385; 592 1.1.1.8 christos uint8_t client_cookie[] = { 593 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57, 594 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 595 1.1.1.8 christos 0x5c, 0xf7, 0x9f, 0x11, 596 1.1.1.8 christos 0x1f, 0x81, 0x30, 0xc3, 0xee, 0xe2, 0x94, 0x80 }; 597 1.1.1.8 christos uint8_t server_cookie[] = { 598 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57, 599 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 600 1.1.1.8 christos 0x5c, 0xf7, 0xa8, 0x71, 601 1.1.1.8 christos 0xd4, 0xa5, 0x64, 0xa1, 0x44, 0x2a, 0xca, 0x77 }; 602 1.1.1.8 christos uint8_t server_secret[] = { 603 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 604 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 605 1.1.1.8 christos uint8_t buf[32]; 606 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 607 1.1.1.8 christos memcpy(buf, client_cookie, 8 + 4 + 4); 608 1.1.1.8 christos /* copy ip 198.51.100.100 */ 609 1.1.1.8 christos memcpy(buf + 16, "\306\063\144\144", 4); 610 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 611 1.1.1.8 christos sizeof(client_cookie), server_secret, sizeof(server_secret), 1, 612 1.1.1.8 christos buf, timestamp) == COOKIE_STATUS_VALID_RENEW); 613 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 614 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 615 1.1.1.8 christos } 616 1.1.1.8 christos 617 1.1.1.8 christos /* Only client cookie; needs a complete server cookie. */ 618 1.1.1.8 christos static void 619 1.1.1.8 christos edns_cookie_rfc9018_a1(void) 620 1.1.1.8 christos { 621 1.1.1.8 christos uint32_t timestamp = 1559731985; 622 1.1.1.8 christos uint8_t client_cookie[] = { 623 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57 }; 624 1.1.1.8 christos uint8_t server_cookie[] = { 625 1.1.1.8 christos 0x24, 0x64, 0xc4, 0xab, 0xcf, 0x10, 0xc9, 0x57, 626 1.1.1.8 christos 0x01, 0x00, 0x00, 0x00, 627 1.1.1.8 christos 0x5c, 0xf7, 0x9f, 0x11, 628 1.1.1.8 christos 0x1f, 0x81, 0x30, 0xc3, 0xee, 0xe2, 0x94, 0x80 }; 629 1.1.1.8 christos uint8_t server_secret[] = { 630 1.1.1.8 christos 0xe5, 0xe9, 0x73, 0xe5, 0xa6, 0xb2, 0xa4, 0x3f, 631 1.1.1.8 christos 0x48, 0xe7, 0xdc, 0x84, 0x9e, 0x37, 0xbf, 0xcf }; 632 1.1.1.8 christos uint8_t buf[32]; 633 1.1.1.8 christos /* copy client cookie|version|reserved|timestamp */ 634 1.1.1.8 christos memcpy(buf, server_cookie, 8 + 4 + 4); 635 1.1.1.8 christos /* copy ip 198.51.100.100 */ 636 1.1.1.8 christos memcpy(buf + 16, "\306\063\144\144", 4); 637 1.1.1.8 christos unit_assert(edns_cookie_server_validate(client_cookie, 638 1.1.1.8 christos sizeof(client_cookie), 639 1.1.1.8 christos /* these will not be used; it will return invalid 640 1.1.1.8 christos * because of the size. */ 641 1.1.1.8 christos NULL, 0, 1, NULL, 0) == COOKIE_STATUS_CLIENT_ONLY); 642 1.1.1.8 christos edns_cookie_server_write(buf, server_secret, 1, timestamp); 643 1.1.1.8 christos unit_assert(memcmp(server_cookie, buf, 24) == 0); 644 1.1.1.8 christos } 645 1.1.1.8 christos 646 1.1.1.8 christos /** test interoperable DNS cookies (RFC9018) */ 647 1.1.1.8 christos static void 648 1.1.1.8 christos edns_cookie_test(void) 649 1.1.1.8 christos { 650 1.1.1.8 christos unit_show_feature("interoperable dns cookies"); 651 1.1.1.8 christos /* Check RFC9018 appendix test vectors */ 652 1.1.1.8 christos edns_cookie_rfc9018_a1(); 653 1.1.1.8 christos edns_cookie_rfc9018_a2(); 654 1.1.1.8 christos edns_cookie_rfc9018_a3(); 655 1.1.1.8 christos /* More tests */ 656 1.1.1.8 christos edns_cookie_rfc9018_a3_better(); 657 1.1.1.8 christos edns_cookie_invalid_hash(); 658 1.1.1.8 christos edns_cookie_invalid_version(); 659 1.1.1.8 christos } 660 1.1.1.8 christos 661 1.1 christos #include "util/random.h" 662 1.1 christos /** test randomness */ 663 1.1 christos static void 664 1.1 christos rnd_test(void) 665 1.1 christos { 666 1.1 christos struct ub_randstate* r; 667 1.1 christos int num = 1000, i; 668 1.1 christos long int a[1000]; 669 1.1 christos unit_show_feature("ub_random"); 670 1.1.1.5 christos unit_assert( (r = ub_initstate(NULL)) ); 671 1.1 christos for(i=0; i<num; i++) { 672 1.1 christos a[i] = ub_random(r); 673 1.1 christos unit_assert(a[i] >= 0); 674 1.1 christos unit_assert((size_t)a[i] <= (size_t)0x7fffffff); 675 1.1 christos if(i > 5) 676 1.1 christos unit_assert(a[i] != a[i-1] || a[i] != a[i-2] || 677 1.1 christos a[i] != a[i-3] || a[i] != a[i-4] || 678 1.1 christos a[i] != a[i-5] || a[i] != a[i-6]); 679 1.1 christos } 680 1.1 christos a[0] = ub_random_max(r, 1); 681 1.1 christos unit_assert(a[0] >= 0 && a[0] < 1); 682 1.1 christos a[0] = ub_random_max(r, 10000); 683 1.1 christos unit_assert(a[0] >= 0 && a[0] < 10000); 684 1.1 christos for(i=0; i<num; i++) { 685 1.1 christos a[i] = ub_random_max(r, 10); 686 1.1 christos unit_assert(a[i] >= 0 && a[i] < 10); 687 1.1 christos } 688 1.1 christos ub_randfree(r); 689 1.1 christos } 690 1.1 christos 691 1.1.1.2 christos #include "respip/respip.h" 692 1.1.1.2 christos #include "services/localzone.h" 693 1.1.1.2 christos #include "util/data/packed_rrset.h" 694 1.1.1.2 christos typedef struct addr_action {char* ip; char* sact; enum respip_action act;} 695 1.1.1.2 christos addr_action_t; 696 1.1.1.2 christos 697 1.1.1.2 christos /** Utility function that verifies that the respip set has actions as expected */ 698 1.1.1.2 christos static void 699 1.1.1.2 christos verify_respip_set_actions(struct respip_set* set, addr_action_t actions[], 700 1.1.1.2 christos int actions_len) 701 1.1.1.2 christos { 702 1.1.1.2 christos int i = 0; 703 1.1.1.2 christos struct rbtree_type* tree = respip_set_get_tree(set); 704 1.1.1.2 christos for (i=0; i<actions_len; i++) { 705 1.1.1.2 christos struct sockaddr_storage addr; 706 1.1.1.2 christos int net; 707 1.1.1.2 christos socklen_t addrlen; 708 1.1.1.2 christos struct resp_addr* node; 709 1.1.1.2 christos netblockstrtoaddr(actions[i].ip, UNBOUND_DNS_PORT, &addr, 710 1.1.1.2 christos &addrlen, &net); 711 1.1.1.2 christos node = (struct resp_addr*)addr_tree_find(tree, &addr, addrlen, net); 712 1.1.1.2 christos 713 1.1.1.2 christos /** we have the node and the node has the correct action 714 1.1.1.2 christos * and has no data */ 715 1.1.1.2 christos unit_assert(node); 716 1.1.1.2 christos unit_assert(actions[i].act == 717 1.1.1.2 christos resp_addr_get_action(node)); 718 1.1.1.2 christos unit_assert(resp_addr_get_rrset(node) == NULL); 719 1.1.1.2 christos } 720 1.1.1.2 christos unit_assert(actions_len && i == actions_len); 721 1.1.1.2 christos unit_assert(actions_len == (int)tree->count); 722 1.1.1.2 christos } 723 1.1.1.2 christos 724 1.1.1.2 christos /** Global respip actions test; apply raw config data and verify that 725 1.1.1.2 christos * all the nodes in the respip set, looked up by address, have expected 726 1.1.1.2 christos * actions */ 727 1.1.1.2 christos static void 728 1.1.1.2 christos respip_conf_actions_test(void) 729 1.1.1.2 christos { 730 1.1.1.2 christos addr_action_t config_response_ip[] = { 731 1.1.1.2 christos {"192.0.1.0/24", "deny", respip_deny}, 732 1.1.1.2 christos {"192.0.2.0/24", "redirect", respip_redirect}, 733 1.1.1.2 christos {"192.0.3.0/26", "inform", respip_inform}, 734 1.1.1.2 christos {"192.0.4.0/27", "inform_deny", respip_inform_deny}, 735 1.1.1.2 christos {"2001:db8:1::/48", "always_transparent", respip_always_transparent}, 736 1.1.1.2 christos {"2001:db8:2::/49", "always_refuse", respip_always_refuse}, 737 1.1.1.2 christos {"2001:db8:3::/50", "always_nxdomain", respip_always_nxdomain}, 738 1.1.1.2 christos }; 739 1.1.1.2 christos int i; 740 1.1.1.2 christos struct respip_set* set = respip_set_create(); 741 1.1.1.2 christos struct config_file cfg; 742 1.1.1.2 christos int clen = (int)(sizeof(config_response_ip) / sizeof(addr_action_t)); 743 1.1.1.2 christos 744 1.1.1.2 christos unit_assert(set); 745 1.1.1.2 christos unit_show_feature("global respip config actions apply"); 746 1.1.1.2 christos memset(&cfg, 0, sizeof(cfg)); 747 1.1.1.2 christos for(i=0; i<clen; i++) { 748 1.1.1.2 christos char* ip = strdup(config_response_ip[i].ip); 749 1.1.1.2 christos char* sact = strdup(config_response_ip[i].sact); 750 1.1.1.2 christos unit_assert(ip && sact); 751 1.1.1.2 christos if(!cfg_str2list_insert(&cfg.respip_actions, ip, sact)) 752 1.1.1.2 christos unit_assert(0); 753 1.1.1.2 christos } 754 1.1.1.2 christos unit_assert(respip_global_apply_cfg(set, &cfg)); 755 1.1.1.2 christos verify_respip_set_actions(set, config_response_ip, clen); 756 1.1.1.2 christos 757 1.1.1.2 christos respip_set_delete(set); 758 1.1.1.2 christos config_deldblstrlist(cfg.respip_actions); 759 1.1.1.2 christos } 760 1.1.1.2 christos 761 1.1.1.2 christos /** Per-view respip actions test; apply raw configuration with two views 762 1.1.1.2 christos * and verify that actions are as expected in respip sets of both views */ 763 1.1.1.2 christos static void 764 1.1.1.2 christos respip_view_conf_actions_test(void) 765 1.1.1.2 christos { 766 1.1.1.2 christos addr_action_t config_response_ip_view1[] = { 767 1.1.1.2 christos {"192.0.1.0/24", "deny", respip_deny}, 768 1.1.1.2 christos {"192.0.2.0/24", "redirect", respip_redirect}, 769 1.1.1.2 christos {"192.0.3.0/26", "inform", respip_inform}, 770 1.1.1.2 christos {"192.0.4.0/27", "inform_deny", respip_inform_deny}, 771 1.1.1.2 christos }; 772 1.1.1.2 christos addr_action_t config_response_ip_view2[] = { 773 1.1.1.2 christos {"2001:db8:1::/48", "always_transparent", respip_always_transparent}, 774 1.1.1.2 christos {"2001:db8:2::/49", "always_refuse", respip_always_refuse}, 775 1.1.1.2 christos {"2001:db8:3::/50", "always_nxdomain", respip_always_nxdomain}, 776 1.1.1.2 christos }; 777 1.1.1.2 christos int i; 778 1.1.1.2 christos struct config_file cfg; 779 1.1.1.2 christos int clen1 = (int)(sizeof(config_response_ip_view1) / sizeof(addr_action_t)); 780 1.1.1.2 christos int clen2 = (int)(sizeof(config_response_ip_view2) / sizeof(addr_action_t)); 781 1.1.1.2 christos struct config_view* cv1; 782 1.1.1.2 christos struct config_view* cv2; 783 1.1.1.2 christos int have_respip_cfg = 0; 784 1.1.1.2 christos struct views* views = NULL; 785 1.1.1.2 christos struct view* v = NULL; 786 1.1.1.2 christos 787 1.1.1.2 christos unit_show_feature("per-view respip config actions apply"); 788 1.1.1.2 christos memset(&cfg, 0, sizeof(cfg)); 789 1.1.1.2 christos cv1 = (struct config_view*)calloc(1, sizeof(struct config_view)); 790 1.1.1.2 christos cv2 = (struct config_view*)calloc(1, sizeof(struct config_view)); 791 1.1.1.2 christos unit_assert(cv1 && cv2); 792 1.1.1.2 christos cv1->name = strdup("view1"); 793 1.1.1.2 christos cv2->name = strdup("view2"); 794 1.1.1.2 christos unit_assert(cv1->name && cv2->name); 795 1.1.1.2 christos cv1->next = cv2; 796 1.1.1.2 christos cfg.views = cv1; 797 1.1.1.2 christos 798 1.1.1.2 christos for(i=0; i<clen1; i++) { 799 1.1.1.2 christos char* ip = strdup(config_response_ip_view1[i].ip); 800 1.1.1.2 christos char* sact = strdup(config_response_ip_view1[i].sact); 801 1.1.1.2 christos unit_assert(ip && sact); 802 1.1.1.2 christos if(!cfg_str2list_insert(&cv1->respip_actions, ip, sact)) 803 1.1.1.2 christos unit_assert(0); 804 1.1.1.2 christos } 805 1.1.1.2 christos for(i=0; i<clen2; i++) { 806 1.1.1.2 christos char* ip = strdup(config_response_ip_view2[i].ip); 807 1.1.1.2 christos char* sact = strdup(config_response_ip_view2[i].sact); 808 1.1.1.2 christos unit_assert(ip && sact); 809 1.1.1.2 christos if(!cfg_str2list_insert(&cv2->respip_actions, ip, sact)) 810 1.1.1.2 christos unit_assert(0); 811 1.1.1.2 christos } 812 1.1.1.2 christos views = views_create(); 813 1.1.1.2 christos unit_assert(views); 814 1.1.1.2 christos unit_assert(views_apply_cfg(views, &cfg)); 815 1.1.1.2 christos unit_assert(respip_views_apply_cfg(views, &cfg, &have_respip_cfg)); 816 1.1.1.2 christos 817 1.1.1.2 christos /* now verify the respip sets in each view */ 818 1.1.1.2 christos v = views_find_view(views, "view1", 0); 819 1.1.1.2 christos unit_assert(v); 820 1.1.1.2 christos verify_respip_set_actions(v->respip_set, config_response_ip_view1, clen1); 821 1.1.1.2 christos lock_rw_unlock(&v->lock); 822 1.1.1.2 christos v = views_find_view(views, "view2", 0); 823 1.1.1.2 christos unit_assert(v); 824 1.1.1.2 christos verify_respip_set_actions(v->respip_set, config_response_ip_view2, clen2); 825 1.1.1.2 christos lock_rw_unlock(&v->lock); 826 1.1.1.2 christos 827 1.1.1.2 christos views_delete(views); 828 1.1.1.2 christos free(cv1->name); 829 1.1.1.2 christos free(cv1); 830 1.1.1.2 christos free(cv2->name); 831 1.1.1.2 christos free(cv2); 832 1.1.1.2 christos } 833 1.1.1.2 christos 834 1.1.1.2 christos typedef struct addr_data {char* ip; char* data;} addr_data_t; 835 1.1.1.2 christos 836 1.1.1.2 christos /** find the respip address node in the specified tree (by address lookup) 837 1.1.1.2 christos * and verify type and address of the specified rdata (by index) in this 838 1.1.1.2 christos * node's rrset */ 839 1.1.1.2 christos static void 840 1.1.1.2 christos verify_rrset(struct respip_set* set, const char* ipstr, 841 1.1.1.2 christos const char* rdatastr, size_t rdi, uint16_t type) 842 1.1.1.2 christos { 843 1.1.1.2 christos struct sockaddr_storage addr; 844 1.1.1.2 christos int net; 845 1.1.1.2 christos char buf[65536]; 846 1.1.1.2 christos socklen_t addrlen; 847 1.1.1.2 christos struct rbtree_type* tree; 848 1.1.1.2 christos struct resp_addr* node; 849 1.1.1.2 christos const struct ub_packed_rrset_key* rrs; 850 1.1.1.2 christos 851 1.1.1.2 christos netblockstrtoaddr(ipstr, UNBOUND_DNS_PORT, &addr, &addrlen, &net); 852 1.1.1.2 christos tree = respip_set_get_tree(set); 853 1.1.1.2 christos node = (struct resp_addr*)addr_tree_find(tree, &addr, addrlen, net); 854 1.1.1.2 christos unit_assert(node); 855 1.1.1.2 christos unit_assert((rrs = resp_addr_get_rrset(node))); 856 1.1.1.2 christos unit_assert(ntohs(rrs->rk.type) == type); 857 1.1.1.2 christos packed_rr_to_string((struct ub_packed_rrset_key*)rrs, 858 1.1.1.2 christos rdi, 0, buf, sizeof(buf)); 859 1.1.1.2 christos unit_assert(strstr(buf, rdatastr)); 860 1.1.1.2 christos } 861 1.1.1.2 christos 862 1.1.1.2 christos /** Dataset used to test redirect rrset initialization for both 863 1.1.1.2 christos * global and per-view respip redirect configuration */ 864 1.1.1.2 christos static addr_data_t config_response_ip_data[] = { 865 1.1.1.2 christos {"192.0.1.0/24", "A 1.2.3.4"}, 866 1.1.1.2 christos {"192.0.1.0/24", "A 11.12.13.14"}, 867 1.1.1.2 christos {"192.0.2.0/24", "CNAME www.example.com."}, 868 1.1.1.2 christos {"2001:db8:1::/48", "AAAA 2001:db8:1::2:1"}, 869 1.1.1.2 christos }; 870 1.1.1.2 christos 871 1.1.1.2 christos /** Populate raw respip redirect config data, used for both global and 872 1.1.1.2 christos * view-based respip redirect test case */ 873 1.1.1.2 christos static void 874 1.1.1.2 christos cfg_insert_respip_data(struct config_str2list** respip_actions, 875 1.1.1.2 christos struct config_str2list** respip_data) 876 1.1.1.2 christos { 877 1.1.1.2 christos int clen = (int)(sizeof(config_response_ip_data) / sizeof(addr_data_t)); 878 1.1.1.2 christos int i = 0; 879 1.1.1.2 christos 880 1.1.1.2 christos /* insert actions (duplicate netblocks don't matter) */ 881 1.1.1.2 christos for(i=0; i<clen; i++) { 882 1.1.1.2 christos char* ip = strdup(config_response_ip_data[i].ip); 883 1.1.1.2 christos char* sact = strdup("redirect"); 884 1.1.1.2 christos unit_assert(ip && sact); 885 1.1.1.2 christos if(!cfg_str2list_insert(respip_actions, ip, sact)) 886 1.1.1.2 christos unit_assert(0); 887 1.1.1.2 christos } 888 1.1.1.2 christos /* insert data */ 889 1.1.1.2 christos for(i=0; i<clen; i++) { 890 1.1.1.2 christos char* ip = strdup(config_response_ip_data[i].ip); 891 1.1.1.2 christos char* data = strdup(config_response_ip_data[i].data); 892 1.1.1.2 christos unit_assert(ip && data); 893 1.1.1.2 christos if(!cfg_str2list_insert(respip_data, ip, data)) 894 1.1.1.2 christos unit_assert(0); 895 1.1.1.2 christos } 896 1.1.1.2 christos } 897 1.1.1.2 christos 898 1.1.1.2 christos /** Test global respip redirect w/ data directives */ 899 1.1.1.2 christos static void 900 1.1.1.2 christos respip_conf_data_test(void) 901 1.1.1.2 christos { 902 1.1.1.2 christos struct respip_set* set = respip_set_create(); 903 1.1.1.2 christos struct config_file cfg; 904 1.1.1.2 christos 905 1.1.1.2 christos unit_show_feature("global respip config data apply"); 906 1.1.1.2 christos memset(&cfg, 0, sizeof(cfg)); 907 1.1.1.2 christos 908 1.1.1.2 christos cfg_insert_respip_data(&cfg.respip_actions, &cfg.respip_data); 909 1.1.1.2 christos 910 1.1.1.2 christos /* apply configuration and verify rrsets */ 911 1.1.1.2 christos unit_assert(respip_global_apply_cfg(set, &cfg)); 912 1.1.1.2 christos verify_rrset(set, "192.0.1.0/24", "1.2.3.4", 0, LDNS_RR_TYPE_A); 913 1.1.1.2 christos verify_rrset(set, "192.0.1.0/24", "11.12.13.14", 1, LDNS_RR_TYPE_A); 914 1.1.1.2 christos verify_rrset(set, "192.0.2.0/24", "www.example.com", 0, LDNS_RR_TYPE_CNAME); 915 1.1.1.2 christos verify_rrset(set, "2001:db8:1::/48", "2001:db8:1::2:1", 0, LDNS_RR_TYPE_AAAA); 916 1.1.1.2 christos 917 1.1.1.2 christos respip_set_delete(set); 918 1.1.1.2 christos } 919 1.1.1.2 christos 920 1.1.1.2 christos /** Test per-view respip redirect w/ data directives */ 921 1.1.1.2 christos static void 922 1.1.1.2 christos respip_view_conf_data_test(void) 923 1.1.1.2 christos { 924 1.1.1.2 christos struct config_file cfg; 925 1.1.1.2 christos struct config_view* cv; 926 1.1.1.2 christos int have_respip_cfg = 0; 927 1.1.1.2 christos struct views* views = NULL; 928 1.1.1.2 christos struct view* v = NULL; 929 1.1.1.2 christos 930 1.1.1.2 christos unit_show_feature("per-view respip config data apply"); 931 1.1.1.2 christos memset(&cfg, 0, sizeof(cfg)); 932 1.1.1.2 christos cv = (struct config_view*)calloc(1, sizeof(struct config_view)); 933 1.1.1.2 christos unit_assert(cv); 934 1.1.1.2 christos cv->name = strdup("view1"); 935 1.1.1.2 christos unit_assert(cv->name); 936 1.1.1.2 christos cfg.views = cv; 937 1.1.1.2 christos cfg_insert_respip_data(&cv->respip_actions, &cv->respip_data); 938 1.1.1.2 christos views = views_create(); 939 1.1.1.2 christos unit_assert(views); 940 1.1.1.2 christos unit_assert(views_apply_cfg(views, &cfg)); 941 1.1.1.2 christos 942 1.1.1.2 christos /* apply configuration and verify rrsets */ 943 1.1.1.2 christos unit_assert(respip_views_apply_cfg(views, &cfg, &have_respip_cfg)); 944 1.1.1.2 christos v = views_find_view(views, "view1", 0); 945 1.1.1.2 christos unit_assert(v); 946 1.1.1.2 christos verify_rrset(v->respip_set, "192.0.1.0/24", "1.2.3.4", 947 1.1.1.2 christos 0, LDNS_RR_TYPE_A); 948 1.1.1.2 christos verify_rrset(v->respip_set, "192.0.1.0/24", "11.12.13.14", 949 1.1.1.2 christos 1, LDNS_RR_TYPE_A); 950 1.1.1.2 christos verify_rrset(v->respip_set, "192.0.2.0/24", "www.example.com", 951 1.1.1.2 christos 0, LDNS_RR_TYPE_CNAME); 952 1.1.1.2 christos verify_rrset(v->respip_set, "2001:db8:1::/48", "2001:db8:1::2:1", 953 1.1.1.2 christos 0, LDNS_RR_TYPE_AAAA); 954 1.1.1.2 christos lock_rw_unlock(&v->lock); 955 1.1.1.2 christos 956 1.1.1.2 christos views_delete(views); 957 1.1.1.2 christos free(cv->name); 958 1.1.1.2 christos free(cv); 959 1.1.1.2 christos } 960 1.1.1.2 christos 961 1.1.1.2 christos /** respip unit tests */ 962 1.1.1.2 christos static void respip_test(void) 963 1.1.1.2 christos { 964 1.1.1.2 christos respip_view_conf_data_test(); 965 1.1.1.2 christos respip_conf_data_test(); 966 1.1.1.2 christos respip_view_conf_actions_test(); 967 1.1.1.2 christos respip_conf_actions_test(); 968 1.1.1.2 christos } 969 1.1.1.2 christos 970 1.1.1.8 christos #include "util/regional.h" 971 1.1.1.8 christos #include "sldns/sbuffer.h" 972 1.1.1.8 christos #include "util/data/dname.h" 973 1.1.1.8 christos #include "util/data/msgreply.h" 974 1.1.1.8 christos #include "util/data/msgencode.h" 975 1.1.1.8 christos #include "sldns/str2wire.h" 976 1.1.1.8 christos 977 1.1.1.8 christos static void edns_ede_encode_setup(struct edns_data* edns, 978 1.1.1.8 christos struct regional* region) 979 1.1.1.8 christos { 980 1.1.1.8 christos memset(edns, 0, sizeof(*edns)); 981 1.1.1.8 christos edns->edns_present = 1; 982 1.1.1.8 christos edns->edns_version = EDNS_ADVERTISED_VERSION; 983 1.1.1.8 christos edns->udp_size = EDNS_ADVERTISED_SIZE; 984 1.1.1.8 christos edns->bits &= EDNS_DO; 985 1.1.1.8 christos /* Fill up opt_list_out with EDEs */ 986 1.1.1.8 christos unit_assert( 987 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 988 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 989 1.1.1.8 christos unit_assert( 990 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 991 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 992 1.1.1.8 christos unit_assert( 993 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 994 1.1.1.8 christos LDNS_EDE_BLOCKED, "Too long blocked text")); 995 1.1.1.8 christos unit_assert( 996 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 997 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 998 1.1.1.8 christos unit_assert( 999 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 1000 1.1.1.8 christos LDNS_EDE_BLOCKED, "Too long blocked text")); 1001 1.1.1.8 christos /* Fill up opt_list_inplace_cb_out with EDEs */ 1002 1.1.1.8 christos unit_assert( 1003 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1004 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 1005 1.1.1.8 christos unit_assert( 1006 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1007 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 1008 1.1.1.8 christos unit_assert( 1009 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1010 1.1.1.8 christos LDNS_EDE_BLOCKED, "Too long blocked text")); 1011 1.1.1.8 christos unit_assert( 1012 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1013 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 1014 1.1.1.8 christos unit_assert( 1015 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1016 1.1.1.8 christos LDNS_EDE_BLOCKED, "Too long blocked text")); 1017 1.1.1.8 christos /* append another EDNS option to both lists */ 1018 1.1.1.8 christos unit_assert( 1019 1.1.1.8 christos edns_opt_list_append(&edns->opt_list_out, 1020 1.1.1.8 christos LDNS_EDNS_UNBOUND_CACHEDB_TESTFRAME_TEST, 0, NULL, region)); 1021 1.1.1.8 christos unit_assert( 1022 1.1.1.8 christos edns_opt_list_append(&edns->opt_list_inplace_cb_out, 1023 1.1.1.8 christos LDNS_EDNS_UNBOUND_CACHEDB_TESTFRAME_TEST, 0, NULL, region)); 1024 1.1.1.8 christos /* append LDNS_EDE_OTHER at the end of both lists */ 1025 1.1.1.8 christos unit_assert( 1026 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_out, region, 1027 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 1028 1.1.1.8 christos unit_assert( 1029 1.1.1.8 christos edns_opt_list_append_ede(&edns->opt_list_inplace_cb_out, region, 1030 1.1.1.8 christos LDNS_EDE_OTHER, "Too long other text")); 1031 1.1.1.8 christos } 1032 1.1.1.8 christos 1033 1.1.1.8 christos static void edns_ede_encode_encodedecode(struct query_info* qinfo, 1034 1.1.1.8 christos struct reply_info* rep, struct regional* region, 1035 1.1.1.8 christos struct edns_data* edns, sldns_buffer* pkt) 1036 1.1.1.8 christos { 1037 1.1.1.8 christos /* encode */ 1038 1.1.1.8 christos unit_assert( 1039 1.1.1.8 christos reply_info_answer_encode(qinfo, rep, 1, rep->flags, pkt, 1040 1.1.1.8 christos 0, 0, region, 65535, edns, 0, 0)); 1041 1.1.1.8 christos /* buffer ready for reading; skip after the question section */ 1042 1.1.1.8 christos sldns_buffer_skip(pkt, LDNS_HEADER_SIZE); 1043 1.1.1.8 christos (void)query_dname_len(pkt); 1044 1.1.1.8 christos sldns_buffer_skip(pkt, 2 + 2); 1045 1.1.1.8 christos /* decode */ 1046 1.1.1.8 christos unit_assert(parse_edns_from_query_pkt(pkt, edns, NULL, NULL, NULL, 0, 1047 1.1.1.9 christos region, NULL) == 0); 1048 1.1.1.8 christos } 1049 1.1.1.8 christos 1050 1.1.1.8 christos static void edns_ede_encode_check(struct edns_data* edns, int* found_ede, 1051 1.1.1.8 christos int* found_ede_other, int* found_ede_txt, int* found_other_edns) 1052 1.1.1.8 christos { 1053 1.1.1.8 christos struct edns_option* opt; 1054 1.1.1.8 christos for(opt = edns->opt_list_in; opt; opt = opt->next) { 1055 1.1.1.8 christos if(opt->opt_code == LDNS_EDNS_EDE) { 1056 1.1.1.8 christos (*found_ede)++; 1057 1.1.1.8 christos if(opt->opt_len > 2) 1058 1.1.1.8 christos (*found_ede_txt)++; 1059 1.1.1.8 christos if(opt->opt_len >= 2 && sldns_read_uint16( 1060 1.1.1.8 christos opt->opt_data) == LDNS_EDE_OTHER) 1061 1.1.1.8 christos (*found_ede_other)++; 1062 1.1.1.8 christos } else { 1063 1.1.1.8 christos (*found_other_edns)++; 1064 1.1.1.8 christos } 1065 1.1.1.8 christos } 1066 1.1.1.8 christos 1067 1.1.1.8 christos } 1068 1.1.1.8 christos 1069 1.1.1.8 christos static void edns_ede_encode_fit_test(struct query_info* qinfo, 1070 1.1.1.8 christos struct reply_info* rep, struct regional* region) 1071 1.1.1.8 christos { 1072 1.1.1.8 christos struct edns_data edns; 1073 1.1.1.8 christos int found_ede = 0, found_ede_other = 0, found_ede_txt = 0; 1074 1.1.1.8 christos int found_other_edns = 0; 1075 1.1.1.8 christos sldns_buffer* pkt = sldns_buffer_new(65535); 1076 1.1.1.8 christos unit_assert(pkt); 1077 1.1.1.8 christos edns_ede_encode_setup(&edns, region); 1078 1.1.1.8 christos /* leave the pkt buffer as is; everything should fit */ 1079 1.1.1.8 christos edns_ede_encode_encodedecode(qinfo, rep, region, &edns, pkt); 1080 1.1.1.8 christos edns_ede_encode_check(&edns, &found_ede, &found_ede_other, 1081 1.1.1.8 christos &found_ede_txt, &found_other_edns); 1082 1.1.1.8 christos unit_assert(found_ede == 12); 1083 1.1.1.8 christos unit_assert(found_ede_other == 8); 1084 1.1.1.8 christos unit_assert(found_ede_txt == 12); 1085 1.1.1.8 christos unit_assert(found_other_edns == 2); 1086 1.1.1.8 christos /* cleanup */ 1087 1.1.1.8 christos sldns_buffer_free(pkt); 1088 1.1.1.8 christos } 1089 1.1.1.8 christos 1090 1.1.1.8 christos static void edns_ede_encode_notxt_fit_test( struct query_info* qinfo, 1091 1.1.1.8 christos struct reply_info* rep, struct regional* region) 1092 1.1.1.8 christos { 1093 1.1.1.8 christos struct edns_data edns; 1094 1.1.1.8 christos sldns_buffer* pkt; 1095 1.1.1.8 christos uint16_t edns_field_size, ede_txt_size; 1096 1.1.1.8 christos int found_ede = 0, found_ede_other = 0, found_ede_txt = 0; 1097 1.1.1.8 christos int found_other_edns = 0; 1098 1.1.1.8 christos edns_ede_encode_setup(&edns, region); 1099 1.1.1.8 christos /* pkt buffer should fit everything if the ede txt is cropped. 1100 1.1.1.8 christos * OTHER EDE should not be there since it is useless without text. */ 1101 1.1.1.8 christos edns_field_size = calc_edns_field_size(&edns); 1102 1.1.1.8 christos (void)calc_ede_option_size(&edns, &ede_txt_size); 1103 1.1.1.8 christos pkt = sldns_buffer_new(LDNS_HEADER_SIZE 1104 1.1.1.8 christos + qinfo->qname_len 1105 1.1.1.8 christos + 2 + 2 /* qtype + qclass */ 1106 1.1.1.8 christos + 11 /* opt record */ 1107 1.1.1.8 christos + edns_field_size 1108 1.1.1.8 christos - ede_txt_size); 1109 1.1.1.8 christos unit_assert(pkt); 1110 1.1.1.8 christos edns_ede_encode_encodedecode(qinfo, rep, region, &edns, pkt); 1111 1.1.1.8 christos edns_ede_encode_check(&edns, &found_ede, &found_ede_other, 1112 1.1.1.8 christos &found_ede_txt, &found_other_edns); 1113 1.1.1.8 christos unit_assert(found_ede == 4); 1114 1.1.1.8 christos unit_assert(found_ede_other == 0); 1115 1.1.1.8 christos unit_assert(found_ede_txt == 0); 1116 1.1.1.8 christos unit_assert(found_other_edns == 2); 1117 1.1.1.8 christos /* cleanup */ 1118 1.1.1.8 christos sldns_buffer_free(pkt); 1119 1.1.1.8 christos } 1120 1.1.1.8 christos 1121 1.1.1.8 christos static void edns_ede_encode_no_fit_test( struct query_info* qinfo, 1122 1.1.1.8 christos struct reply_info* rep, struct regional* region) 1123 1.1.1.8 christos { 1124 1.1.1.8 christos struct edns_data edns; 1125 1.1.1.8 christos sldns_buffer* pkt; 1126 1.1.1.8 christos uint16_t edns_field_size, ede_size, ede_txt_size; 1127 1.1.1.8 christos int found_ede = 0, found_ede_other = 0, found_ede_txt = 0; 1128 1.1.1.8 christos int found_other_edns = 0; 1129 1.1.1.8 christos edns_ede_encode_setup(&edns, region); 1130 1.1.1.8 christos /* pkt buffer should fit only non-EDE options. */ 1131 1.1.1.8 christos edns_field_size = calc_edns_field_size(&edns); 1132 1.1.1.8 christos ede_size = calc_ede_option_size(&edns, &ede_txt_size); 1133 1.1.1.8 christos pkt = sldns_buffer_new(LDNS_HEADER_SIZE 1134 1.1.1.8 christos + qinfo->qname_len 1135 1.1.1.8 christos + 2 + 2 /* qtype + qclass */ 1136 1.1.1.8 christos + 11 /* opt record */ 1137 1.1.1.8 christos + edns_field_size 1138 1.1.1.8 christos - ede_size); 1139 1.1.1.8 christos unit_assert(pkt); 1140 1.1.1.8 christos edns_ede_encode_encodedecode(qinfo, rep, region, &edns, pkt); 1141 1.1.1.8 christos edns_ede_encode_check(&edns, &found_ede, &found_ede_other, 1142 1.1.1.8 christos &found_ede_txt, &found_other_edns); 1143 1.1.1.8 christos unit_assert(found_ede == 0); 1144 1.1.1.8 christos unit_assert(found_ede_other == 0); 1145 1.1.1.8 christos unit_assert(found_ede_txt == 0); 1146 1.1.1.8 christos unit_assert(found_other_edns == 2); 1147 1.1.1.8 christos /* cleanup */ 1148 1.1.1.8 christos sldns_buffer_free(pkt); 1149 1.1.1.8 christos } 1150 1.1.1.8 christos 1151 1.1.1.8 christos /** test optional EDE encoding with various buffer 1152 1.1.1.8 christos * available sizes */ 1153 1.1.1.8 christos static void edns_ede_answer_encode_test(void) 1154 1.1.1.8 christos { 1155 1.1.1.8 christos struct regional* region = regional_create(); 1156 1.1.1.8 christos struct reply_info* rep; 1157 1.1.1.8 christos struct query_info qinfo; 1158 1.1.1.8 christos unit_show_feature("edns ede optional encoding"); 1159 1.1.1.8 christos unit_assert(region); 1160 1.1.1.8 christos rep = construct_reply_info_base(region, 1161 1.1.1.8 christos LDNS_RCODE_NOERROR | BIT_QR, 1, 1162 1.1.1.9 christos 3600, 3600, 3600, 0, 1163 1.1.1.8 christos 0, 0, 0, 0, 1164 1.1.1.8 christos sec_status_unchecked, LDNS_EDE_NONE); 1165 1.1.1.8 christos unit_assert(rep); 1166 1.1.1.8 christos memset(&qinfo, 0, sizeof(qinfo)); 1167 1.1.1.8 christos qinfo.qname = sldns_str2wire_dname("encode.ede.", &qinfo.qname_len); 1168 1.1.1.8 christos unit_assert(qinfo.qname); 1169 1.1.1.8 christos qinfo.qtype = LDNS_RR_TYPE_TXT; 1170 1.1.1.8 christos qinfo.qclass = LDNS_RR_CLASS_IN; 1171 1.1.1.8 christos 1172 1.1.1.8 christos edns_ede_encode_fit_test(&qinfo, rep, region); 1173 1.1.1.8 christos edns_ede_encode_notxt_fit_test(&qinfo, rep, region); 1174 1.1.1.8 christos edns_ede_encode_no_fit_test(&qinfo, rep, region); 1175 1.1.1.8 christos 1176 1.1.1.8 christos /* cleanup */ 1177 1.1.1.8 christos free(qinfo.qname); 1178 1.1.1.8 christos regional_free_all(region); 1179 1.1.1.8 christos regional_destroy(region); 1180 1.1.1.8 christos } 1181 1.1.1.8 christos 1182 1.1.1.9 christos #include "services/localzone.h" 1183 1.1.1.9 christos /* Utility function that compares two localzone trees */ 1184 1.1.1.9 christos static void compare_localzone_trees(struct local_zones* z1, 1185 1.1.1.9 christos struct local_zones* z2) 1186 1.1.1.9 christos { 1187 1.1.1.9 christos struct local_zone *node1, *node2; 1188 1.1.1.9 christos lock_rw_rdlock(&z1->lock); 1189 1.1.1.9 christos lock_rw_rdlock(&z2->lock); 1190 1.1.1.9 christos /* size should be the same */ 1191 1.1.1.9 christos unit_assert(z1->ztree.count == z2->ztree.count); 1192 1.1.1.9 christos for(node1=(struct local_zone*)rbtree_first(&z1->ztree), 1193 1.1.1.9 christos node2=(struct local_zone*)rbtree_first(&z2->ztree); 1194 1.1.1.9 christos (rbnode_type*)node1 != RBTREE_NULL && 1195 1.1.1.9 christos (rbnode_type*)node2 != RBTREE_NULL; 1196 1.1.1.9 christos node1=(struct local_zone*)rbtree_next((rbnode_type*)node1), 1197 1.1.1.9 christos node2=(struct local_zone*)rbtree_next((rbnode_type*)node2)) { 1198 1.1.1.9 christos int labs; 1199 1.1.1.9 christos /* the same zone should be at the same nodes */ 1200 1.1.1.9 christos unit_assert(!dname_lab_cmp( 1201 1.1.1.9 christos node1->name, node1->namelabs, 1202 1.1.1.9 christos node2->name, node2->namelabs, 1203 1.1.1.9 christos &labs)); 1204 1.1.1.9 christos /* the zone's parent should be the same on both nodes */ 1205 1.1.1.9 christos unit_assert( 1206 1.1.1.9 christos (node1->parent == NULL && node2->parent == NULL) || 1207 1.1.1.9 christos (node1->parent != NULL && node2->parent != NULL)); 1208 1.1.1.9 christos if(node1->parent) { 1209 1.1.1.9 christos unit_assert(!dname_lab_cmp( 1210 1.1.1.9 christos node1->parent->name, node1->parent->namelabs, 1211 1.1.1.9 christos node2->parent->name, node2->parent->namelabs, 1212 1.1.1.9 christos &labs)); 1213 1.1.1.9 christos } 1214 1.1.1.9 christos } 1215 1.1.1.9 christos lock_rw_unlock(&z1->lock); 1216 1.1.1.9 christos lock_rw_unlock(&z2->lock); 1217 1.1.1.9 christos } 1218 1.1.1.9 christos 1219 1.1.1.9 christos /* test that zone addition results in the same tree from both the configuration 1220 1.1.1.9 christos * file and the unbound-control commands */ 1221 1.1.1.9 christos static void localzone_parents_test(void) 1222 1.1.1.9 christos { 1223 1.1.1.9 christos struct local_zones *z1, *z2; 1224 1.1.1.9 christos size_t i; 1225 1.1.1.9 christos char* zone_data[] = { 1226 1.1.1.9 christos "one", 1227 1.1.1.9 christos "a.b.c.one", 1228 1.1.1.9 christos "b.c.one", 1229 1.1.1.9 christos "c.one", 1230 1.1.1.9 christos "two", 1231 1.1.1.9 christos "c.two", 1232 1.1.1.9 christos "b.c.two", 1233 1.1.1.9 christos "a.b.c.two", 1234 1.1.1.9 christos "a.b.c.three", 1235 1.1.1.9 christos "b.c.three", 1236 1.1.1.9 christos "c.three", 1237 1.1.1.9 christos "three", 1238 1.1.1.9 christos "c.four", 1239 1.1.1.9 christos "b.c.four", 1240 1.1.1.9 christos "a.b.c.four", 1241 1.1.1.9 christos "four", 1242 1.1.1.9 christos "." 1243 1.1.1.9 christos }; 1244 1.1.1.9 christos unit_show_feature("localzones parent calculation"); 1245 1.1.1.9 christos z1 = local_zones_create(); 1246 1.1.1.9 christos z2 = local_zones_create(); 1247 1.1.1.9 christos /* parse test data */ 1248 1.1.1.9 christos for(i=0; i<sizeof(zone_data)/sizeof(zone_data[0]); i++) { 1249 1.1.1.9 christos uint8_t* nm; 1250 1.1.1.9 christos int nmlabs; 1251 1.1.1.9 christos size_t nmlen; 1252 1.1.1.9 christos struct local_zone* z; 1253 1.1.1.9 christos 1254 1.1.1.9 christos /* This is the config way */ 1255 1.1.1.9 christos z = lz_enter_zone(z1, zone_data[i], "always_nxdomain", 1256 1.1.1.9 christos LDNS_RR_CLASS_IN); 1257 1.1.1.9 christos (void)z; /* please compiler when no threading and no lock 1258 1.1.1.9 christos code; the following line disappears and z stays unused */ 1259 1.1.1.9 christos lock_rw_unlock(&z->lock); 1260 1.1.1.9 christos lz_init_parents(z1); 1261 1.1.1.9 christos 1262 1.1.1.9 christos /* This is the unbound-control way */ 1263 1.1.1.9 christos nm = sldns_str2wire_dname(zone_data[i], &nmlen); 1264 1.1.1.9 christos if(!nm) unit_assert(0); 1265 1.1.1.9 christos nmlabs = dname_count_size_labels(nm, &nmlen); 1266 1.1.1.9 christos lock_rw_wrlock(&z2->lock); 1267 1.1.1.9 christos local_zones_add_zone(z2, nm, nmlen, nmlabs, LDNS_RR_CLASS_IN, 1268 1.1.1.9 christos local_zone_always_nxdomain); 1269 1.1.1.9 christos lock_rw_unlock(&z2->lock); 1270 1.1.1.9 christos } 1271 1.1.1.9 christos /* The trees should be the same, iterate and check the nodes */ 1272 1.1.1.9 christos compare_localzone_trees(z1, z2); 1273 1.1.1.9 christos 1274 1.1.1.9 christos /* cleanup */ 1275 1.1.1.9 christos local_zones_delete(z1); 1276 1.1.1.9 christos local_zones_delete(z2); 1277 1.1.1.9 christos } 1278 1.1.1.9 christos 1279 1.1.1.9 christos /** localzone unit tests */ 1280 1.1.1.9 christos static void localzone_test(void) 1281 1.1.1.9 christos { 1282 1.1.1.9 christos localzone_parents_test(); 1283 1.1.1.9 christos } 1284 1.1.1.9 christos 1285 1.1 christos void unit_show_func(const char* file, const char* func) 1286 1.1 christos { 1287 1.1 christos printf("test %s:%s\n", file, func); 1288 1.1 christos } 1289 1.1 christos 1290 1.1 christos void unit_show_feature(const char* feature) 1291 1.1 christos { 1292 1.1 christos printf("test %s functions\n", feature); 1293 1.1 christos } 1294 1.1 christos 1295 1.1.1.2 christos #ifdef USE_ECDSA_EVP_WORKAROUND 1296 1.1.1.2 christos void ecdsa_evp_workaround_init(void); 1297 1.1.1.2 christos #endif 1298 1.1.1.8 christos 1299 1.1 christos /** 1300 1.1 christos * Main unit test program. Setup, teardown and report errors. 1301 1.1 christos * @param argc: arg count. 1302 1.1 christos * @param argv: array of commandline arguments. 1303 1.1 christos * @return program failure if test fails. 1304 1.1 christos */ 1305 1.1 christos int 1306 1.1 christos main(int argc, char* argv[]) 1307 1.1 christos { 1308 1.1.1.7 christos checklock_start(); 1309 1.1 christos log_init(NULL, 0, NULL); 1310 1.1 christos if(argc != 1) { 1311 1.1 christos printf("usage: %s\n", argv[0]); 1312 1.1 christos printf("\tperforms unit tests.\n"); 1313 1.1 christos return 1; 1314 1.1 christos } 1315 1.1.1.6 christos /* Disable roundrobin for the unit tests */ 1316 1.1.1.6 christos RRSET_ROUNDROBIN = 0; 1317 1.1.1.6 christos #ifdef USE_LIBEVENT 1318 1.1.1.6 christos printf("Start of %s+libevent unit test.\n", PACKAGE_STRING); 1319 1.1.1.6 christos #else 1320 1.1 christos printf("Start of %s unit test.\n", PACKAGE_STRING); 1321 1.1.1.6 christos #endif 1322 1.1 christos #ifdef HAVE_SSL 1323 1.1.1.2 christos # ifdef HAVE_ERR_LOAD_CRYPTO_STRINGS 1324 1.1 christos ERR_load_crypto_strings(); 1325 1.1.1.2 christos # endif 1326 1.1 christos # ifdef USE_GOST 1327 1.1 christos (void)sldns_key_EVP_load_gost_id(); 1328 1.1 christos # endif 1329 1.1.1.2 christos # ifdef USE_ECDSA_EVP_WORKAROUND 1330 1.1.1.2 christos ecdsa_evp_workaround_init(); 1331 1.1.1.2 christos # endif 1332 1.1 christos #elif defined(HAVE_NSS) 1333 1.1 christos if(NSS_NoDB_Init(".") != SECSuccess) 1334 1.1 christos fatal_exit("could not init NSS"); 1335 1.1 christos #endif /* HAVE_SSL or HAVE_NSS*/ 1336 1.1.1.2 christos authzone_test(); 1337 1.1 christos neg_test(); 1338 1.1 christos rnd_test(); 1339 1.1.1.2 christos respip_test(); 1340 1.1 christos verify_test(); 1341 1.1 christos net_test(); 1342 1.1 christos config_memsize_test(); 1343 1.1 christos config_tag_test(); 1344 1.1 christos dname_test(); 1345 1.1 christos rtt_test(); 1346 1.1 christos anchors_test(); 1347 1.1 christos alloc_test(); 1348 1.1 christos regional_test(); 1349 1.1 christos lruhash_test(); 1350 1.1 christos slabhash_test(); 1351 1.1 christos infra_test(); 1352 1.1 christos ldns_test(); 1353 1.1.1.8 christos edns_cookie_test(); 1354 1.1.1.7 christos zonemd_test(); 1355 1.1.1.7 christos tcpreuse_test(); 1356 1.1 christos msgparse_test(); 1357 1.1.1.8 christos edns_ede_answer_encode_test(); 1358 1.1.1.9 christos localzone_test(); 1359 1.1.1.2 christos #ifdef CLIENT_SUBNET 1360 1.1.1.2 christos ecs_test(); 1361 1.1.1.2 christos #endif /* CLIENT_SUBNET */ 1362 1.1.1.9 christos #ifdef HAVE_NGTCP2 1363 1.1.1.9 christos doq_test(); 1364 1.1.1.9 christos #endif /* HAVE_NGTCP2 */ 1365 1.1.1.3 christos if(log_get_lock()) { 1366 1.1.1.5 christos lock_basic_destroy((lock_basic_type*)log_get_lock()); 1367 1.1.1.3 christos } 1368 1.1 christos checklock_stop(); 1369 1.1 christos printf("%d checks ok.\n", testcount); 1370 1.1 christos #ifdef HAVE_SSL 1371 1.1.1.7 christos # if defined(USE_GOST) 1372 1.1 christos sldns_key_EVP_unload_gost(); 1373 1.1 christos # endif 1374 1.1 christos # ifdef HAVE_OPENSSL_CONFIG 1375 1.1.1.2 christos # ifdef HAVE_EVP_CLEANUP 1376 1.1 christos EVP_cleanup(); 1377 1.1.1.2 christos # endif 1378 1.1.1.6 christos # if (OPENSSL_VERSION_NUMBER < 0x10100000) && !defined(OPENSSL_NO_ENGINE) && defined(HAVE_ENGINE_CLEANUP) 1379 1.1 christos ENGINE_cleanup(); 1380 1.1.1.6 christos # endif 1381 1.1 christos CONF_modules_free(); 1382 1.1 christos # endif 1383 1.1.1.2 christos # ifdef HAVE_CRYPTO_CLEANUP_ALL_EX_DATA 1384 1.1 christos CRYPTO_cleanup_all_ex_data(); 1385 1.1.1.2 christos # endif 1386 1.1.1.2 christos # ifdef HAVE_ERR_FREE_STRINGS 1387 1.1 christos ERR_free_strings(); 1388 1.1.1.2 christos # endif 1389 1.1.1.2 christos # ifdef HAVE_RAND_CLEANUP 1390 1.1 christos RAND_cleanup(); 1391 1.1.1.2 christos # endif 1392 1.1 christos #elif defined(HAVE_NSS) 1393 1.1 christos if(NSS_Shutdown() != SECSuccess) 1394 1.1 christos fatal_exit("could not shutdown NSS"); 1395 1.1 christos #endif /* HAVE_SSL or HAVE_NSS */ 1396 1.1 christos #ifdef HAVE_PTHREAD 1397 1.1 christos /* dlopen frees its thread specific state */ 1398 1.1 christos pthread_exit(NULL); 1399 1.1 christos #endif 1400 1.1 christos return 0; 1401 1.1 christos } 1402