1 /* $NetBSD: sshfp_44.c,v 1.6 2014/12/10 04:37:59 christos Exp $ */ 2 3 /* 4 * Copyright (C) 2004, 2006, 2007, 2009, 2011-2013 Internet Systems Consortium, Inc. ("ISC") 5 * Copyright (C) 2003 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 */ 21 22 /* RFC 4255 */ 23 24 #ifndef RDATA_GENERIC_SSHFP_44_C 25 #define RDATA_GENERIC_SSHFP_44_C 26 27 #define RRTYPE_SSHFP_ATTRIBUTES (0) 28 29 static inline isc_result_t 30 fromtext_sshfp(ARGS_FROMTEXT) { 31 isc_token_t token; 32 33 REQUIRE(type == 44); 34 35 UNUSED(type); 36 UNUSED(rdclass); 37 UNUSED(origin); 38 UNUSED(options); 39 UNUSED(callbacks); 40 41 /* 42 * Algorithm. 43 */ 44 RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_number, 45 ISC_FALSE)); 46 if (token.value.as_ulong > 0xffU) 47 RETTOK(ISC_R_RANGE); 48 RETERR(uint8_tobuffer(token.value.as_ulong, target)); 49 50 /* 51 * Digest type. 52 */ 53 RETERR(isc_lex_getmastertoken(lexer, &token, isc_tokentype_number, 54 ISC_FALSE)); 55 if (token.value.as_ulong > 0xffU) 56 RETTOK(ISC_R_RANGE); 57 RETERR(uint8_tobuffer(token.value.as_ulong, target)); 58 59 /* 60 * Digest. 61 */ 62 return (isc_hex_tobuffer(lexer, target, -1)); 63 } 64 65 static inline isc_result_t 66 totext_sshfp(ARGS_TOTEXT) { 67 isc_region_t sr; 68 char buf[sizeof("64000 ")]; 69 unsigned int n; 70 71 REQUIRE(rdata->type == 44); 72 REQUIRE(rdata->length != 0); 73 74 UNUSED(tctx); 75 76 dns_rdata_toregion(rdata, &sr); 77 78 /* 79 * Algorithm. 80 */ 81 n = uint8_fromregion(&sr); 82 isc_region_consume(&sr, 1); 83 sprintf(buf, "%u ", n); 84 RETERR(str_totext(buf, target)); 85 86 /* 87 * Digest type. 88 */ 89 n = uint8_fromregion(&sr); 90 isc_region_consume(&sr, 1); 91 sprintf(buf, "%u", n); 92 RETERR(str_totext(buf, target)); 93 94 /* 95 * Digest. 96 */ 97 if ((tctx->flags & DNS_STYLEFLAG_MULTILINE) != 0) 98 RETERR(str_totext(" (", target)); 99 RETERR(str_totext(tctx->linebreak, target)); 100 if (tctx->width == 0) /* No splitting */ 101 RETERR(isc_hex_totext(&sr, 0, "", target)); 102 else 103 RETERR(isc_hex_totext(&sr, tctx->width - 2, 104 tctx->linebreak, target)); 105 if ((tctx->flags & DNS_STYLEFLAG_MULTILINE) != 0) 106 RETERR(str_totext(" )", target)); 107 return (ISC_R_SUCCESS); 108 } 109 110 static inline isc_result_t 111 fromwire_sshfp(ARGS_FROMWIRE) { 112 isc_region_t sr; 113 114 REQUIRE(type == 44); 115 116 UNUSED(type); 117 UNUSED(rdclass); 118 UNUSED(dctx); 119 UNUSED(options); 120 121 isc_buffer_activeregion(source, &sr); 122 if (sr.length < 4) 123 return (ISC_R_UNEXPECTEDEND); 124 125 isc_buffer_forward(source, sr.length); 126 return (mem_tobuffer(target, sr.base, sr.length)); 127 } 128 129 static inline isc_result_t 130 towire_sshfp(ARGS_TOWIRE) { 131 isc_region_t sr; 132 133 REQUIRE(rdata->type == 44); 134 REQUIRE(rdata->length != 0); 135 136 UNUSED(cctx); 137 138 dns_rdata_toregion(rdata, &sr); 139 return (mem_tobuffer(target, sr.base, sr.length)); 140 } 141 142 static inline int 143 compare_sshfp(ARGS_COMPARE) { 144 isc_region_t r1; 145 isc_region_t r2; 146 147 REQUIRE(rdata1->type == rdata2->type); 148 REQUIRE(rdata1->rdclass == rdata2->rdclass); 149 REQUIRE(rdata1->type == 44); 150 REQUIRE(rdata1->length != 0); 151 REQUIRE(rdata2->length != 0); 152 153 dns_rdata_toregion(rdata1, &r1); 154 dns_rdata_toregion(rdata2, &r2); 155 return (isc_region_compare(&r1, &r2)); 156 } 157 158 static inline isc_result_t 159 fromstruct_sshfp(ARGS_FROMSTRUCT) { 160 dns_rdata_sshfp_t *sshfp = source; 161 162 REQUIRE(type == 44); 163 REQUIRE(source != NULL); 164 REQUIRE(sshfp->common.rdtype == type); 165 REQUIRE(sshfp->common.rdclass == rdclass); 166 167 UNUSED(type); 168 UNUSED(rdclass); 169 170 RETERR(uint8_tobuffer(sshfp->algorithm, target)); 171 RETERR(uint8_tobuffer(sshfp->digest_type, target)); 172 173 return (mem_tobuffer(target, sshfp->digest, sshfp->length)); 174 } 175 176 static inline isc_result_t 177 tostruct_sshfp(ARGS_TOSTRUCT) { 178 dns_rdata_sshfp_t *sshfp = target; 179 isc_region_t region; 180 181 REQUIRE(rdata->type == 44); 182 REQUIRE(target != NULL); 183 REQUIRE(rdata->length != 0); 184 185 sshfp->common.rdclass = rdata->rdclass; 186 sshfp->common.rdtype = rdata->type; 187 ISC_LINK_INIT(&sshfp->common, link); 188 189 dns_rdata_toregion(rdata, ®ion); 190 191 sshfp->algorithm = uint8_fromregion(®ion); 192 isc_region_consume(®ion, 1); 193 sshfp->digest_type = uint8_fromregion(®ion); 194 isc_region_consume(®ion, 1); 195 sshfp->length = region.length; 196 197 sshfp->digest = mem_maybedup(mctx, region.base, region.length); 198 if (sshfp->digest == NULL) 199 return (ISC_R_NOMEMORY); 200 201 sshfp->mctx = mctx; 202 return (ISC_R_SUCCESS); 203 } 204 205 static inline void 206 freestruct_sshfp(ARGS_FREESTRUCT) { 207 dns_rdata_sshfp_t *sshfp = source; 208 209 REQUIRE(sshfp != NULL); 210 REQUIRE(sshfp->common.rdtype == 44); 211 212 if (sshfp->mctx == NULL) 213 return; 214 215 if (sshfp->digest != NULL) 216 isc_mem_free(sshfp->mctx, sshfp->digest); 217 sshfp->mctx = NULL; 218 } 219 220 static inline isc_result_t 221 additionaldata_sshfp(ARGS_ADDLDATA) { 222 REQUIRE(rdata->type == 44); 223 224 UNUSED(rdata); 225 UNUSED(add); 226 UNUSED(arg); 227 228 return (ISC_R_SUCCESS); 229 } 230 231 static inline isc_result_t 232 digest_sshfp(ARGS_DIGEST) { 233 isc_region_t r; 234 235 REQUIRE(rdata->type == 44); 236 237 dns_rdata_toregion(rdata, &r); 238 239 return ((digest)(arg, &r)); 240 } 241 242 static inline isc_boolean_t 243 checkowner_sshfp(ARGS_CHECKOWNER) { 244 245 REQUIRE(type == 44); 246 247 UNUSED(name); 248 UNUSED(type); 249 UNUSED(rdclass); 250 UNUSED(wildcard); 251 252 return (ISC_TRUE); 253 } 254 255 static inline isc_boolean_t 256 checknames_sshfp(ARGS_CHECKNAMES) { 257 258 REQUIRE(rdata->type == 44); 259 260 UNUSED(rdata); 261 UNUSED(owner); 262 UNUSED(bad); 263 264 return (ISC_TRUE); 265 } 266 267 static inline int 268 casecompare_sshfp(ARGS_COMPARE) { 269 return (compare_sshfp(rdata1, rdata2)); 270 } 271 272 #endif /* RDATA_GENERIC_SSHFP_44_C */ 273