1 /* $NetBSD: sig0_test.c,v 1.8 2015/07/08 17:28:55 christos Exp $ */ 2 3 /* 4 * Copyright (C) 2004, 2005, 2007-2009, 2012, 2015 Internet Systems Consortium, Inc. ("ISC") 5 * Copyright (C) 2000, 2001 Internet Software Consortium. 6 * 7 * Permission to use, copy, modify, and/or distribute this software for any 8 * purpose with or without fee is hereby granted, provided that the above 9 * copyright notice and this permission notice appear in all copies. 10 * 11 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH 12 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY 13 * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT, 14 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM 15 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE 16 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20 /* Id: sig0_test.c,v 1.19 2009/09/02 23:48:01 tbox Exp */ 21 22 #include <config.h> 23 24 #include <stddef.h> 25 #include <stdlib.h> 26 #include <string.h> 27 28 #include <isc/app.h> 29 #include <isc/boolean.h> 30 #include <isc/assertions.h> 31 #include <isc/commandline.h> 32 #include <isc/entropy.h> 33 #include <isc/error.h> 34 #include <isc/log.h> 35 #include <isc/mem.h> 36 #include <isc/mutex.h> 37 #include <isc/net.h> 38 #include <isc/task.h> 39 #include <isc/timer.h> 40 #include <isc/socket.h> 41 #include <isc/util.h> 42 43 #include <dns/dnssec.h> 44 #include <dns/events.h> 45 #include <dns/fixedname.h> 46 #include <dns/keyvalues.h> 47 #include <dns/masterdump.h> 48 #include <dns/message.h> 49 #include <dns/name.h> 50 #include <dns/rdataset.h> 51 #include <dns/resolver.h> 52 #include <dns/result.h> 53 #include <dns/types.h> 54 55 #include <dst/result.h> 56 #include <dst/dst.h> 57 58 #define CHECK(str, x) { \ 59 if ((x) != ISC_R_SUCCESS) { \ 60 printf("%s: %s\n", (str), isc_result_totext(x)); \ 61 exit(-1); \ 62 } \ 63 } 64 65 isc_mutex_t lock; 66 dst_key_t *key; 67 isc_mem_t *mctx; 68 unsigned char qdata[1024], rdata[1024]; 69 isc_buffer_t qbuffer, rbuffer; 70 isc_taskmgr_t *taskmgr; 71 isc_entropy_t *ent = NULL; 72 isc_task_t *task1; 73 isc_log_t *lctx = NULL; 74 isc_logconfig_t *logconfig = NULL; 75 isc_socket_t *s; 76 isc_sockaddr_t address; 77 char output[10 * 1024]; 78 isc_buffer_t outbuf; 79 static const dns_master_style_t *style = &dns_master_style_debug; 80 81 static void 82 senddone(isc_task_t *task, isc_event_t *event) { 83 isc_socketevent_t *sevent = (isc_socketevent_t *)event; 84 85 REQUIRE(sevent != NULL); 86 REQUIRE(sevent->ev_type == ISC_SOCKEVENT_SENDDONE); 87 REQUIRE(task == task1); 88 89 printf("senddone\n"); 90 91 isc_event_free(&event); 92 } 93 94 static void 95 recvdone(isc_task_t *task, isc_event_t *event) { 96 isc_socketevent_t *sevent = (isc_socketevent_t *)event; 97 isc_buffer_t source; 98 isc_result_t result; 99 dns_message_t *response; 100 101 REQUIRE(sevent != NULL); 102 REQUIRE(sevent->ev_type == ISC_SOCKEVENT_RECVDONE); 103 REQUIRE(task == task1); 104 105 printf("recvdone\n"); 106 if (sevent->result != ISC_R_SUCCESS) { 107 printf("failed\n"); 108 exit(-1); 109 } 110 111 isc_buffer_init(&source, sevent->region.base, sevent->region.length); 112 isc_buffer_add(&source, sevent->n); 113 114 response = NULL; 115 result = dns_message_create(mctx, DNS_MESSAGE_INTENTPARSE, &response); 116 CHECK("dns_message_create", result); 117 result = dns_message_parse(response, &source, 0); 118 CHECK("dns_message_parse", result); 119 120 isc_buffer_init(&outbuf, output, sizeof(output)); 121 result = dns_message_totext(response, style, 0, &outbuf); 122 CHECK("dns_message_totext", result); 123 printf("%.*s\n", (int)isc_buffer_usedlength(&outbuf), 124 (char *)isc_buffer_base(&outbuf)); 125 126 dns_message_destroy(&response); 127 isc_event_free(&event); 128 129 isc_app_shutdown(); 130 } 131 132 static void 133 buildquery(void) { 134 isc_result_t result; 135 dns_rdataset_t *question = NULL; 136 dns_name_t *qname = NULL; 137 isc_region_t r, inr; 138 dns_message_t *query; 139 char nametext[] = "host.example"; 140 isc_buffer_t namesrc, namedst; 141 unsigned char namedata[256]; 142 isc_sockaddr_t sa; 143 dns_compress_t cctx; 144 145 query = NULL; 146 result = dns_message_create(mctx, DNS_MESSAGE_INTENTRENDER, &query); 147 CHECK("dns_message_create", result); 148 result = dns_message_setsig0key(query, key); 149 CHECK("dns_message_setsig0key", result); 150 151 result = dns_message_gettemprdataset(query, &question); 152 CHECK("dns_message_gettemprdataset", result); 153 dns_rdataset_makequestion(question, dns_rdataclass_in, 154 dns_rdatatype_a); 155 result = dns_message_gettempname(query, &qname); 156 CHECK("dns_message_gettempname", result); 157 isc_buffer_init(&namesrc, nametext, strlen(nametext)); 158 isc_buffer_add(&namesrc, strlen(nametext)); 159 isc_buffer_init(&namedst, namedata, sizeof(namedata)); 160 dns_name_init(qname, NULL); 161 result = dns_name_fromtext(qname, &namesrc, dns_rootname, 0, &namedst); 162 CHECK("dns_name_fromtext", result); 163 ISC_LIST_APPEND(qname->list, question, link); 164 dns_message_addname(query, qname, DNS_SECTION_QUESTION); 165 166 isc_buffer_init(&qbuffer, qdata, sizeof(qdata)); 167 168 result = dns_compress_init(&cctx, -1, mctx); 169 CHECK("dns_compress_init", result); 170 result = dns_message_renderbegin(query, &cctx, &qbuffer); 171 CHECK("dns_message_renderbegin", result); 172 result = dns_message_rendersection(query, DNS_SECTION_QUESTION, 0); 173 CHECK("dns_message_rendersection(question)", result); 174 result = dns_message_rendersection(query, DNS_SECTION_ANSWER, 0); 175 CHECK("dns_message_rendersection(answer)", result); 176 result = dns_message_rendersection(query, DNS_SECTION_AUTHORITY, 0); 177 CHECK("dns_message_rendersection(auth)", result); 178 result = dns_message_rendersection(query, DNS_SECTION_ADDITIONAL, 0); 179 CHECK("dns_message_rendersection(add)", result); 180 result = dns_message_renderend(query); 181 CHECK("dns_message_renderend", result); 182 dns_compress_invalidate(&cctx); 183 184 isc_buffer_init(&outbuf, output, sizeof(output)); 185 result = dns_message_totext(query, style, 0, &outbuf); 186 CHECK("dns_message_totext", result); 187 printf("%.*s\n", (int)isc_buffer_usedlength(&outbuf), 188 (char *)isc_buffer_base(&outbuf)); 189 190 isc_buffer_usedregion(&qbuffer, &r); 191 isc_sockaddr_any(&sa); 192 result = isc_socket_bind(s, &sa, 0); 193 CHECK("isc_socket_bind", result); 194 result = isc_socket_sendto(s, &r, task1, senddone, NULL, &address, 195 NULL); 196 CHECK("isc_socket_sendto", result); 197 198 inr.base = rdata; 199 inr.length = sizeof(rdata); 200 result = isc_socket_recv(s, &inr, 1, task1, recvdone, NULL); 201 CHECK("isc_socket_recv", result); 202 dns_message_destroy(&query); 203 } 204 205 int 206 main(int argc, char *argv[]) { 207 isc_boolean_t verbose = ISC_FALSE; 208 isc_socketmgr_t *socketmgr; 209 isc_timermgr_t *timermgr; 210 struct in_addr inaddr; 211 dns_fixedname_t fname; 212 dns_name_t *name; 213 isc_buffer_t b; 214 int ch; 215 isc_result_t result; 216 in_port_t port = 53; 217 218 RUNTIME_CHECK(isc_app_start() == ISC_R_SUCCESS); 219 220 RUNTIME_CHECK(isc_mutex_init(&lock) == ISC_R_SUCCESS); 221 222 mctx = NULL; 223 RUNTIME_CHECK(isc_mem_create(0, 0, &mctx) == ISC_R_SUCCESS); 224 225 while ((ch = isc_commandline_parse(argc, argv, "vp:")) != -1) { 226 switch (ch) { 227 case 'v': 228 verbose = ISC_TRUE; 229 break; 230 case 'p': 231 port = (unsigned int)atoi(isc_commandline_argument); 232 break; 233 } 234 } 235 236 RUNTIME_CHECK(isc_entropy_create(mctx, &ent) == ISC_R_SUCCESS); 237 RUNTIME_CHECK(dst_lib_init(mctx, ent, 0) == ISC_R_SUCCESS); 238 239 dns_result_register(); 240 dst_result_register(); 241 242 taskmgr = NULL; 243 RUNTIME_CHECK(isc_taskmgr_create(mctx, 2, 0, &taskmgr) == 244 ISC_R_SUCCESS); 245 task1 = NULL; 246 RUNTIME_CHECK(isc_task_create(taskmgr, 0, &task1) == ISC_R_SUCCESS); 247 248 timermgr = NULL; 249 RUNTIME_CHECK(isc_timermgr_create(mctx, &timermgr) == ISC_R_SUCCESS); 250 socketmgr = NULL; 251 RUNTIME_CHECK(isc_socketmgr_create(mctx, &socketmgr) == ISC_R_SUCCESS); 252 253 RUNTIME_CHECK(isc_log_create(mctx, &lctx, &logconfig) == ISC_R_SUCCESS); 254 255 s = NULL; 256 RUNTIME_CHECK(isc_socket_create(socketmgr, PF_INET, 257 isc_sockettype_udp, &s) == 258 ISC_R_SUCCESS); 259 260 inaddr.s_addr = htonl(INADDR_LOOPBACK); 261 isc_sockaddr_fromin(&address, &inaddr, port); 262 263 dns_fixedname_init(&fname); 264 name = dns_fixedname_name(&fname); 265 isc_buffer_constinit(&b, "child.example.", strlen("child.example.")); 266 isc_buffer_add(&b, strlen("child.example.")); 267 result = dns_name_fromtext(name, &b, dns_rootname, 0, NULL); 268 CHECK("dns_name_fromtext", result); 269 270 key = NULL; 271 result = dst_key_fromfile(name, 4017, DNS_KEYALG_DSA, 272 DST_TYPE_PUBLIC | DST_TYPE_PRIVATE, 273 NULL, mctx, &key); 274 CHECK("dst_key_fromfile", result); 275 276 buildquery(); 277 278 (void)isc_app_run(); 279 280 isc_task_shutdown(task1); 281 isc_task_detach(&task1); 282 isc_taskmgr_destroy(&taskmgr); 283 284 isc_socket_detach(&s); 285 isc_socketmgr_destroy(&socketmgr); 286 isc_timermgr_destroy(&timermgr); 287 288 dst_key_free(&key); 289 290 dst_lib_destroy(); 291 292 isc_entropy_detach(&ent); 293 294 isc_log_destroy(&lctx); 295 296 if (verbose) 297 isc_mem_stats(mctx, stdout); 298 isc_mem_destroy(&mctx); 299 300 DESTROYLOCK(&lock); 301 302 isc_app_finish(); 303 304 return (0); 305 } 306