1/* 2 * Copyright (C) 2004, 2007-2009 Internet Systems Consortium, Inc. ("ISC") 3 * Copyright (C) 1998-2002 Internet Software Consortium. 4 * 5 * Permission to use, copy, modify, and/or distribute this software for any 6 * purpose with or without fee is hereby granted, provided that the above 7 * copyright notice and this permission notice appear in all copies. 8 * 9 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH 10 * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY 11 * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT, 12 * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM 13 * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE 14 * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 15 * PERFORMANCE OF THIS SOFTWARE. 16 */ 17 18/* $Id: txt_16.c,v 1.47 2009/12/04 22:06:37 tbox Exp $ */ 19 20/* Reviewed: Thu Mar 16 15:40:00 PST 2000 by bwelling */ 21 22#ifndef RDATA_GENERIC_TXT_16_C 23#define RDATA_GENERIC_TXT_16_C 24 25#define RRTYPE_TXT_ATTRIBUTES (0) 26 27static inline isc_result_t 28fromtext_txt(ARGS_FROMTEXT) { 29 isc_token_t token; 30 int strings; 31 32 REQUIRE(type == 16); 33 34 UNUSED(type); 35 UNUSED(rdclass); 36 UNUSED(origin); 37 UNUSED(options); 38 UNUSED(callbacks); 39 40 strings = 0; 41 for (;;) { 42 RETERR(isc_lex_getmastertoken(lexer, &token, 43 isc_tokentype_qstring, 44 ISC_TRUE)); 45 if (token.type != isc_tokentype_qstring && 46 token.type != isc_tokentype_string) 47 break; 48 RETTOK(txt_fromtext(&token.value.as_textregion, target)); 49 strings++; 50 } 51 /* Let upper layer handle eol/eof. */ 52 isc_lex_ungettoken(lexer, &token); 53 return (strings == 0 ? ISC_R_UNEXPECTEDEND : ISC_R_SUCCESS); 54} 55 56static inline isc_result_t 57totext_txt(ARGS_TOTEXT) { 58 isc_region_t region; 59 60 UNUSED(tctx); 61 62 REQUIRE(rdata->type == 16); 63 64 dns_rdata_toregion(rdata, ®ion); 65 66 while (region.length > 0) { 67 RETERR(txt_totext(®ion, target)); 68 if (region.length > 0) 69 RETERR(str_totext(" ", target)); 70 } 71 72 return (ISC_R_SUCCESS); 73} 74 75static inline isc_result_t 76fromwire_txt(ARGS_FROMWIRE) { 77 isc_result_t result; 78 79 REQUIRE(type == 16); 80 81 UNUSED(type); 82 UNUSED(dctx); 83 UNUSED(rdclass); 84 UNUSED(options); 85 86 do { 87 result = txt_fromwire(source, target); 88 if (result != ISC_R_SUCCESS) 89 return (result); 90 } while (!buffer_empty(source)); 91 return (ISC_R_SUCCESS); 92} 93 94static inline isc_result_t 95towire_txt(ARGS_TOWIRE) { 96 isc_region_t region; 97 98 REQUIRE(rdata->type == 16); 99 100 UNUSED(cctx); 101 102 isc_buffer_availableregion(target, ®ion); 103 if (region.length < rdata->length) 104 return (ISC_R_NOSPACE); 105 106 memcpy(region.base, rdata->data, rdata->length); 107 isc_buffer_add(target, rdata->length); 108 return (ISC_R_SUCCESS); 109} 110 111static inline int 112compare_txt(ARGS_COMPARE) { 113 isc_region_t r1; 114 isc_region_t r2; 115 116 REQUIRE(rdata1->type == rdata2->type); 117 REQUIRE(rdata1->rdclass == rdata2->rdclass); 118 REQUIRE(rdata1->type == 16); 119 120 dns_rdata_toregion(rdata1, &r1); 121 dns_rdata_toregion(rdata2, &r2); 122 return (isc_region_compare(&r1, &r2)); 123} 124 125static inline isc_result_t 126fromstruct_txt(ARGS_FROMSTRUCT) { 127 dns_rdata_txt_t *txt = source; 128 isc_region_t region; 129 isc_uint8_t length; 130 131 REQUIRE(type == 16); 132 REQUIRE(source != NULL); 133 REQUIRE(txt->common.rdtype == type); 134 REQUIRE(txt->common.rdclass == rdclass); 135 REQUIRE(txt->txt != NULL && txt->txt_len != 0); 136 137 UNUSED(type); 138 UNUSED(rdclass); 139 140 region.base = txt->txt; 141 region.length = txt->txt_len; 142 while (region.length > 0) { 143 length = uint8_fromregion(®ion); 144 isc_region_consume(®ion, 1); 145 if (region.length < length) 146 return (ISC_R_UNEXPECTEDEND); 147 isc_region_consume(®ion, length); 148 } 149 150 return (mem_tobuffer(target, txt->txt, txt->txt_len)); 151} 152 153static inline isc_result_t 154tostruct_txt(ARGS_TOSTRUCT) { 155 dns_rdata_txt_t *txt = target; 156 isc_region_t r; 157 158 REQUIRE(rdata->type == 16); 159 REQUIRE(target != NULL); 160 161 txt->common.rdclass = rdata->rdclass; 162 txt->common.rdtype = rdata->type; 163 ISC_LINK_INIT(&txt->common, link); 164 165 dns_rdata_toregion(rdata, &r); 166 txt->txt_len = r.length; 167 txt->txt = mem_maybedup(mctx, r.base, r.length); 168 if (txt->txt == NULL) 169 return (ISC_R_NOMEMORY); 170 171 txt->offset = 0; 172 txt->mctx = mctx; 173 return (ISC_R_SUCCESS); 174} 175 176static inline void 177freestruct_txt(ARGS_FREESTRUCT) { 178 dns_rdata_txt_t *txt = source; 179 180 REQUIRE(source != NULL); 181 REQUIRE(txt->common.rdtype == 16); 182 183 if (txt->mctx == NULL) 184 return; 185 186 if (txt->txt != NULL) 187 isc_mem_free(txt->mctx, txt->txt); 188 txt->mctx = NULL; 189} 190 191static inline isc_result_t 192additionaldata_txt(ARGS_ADDLDATA) { 193 REQUIRE(rdata->type == 16); 194 195 UNUSED(rdata); 196 UNUSED(add); 197 UNUSED(arg); 198 199 return (ISC_R_SUCCESS); 200} 201 202static inline isc_result_t 203digest_txt(ARGS_DIGEST) { 204 isc_region_t r; 205 206 REQUIRE(rdata->type == 16); 207 208 dns_rdata_toregion(rdata, &r); 209 210 return ((digest)(arg, &r)); 211} 212 213static inline isc_boolean_t 214checkowner_txt(ARGS_CHECKOWNER) { 215 216 REQUIRE(type == 16); 217 218 UNUSED(name); 219 UNUSED(type); 220 UNUSED(rdclass); 221 UNUSED(wildcard); 222 223 return (ISC_TRUE); 224} 225 226static inline isc_boolean_t 227checknames_txt(ARGS_CHECKNAMES) { 228 229 REQUIRE(rdata->type == 16); 230 231 UNUSED(rdata); 232 UNUSED(owner); 233 UNUSED(bad); 234 235 return (ISC_TRUE); 236} 237 238static inline isc_result_t 239casecompare_txt(ARGS_COMPARE) { 240 return (compare_txt(rdata1, rdata2)); 241} 242 243#endif /* RDATA_GENERIC_TXT_16_C */ 244