| line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
|
1
|
|
|
|
|
|
|
/* |
|
2
|
|
|
|
|
|
|
* tsig.c |
|
3
|
|
|
|
|
|
|
* |
|
4
|
|
|
|
|
|
|
* contains the functions needed for TSIG [RFC2845] |
|
5
|
|
|
|
|
|
|
* |
|
6
|
|
|
|
|
|
|
* (c) 2005-2006 NLnet Labs |
|
7
|
|
|
|
|
|
|
* See the file LICENSE for the license |
|
8
|
|
|
|
|
|
|
*/ |
|
9
|
|
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
#include |
|
11
|
|
|
|
|
|
|
|
|
12
|
|
|
|
|
|
|
#include |
|
13
|
|
|
|
|
|
|
|
|
14
|
|
|
|
|
|
|
#include |
|
15
|
|
|
|
|
|
|
|
|
16
|
|
|
|
|
|
|
#ifdef HAVE_SSL |
|
17
|
|
|
|
|
|
|
#include |
|
18
|
|
|
|
|
|
|
#include |
|
19
|
|
|
|
|
|
|
#endif /* HAVE_SSL */ |
|
20
|
|
|
|
|
|
|
|
|
21
|
|
|
|
|
|
|
char * |
|
22
|
0
|
|
|
|
|
|
ldns_tsig_algorithm(ldns_tsig_credentials *tc) |
|
23
|
|
|
|
|
|
|
{ |
|
24
|
0
|
|
|
|
|
|
return tc->algorithm; |
|
25
|
|
|
|
|
|
|
} |
|
26
|
|
|
|
|
|
|
|
|
27
|
|
|
|
|
|
|
char * |
|
28
|
0
|
|
|
|
|
|
ldns_tsig_keyname(ldns_tsig_credentials *tc) |
|
29
|
|
|
|
|
|
|
{ |
|
30
|
0
|
|
|
|
|
|
return tc->keyname; |
|
31
|
|
|
|
|
|
|
} |
|
32
|
|
|
|
|
|
|
|
|
33
|
|
|
|
|
|
|
char * |
|
34
|
0
|
|
|
|
|
|
ldns_tsig_keydata(ldns_tsig_credentials *tc) |
|
35
|
|
|
|
|
|
|
{ |
|
36
|
0
|
|
|
|
|
|
return tc->keydata; |
|
37
|
|
|
|
|
|
|
} |
|
38
|
|
|
|
|
|
|
|
|
39
|
|
|
|
|
|
|
char * |
|
40
|
0
|
|
|
|
|
|
ldns_tsig_keyname_clone(ldns_tsig_credentials *tc) |
|
41
|
|
|
|
|
|
|
{ |
|
42
|
0
|
|
|
|
|
|
return strdup(tc->keyname); |
|
43
|
|
|
|
|
|
|
} |
|
44
|
|
|
|
|
|
|
|
|
45
|
|
|
|
|
|
|
char * |
|
46
|
0
|
|
|
|
|
|
ldns_tsig_keydata_clone(ldns_tsig_credentials *tc) |
|
47
|
|
|
|
|
|
|
{ |
|
48
|
0
|
|
|
|
|
|
return strdup(tc->keydata); |
|
49
|
|
|
|
|
|
|
} |
|
50
|
|
|
|
|
|
|
|
|
51
|
|
|
|
|
|
|
/* |
|
52
|
|
|
|
|
|
|
* Makes an exact copy of the wire, but with the tsig rr removed |
|
53
|
|
|
|
|
|
|
*/ |
|
54
|
|
|
|
|
|
|
static uint8_t * |
|
55
|
0
|
|
|
|
|
|
ldns_tsig_prepare_pkt_wire(uint8_t *wire, size_t wire_len, size_t *result_len) |
|
56
|
|
|
|
|
|
|
{ |
|
57
|
0
|
|
|
|
|
|
uint8_t *wire2 = NULL; |
|
58
|
|
|
|
|
|
|
uint16_t qd_count; |
|
59
|
|
|
|
|
|
|
uint16_t an_count; |
|
60
|
|
|
|
|
|
|
uint16_t ns_count; |
|
61
|
|
|
|
|
|
|
uint16_t ar_count; |
|
62
|
|
|
|
|
|
|
ldns_rr *rr; |
|
63
|
|
|
|
|
|
|
|
|
64
|
|
|
|
|
|
|
size_t pos; |
|
65
|
|
|
|
|
|
|
uint16_t i; |
|
66
|
|
|
|
|
|
|
|
|
67
|
|
|
|
|
|
|
ldns_status status; |
|
68
|
|
|
|
|
|
|
|
|
69
|
0
|
0
|
|
|
|
|
if(wire_len < LDNS_HEADER_SIZE) { |
|
70
|
0
|
|
|
|
|
|
return NULL; |
|
71
|
|
|
|
|
|
|
} |
|
72
|
|
|
|
|
|
|
/* fake parse the wire */ |
|
73
|
0
|
|
|
|
|
|
qd_count = LDNS_QDCOUNT(wire); |
|
74
|
0
|
|
|
|
|
|
an_count = LDNS_ANCOUNT(wire); |
|
75
|
0
|
|
|
|
|
|
ns_count = LDNS_NSCOUNT(wire); |
|
76
|
0
|
|
|
|
|
|
ar_count = LDNS_ARCOUNT(wire); |
|
77
|
|
|
|
|
|
|
|
|
78
|
0
|
0
|
|
|
|
|
if (ar_count > 0) { |
|
79
|
0
|
|
|
|
|
|
ar_count--; |
|
80
|
|
|
|
|
|
|
} else { |
|
81
|
0
|
|
|
|
|
|
return NULL; |
|
82
|
|
|
|
|
|
|
} |
|
83
|
|
|
|
|
|
|
|
|
84
|
0
|
|
|
|
|
|
pos = LDNS_HEADER_SIZE; |
|
85
|
|
|
|
|
|
|
|
|
86
|
0
|
0
|
|
|
|
|
for (i = 0; i < qd_count; i++) { |
|
87
|
0
|
|
|
|
|
|
status = ldns_wire2rr(&rr, wire, wire_len, &pos, LDNS_SECTION_QUESTION); |
|
88
|
0
|
0
|
|
|
|
|
if (status != LDNS_STATUS_OK) { |
|
89
|
0
|
|
|
|
|
|
return NULL; |
|
90
|
|
|
|
|
|
|
} |
|
91
|
0
|
|
|
|
|
|
ldns_rr_free(rr); |
|
92
|
|
|
|
|
|
|
} |
|
93
|
|
|
|
|
|
|
|
|
94
|
0
|
0
|
|
|
|
|
for (i = 0; i < an_count; i++) { |
|
95
|
0
|
|
|
|
|
|
status = ldns_wire2rr(&rr, wire, wire_len, &pos, LDNS_SECTION_ANSWER); |
|
96
|
0
|
0
|
|
|
|
|
if (status != LDNS_STATUS_OK) { |
|
97
|
0
|
|
|
|
|
|
return NULL; |
|
98
|
|
|
|
|
|
|
} |
|
99
|
0
|
|
|
|
|
|
ldns_rr_free(rr); |
|
100
|
|
|
|
|
|
|
} |
|
101
|
|
|
|
|
|
|
|
|
102
|
0
|
0
|
|
|
|
|
for (i = 0; i < ns_count; i++) { |
|
103
|
0
|
|
|
|
|
|
status = ldns_wire2rr(&rr, wire, wire_len, &pos, LDNS_SECTION_AUTHORITY); |
|
104
|
0
|
0
|
|
|
|
|
if (status != LDNS_STATUS_OK) { |
|
105
|
0
|
|
|
|
|
|
return NULL; |
|
106
|
|
|
|
|
|
|
} |
|
107
|
0
|
|
|
|
|
|
ldns_rr_free(rr); |
|
108
|
|
|
|
|
|
|
} |
|
109
|
|
|
|
|
|
|
|
|
110
|
0
|
0
|
|
|
|
|
for (i = 0; i < ar_count; i++) { |
|
111
|
0
|
|
|
|
|
|
status = ldns_wire2rr(&rr, wire, wire_len, &pos, |
|
112
|
|
|
|
|
|
|
LDNS_SECTION_ADDITIONAL); |
|
113
|
0
|
0
|
|
|
|
|
if (status != LDNS_STATUS_OK) { |
|
114
|
0
|
|
|
|
|
|
return NULL; |
|
115
|
|
|
|
|
|
|
} |
|
116
|
0
|
|
|
|
|
|
ldns_rr_free(rr); |
|
117
|
|
|
|
|
|
|
} |
|
118
|
|
|
|
|
|
|
|
|
119
|
0
|
|
|
|
|
|
*result_len = pos; |
|
120
|
0
|
|
|
|
|
|
wire2 = LDNS_XMALLOC(uint8_t, *result_len); |
|
121
|
0
|
0
|
|
|
|
|
if(!wire2) { |
|
122
|
0
|
|
|
|
|
|
return NULL; |
|
123
|
|
|
|
|
|
|
} |
|
124
|
0
|
|
|
|
|
|
memcpy(wire2, wire, *result_len); |
|
125
|
|
|
|
|
|
|
|
|
126
|
0
|
|
|
|
|
|
ldns_write_uint16(wire2 + LDNS_ARCOUNT_OFF, ar_count); |
|
127
|
|
|
|
|
|
|
|
|
128
|
0
|
|
|
|
|
|
return wire2; |
|
129
|
|
|
|
|
|
|
} |
|
130
|
|
|
|
|
|
|
|
|
131
|
|
|
|
|
|
|
#ifdef HAVE_SSL |
|
132
|
|
|
|
|
|
|
static const EVP_MD * |
|
133
|
0
|
|
|
|
|
|
ldns_digest_function(char *name) |
|
134
|
|
|
|
|
|
|
{ |
|
135
|
|
|
|
|
|
|
/* these are the mandatory algorithms from RFC4635 */ |
|
136
|
|
|
|
|
|
|
/* The optional algorithms are not yet implemented */ |
|
137
|
0
|
0
|
|
|
|
|
if (strcasecmp(name, "hmac-sha256.") == 0) { |
|
138
|
|
|
|
|
|
|
#ifdef HAVE_EVP_SHA256 |
|
139
|
0
|
|
|
|
|
|
return EVP_sha256(); |
|
140
|
|
|
|
|
|
|
#else |
|
141
|
|
|
|
|
|
|
return NULL; |
|
142
|
|
|
|
|
|
|
#endif |
|
143
|
0
|
0
|
|
|
|
|
} else if (strcasecmp(name, "hmac-sha1.") == 0) { |
|
144
|
0
|
|
|
|
|
|
return EVP_sha1(); |
|
145
|
0
|
0
|
|
|
|
|
} else if (strcasecmp(name, "hmac-md5.sig-alg.reg.int.") == 0) { |
|
146
|
0
|
|
|
|
|
|
return EVP_md5(); |
|
147
|
|
|
|
|
|
|
} else { |
|
148
|
0
|
|
|
|
|
|
return NULL; |
|
149
|
|
|
|
|
|
|
} |
|
150
|
|
|
|
|
|
|
} |
|
151
|
|
|
|
|
|
|
#endif |
|
152
|
|
|
|
|
|
|
|
|
153
|
|
|
|
|
|
|
#ifdef HAVE_SSL |
|
154
|
|
|
|
|
|
|
static ldns_status |
|
155
|
0
|
|
|
|
|
|
ldns_tsig_mac_new(ldns_rdf **tsig_mac, uint8_t *pkt_wire, size_t pkt_wire_size, |
|
156
|
|
|
|
|
|
|
const char *key_data, ldns_rdf *key_name_rdf, ldns_rdf *fudge_rdf, |
|
157
|
|
|
|
|
|
|
ldns_rdf *algorithm_rdf, ldns_rdf *time_signed_rdf, ldns_rdf *error_rdf, |
|
158
|
|
|
|
|
|
|
ldns_rdf *other_data_rdf, ldns_rdf *orig_mac_rdf, int tsig_timers_only) |
|
159
|
|
|
|
|
|
|
{ |
|
160
|
|
|
|
|
|
|
ldns_status status; |
|
161
|
|
|
|
|
|
|
char *wireformat; |
|
162
|
|
|
|
|
|
|
int wiresize; |
|
163
|
0
|
|
|
|
|
|
unsigned char *mac_bytes = NULL; |
|
164
|
0
|
|
|
|
|
|
unsigned char *key_bytes = NULL; |
|
165
|
|
|
|
|
|
|
int key_size; |
|
166
|
|
|
|
|
|
|
const EVP_MD *digester; |
|
167
|
0
|
|
|
|
|
|
char *algorithm_name = NULL; |
|
168
|
0
|
|
|
|
|
|
unsigned int md_len = EVP_MAX_MD_SIZE; |
|
169
|
0
|
|
|
|
|
|
ldns_rdf *result = NULL; |
|
170
|
0
|
|
|
|
|
|
ldns_buffer *data_buffer = NULL; |
|
171
|
0
|
|
|
|
|
|
ldns_rdf *canonical_key_name_rdf = NULL; |
|
172
|
0
|
|
|
|
|
|
ldns_rdf *canonical_algorithm_rdf = NULL; |
|
173
|
|
|
|
|
|
|
|
|
174
|
0
|
0
|
|
|
|
|
if (key_name_rdf == NULL || algorithm_rdf == NULL) { |
|
|
|
0
|
|
|
|
|
|
|
175
|
0
|
|
|
|
|
|
return LDNS_STATUS_NULL; |
|
176
|
|
|
|
|
|
|
} |
|
177
|
0
|
|
|
|
|
|
canonical_key_name_rdf = ldns_rdf_clone(key_name_rdf); |
|
178
|
0
|
0
|
|
|
|
|
if (canonical_key_name_rdf == NULL) { |
|
179
|
0
|
|
|
|
|
|
return LDNS_STATUS_MEM_ERR; |
|
180
|
|
|
|
|
|
|
} |
|
181
|
0
|
|
|
|
|
|
canonical_algorithm_rdf = ldns_rdf_clone(algorithm_rdf); |
|
182
|
0
|
0
|
|
|
|
|
if (canonical_algorithm_rdf == NULL) { |
|
183
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(canonical_key_name_rdf); |
|
184
|
0
|
|
|
|
|
|
return LDNS_STATUS_MEM_ERR; |
|
185
|
|
|
|
|
|
|
} |
|
186
|
|
|
|
|
|
|
/* |
|
187
|
|
|
|
|
|
|
* prepare the digestable information |
|
188
|
|
|
|
|
|
|
*/ |
|
189
|
0
|
|
|
|
|
|
data_buffer = ldns_buffer_new(LDNS_MAX_PACKETLEN); |
|
190
|
0
|
0
|
|
|
|
|
if (!data_buffer) { |
|
191
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
192
|
0
|
|
|
|
|
|
goto clean; |
|
193
|
|
|
|
|
|
|
} |
|
194
|
|
|
|
|
|
|
/* if orig_mac is not NULL, add it too */ |
|
195
|
0
|
0
|
|
|
|
|
if (orig_mac_rdf) { |
|
196
|
0
|
|
|
|
|
|
(void) ldns_rdf2buffer_wire(data_buffer, orig_mac_rdf); |
|
197
|
|
|
|
|
|
|
} |
|
198
|
0
|
|
|
|
|
|
ldns_buffer_write(data_buffer, pkt_wire, pkt_wire_size); |
|
199
|
0
|
0
|
|
|
|
|
if (!tsig_timers_only) { |
|
200
|
0
|
|
|
|
|
|
ldns_dname2canonical(canonical_key_name_rdf); |
|
201
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, |
|
202
|
|
|
|
|
|
|
canonical_key_name_rdf); |
|
203
|
0
|
|
|
|
|
|
ldns_buffer_write_u16(data_buffer, LDNS_RR_CLASS_ANY); |
|
204
|
0
|
|
|
|
|
|
ldns_buffer_write_u32(data_buffer, 0); |
|
205
|
0
|
|
|
|
|
|
ldns_dname2canonical(canonical_algorithm_rdf); |
|
206
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, |
|
207
|
|
|
|
|
|
|
canonical_algorithm_rdf); |
|
208
|
|
|
|
|
|
|
} |
|
209
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, time_signed_rdf); |
|
210
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, fudge_rdf); |
|
211
|
0
|
0
|
|
|
|
|
if (!tsig_timers_only) { |
|
212
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, error_rdf); |
|
213
|
0
|
|
|
|
|
|
(void)ldns_rdf2buffer_wire(data_buffer, other_data_rdf); |
|
214
|
|
|
|
|
|
|
} |
|
215
|
|
|
|
|
|
|
|
|
216
|
0
|
|
|
|
|
|
wireformat = (char *) data_buffer->_data; |
|
217
|
0
|
|
|
|
|
|
wiresize = (int) ldns_buffer_position(data_buffer); |
|
218
|
|
|
|
|
|
|
|
|
219
|
0
|
|
|
|
|
|
algorithm_name = ldns_rdf2str(algorithm_rdf); |
|
220
|
0
|
0
|
|
|
|
|
if(!algorithm_name) { |
|
221
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
222
|
0
|
|
|
|
|
|
goto clean; |
|
223
|
|
|
|
|
|
|
} |
|
224
|
|
|
|
|
|
|
|
|
225
|
|
|
|
|
|
|
/* prepare the key */ |
|
226
|
0
|
|
|
|
|
|
key_bytes = LDNS_XMALLOC(unsigned char, |
|
227
|
|
|
|
|
|
|
ldns_b64_pton_calculate_size(strlen(key_data))); |
|
228
|
0
|
0
|
|
|
|
|
if(!key_bytes) { |
|
229
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
230
|
0
|
|
|
|
|
|
goto clean; |
|
231
|
|
|
|
|
|
|
} |
|
232
|
0
|
|
|
|
|
|
key_size = ldns_b64_pton(key_data, key_bytes, |
|
233
|
|
|
|
|
|
|
ldns_b64_pton_calculate_size(strlen(key_data))); |
|
234
|
0
|
0
|
|
|
|
|
if (key_size < 0) { |
|
235
|
0
|
|
|
|
|
|
status = LDNS_STATUS_INVALID_B64; |
|
236
|
0
|
|
|
|
|
|
goto clean; |
|
237
|
|
|
|
|
|
|
} |
|
238
|
|
|
|
|
|
|
/* hmac it */ |
|
239
|
|
|
|
|
|
|
/* 2 spare bytes for the length */ |
|
240
|
0
|
|
|
|
|
|
mac_bytes = LDNS_XMALLOC(unsigned char, md_len+2); |
|
241
|
0
|
0
|
|
|
|
|
if(!mac_bytes) { |
|
242
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
243
|
0
|
|
|
|
|
|
goto clean; |
|
244
|
|
|
|
|
|
|
} |
|
245
|
0
|
|
|
|
|
|
memset(mac_bytes, 0, md_len+2); |
|
246
|
|
|
|
|
|
|
|
|
247
|
0
|
|
|
|
|
|
digester = ldns_digest_function(algorithm_name); |
|
248
|
|
|
|
|
|
|
|
|
249
|
0
|
0
|
|
|
|
|
if (digester) { |
|
250
|
0
|
|
|
|
|
|
(void) HMAC(digester, key_bytes, key_size, (void *)wireformat, |
|
251
|
|
|
|
|
|
|
(size_t) wiresize, mac_bytes + 2, &md_len); |
|
252
|
|
|
|
|
|
|
|
|
253
|
0
|
|
|
|
|
|
ldns_write_uint16(mac_bytes, md_len); |
|
254
|
0
|
|
|
|
|
|
result = ldns_rdf_new_frm_data(LDNS_RDF_TYPE_INT16_DATA, md_len + 2, |
|
255
|
|
|
|
|
|
|
mac_bytes); |
|
256
|
|
|
|
|
|
|
} else { |
|
257
|
0
|
|
|
|
|
|
status = LDNS_STATUS_CRYPTO_UNKNOWN_ALGO; |
|
258
|
0
|
|
|
|
|
|
goto clean; |
|
259
|
|
|
|
|
|
|
} |
|
260
|
0
|
|
|
|
|
|
*tsig_mac = result; |
|
261
|
0
|
|
|
|
|
|
status = LDNS_STATUS_OK; |
|
262
|
|
|
|
|
|
|
clean: |
|
263
|
0
|
|
|
|
|
|
LDNS_FREE(mac_bytes); |
|
264
|
0
|
|
|
|
|
|
LDNS_FREE(key_bytes); |
|
265
|
0
|
|
|
|
|
|
LDNS_FREE(algorithm_name); |
|
266
|
0
|
|
|
|
|
|
ldns_buffer_free(data_buffer); |
|
267
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(canonical_algorithm_rdf); |
|
268
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(canonical_key_name_rdf); |
|
269
|
0
|
|
|
|
|
|
return status; |
|
270
|
|
|
|
|
|
|
} |
|
271
|
|
|
|
|
|
|
#endif /* HAVE_SSL */ |
|
272
|
|
|
|
|
|
|
|
|
273
|
|
|
|
|
|
|
|
|
274
|
|
|
|
|
|
|
#ifdef HAVE_SSL |
|
275
|
|
|
|
|
|
|
bool |
|
276
|
0
|
|
|
|
|
|
ldns_pkt_tsig_verify(ldns_pkt *pkt, uint8_t *wire, size_t wirelen, const char *key_name, |
|
277
|
|
|
|
|
|
|
const char *key_data, ldns_rdf *orig_mac_rdf) |
|
278
|
|
|
|
|
|
|
{ |
|
279
|
0
|
|
|
|
|
|
return ldns_pkt_tsig_verify_next(pkt, wire, wirelen, key_name, key_data, orig_mac_rdf, 0); |
|
280
|
|
|
|
|
|
|
} |
|
281
|
|
|
|
|
|
|
|
|
282
|
|
|
|
|
|
|
bool |
|
283
|
0
|
|
|
|
|
|
ldns_pkt_tsig_verify_next(ldns_pkt *pkt, uint8_t *wire, size_t wirelen, const char* key_name, |
|
284
|
|
|
|
|
|
|
const char *key_data, ldns_rdf *orig_mac_rdf, int tsig_timers_only) |
|
285
|
|
|
|
|
|
|
{ |
|
286
|
|
|
|
|
|
|
ldns_rdf *fudge_rdf; |
|
287
|
|
|
|
|
|
|
ldns_rdf *algorithm_rdf; |
|
288
|
|
|
|
|
|
|
ldns_rdf *time_signed_rdf; |
|
289
|
|
|
|
|
|
|
ldns_rdf *orig_id_rdf; |
|
290
|
|
|
|
|
|
|
ldns_rdf *error_rdf; |
|
291
|
|
|
|
|
|
|
ldns_rdf *other_data_rdf; |
|
292
|
|
|
|
|
|
|
ldns_rdf *pkt_mac_rdf; |
|
293
|
|
|
|
|
|
|
ldns_rdf *my_mac_rdf; |
|
294
|
0
|
|
|
|
|
|
ldns_rdf *key_name_rdf = ldns_rdf_new_frm_str(LDNS_RDF_TYPE_DNAME, key_name); |
|
295
|
|
|
|
|
|
|
uint16_t pkt_id, orig_pkt_id; |
|
296
|
|
|
|
|
|
|
ldns_status status; |
|
297
|
|
|
|
|
|
|
|
|
298
|
0
|
|
|
|
|
|
uint8_t *prepared_wire = NULL; |
|
299
|
0
|
|
|
|
|
|
size_t prepared_wire_size = 0; |
|
300
|
|
|
|
|
|
|
|
|
301
|
0
|
|
|
|
|
|
ldns_rr *orig_tsig = ldns_pkt_tsig(pkt); |
|
302
|
|
|
|
|
|
|
|
|
303
|
0
|
0
|
|
|
|
|
if (!orig_tsig || ldns_rr_rd_count(orig_tsig) <= 6) { |
|
|
|
0
|
|
|
|
|
|
|
304
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(key_name_rdf); |
|
305
|
0
|
|
|
|
|
|
return false; |
|
306
|
|
|
|
|
|
|
} |
|
307
|
0
|
|
|
|
|
|
algorithm_rdf = ldns_rr_rdf(orig_tsig, 0); |
|
308
|
0
|
|
|
|
|
|
time_signed_rdf = ldns_rr_rdf(orig_tsig, 1); |
|
309
|
0
|
|
|
|
|
|
fudge_rdf = ldns_rr_rdf(orig_tsig, 2); |
|
310
|
0
|
|
|
|
|
|
pkt_mac_rdf = ldns_rr_rdf(orig_tsig, 3); |
|
311
|
0
|
|
|
|
|
|
orig_id_rdf = ldns_rr_rdf(orig_tsig, 4); |
|
312
|
0
|
|
|
|
|
|
error_rdf = ldns_rr_rdf(orig_tsig, 5); |
|
313
|
0
|
|
|
|
|
|
other_data_rdf = ldns_rr_rdf(orig_tsig, 6); |
|
314
|
|
|
|
|
|
|
|
|
315
|
|
|
|
|
|
|
/* remove temporarily */ |
|
316
|
0
|
|
|
|
|
|
ldns_pkt_set_tsig(pkt, NULL); |
|
317
|
|
|
|
|
|
|
/* temporarily change the id to the original id */ |
|
318
|
0
|
|
|
|
|
|
pkt_id = ldns_pkt_id(pkt); |
|
319
|
0
|
|
|
|
|
|
orig_pkt_id = ldns_rdf2native_int16(orig_id_rdf); |
|
320
|
0
|
|
|
|
|
|
ldns_pkt_set_id(pkt, orig_pkt_id); |
|
321
|
|
|
|
|
|
|
|
|
322
|
0
|
|
|
|
|
|
prepared_wire = ldns_tsig_prepare_pkt_wire(wire, wirelen, &prepared_wire_size); |
|
323
|
|
|
|
|
|
|
|
|
324
|
0
|
|
|
|
|
|
status = ldns_tsig_mac_new(&my_mac_rdf, prepared_wire, prepared_wire_size, |
|
325
|
|
|
|
|
|
|
key_data, key_name_rdf, fudge_rdf, algorithm_rdf, |
|
326
|
|
|
|
|
|
|
time_signed_rdf, error_rdf, other_data_rdf, orig_mac_rdf, tsig_timers_only); |
|
327
|
|
|
|
|
|
|
|
|
328
|
0
|
|
|
|
|
|
LDNS_FREE(prepared_wire); |
|
329
|
|
|
|
|
|
|
|
|
330
|
0
|
0
|
|
|
|
|
if (status != LDNS_STATUS_OK) { |
|
331
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(key_name_rdf); |
|
332
|
0
|
|
|
|
|
|
return false; |
|
333
|
|
|
|
|
|
|
} |
|
334
|
|
|
|
|
|
|
/* Put back the values */ |
|
335
|
0
|
|
|
|
|
|
ldns_pkt_set_tsig(pkt, orig_tsig); |
|
336
|
0
|
|
|
|
|
|
ldns_pkt_set_id(pkt, pkt_id); |
|
337
|
|
|
|
|
|
|
|
|
338
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(key_name_rdf); |
|
339
|
|
|
|
|
|
|
|
|
340
|
0
|
0
|
|
|
|
|
if (ldns_rdf_compare(pkt_mac_rdf, my_mac_rdf) == 0) { |
|
341
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(my_mac_rdf); |
|
342
|
0
|
|
|
|
|
|
return true; |
|
343
|
|
|
|
|
|
|
} else { |
|
344
|
0
|
|
|
|
|
|
ldns_rdf_deep_free(my_mac_rdf); |
|
345
|
0
|
|
|
|
|
|
return false; |
|
346
|
|
|
|
|
|
|
} |
|
347
|
|
|
|
|
|
|
} |
|
348
|
|
|
|
|
|
|
#endif /* HAVE_SSL */ |
|
349
|
|
|
|
|
|
|
|
|
350
|
|
|
|
|
|
|
#ifdef HAVE_SSL |
|
351
|
|
|
|
|
|
|
ldns_status |
|
352
|
0
|
|
|
|
|
|
ldns_pkt_tsig_sign(ldns_pkt *pkt, const char *key_name, const char *key_data, |
|
353
|
|
|
|
|
|
|
uint16_t fudge, const char *algorithm_name, ldns_rdf *query_mac) |
|
354
|
|
|
|
|
|
|
{ |
|
355
|
0
|
|
|
|
|
|
return ldns_pkt_tsig_sign_next(pkt, key_name, key_data, fudge, algorithm_name, query_mac, 0); |
|
356
|
|
|
|
|
|
|
} |
|
357
|
|
|
|
|
|
|
|
|
358
|
|
|
|
|
|
|
ldns_status |
|
359
|
0
|
|
|
|
|
|
ldns_pkt_tsig_sign_next(ldns_pkt *pkt, const char *key_name, const char *key_data, |
|
360
|
|
|
|
|
|
|
uint16_t fudge, const char *algorithm_name, ldns_rdf *query_mac, int tsig_timers_only) |
|
361
|
|
|
|
|
|
|
{ |
|
362
|
|
|
|
|
|
|
ldns_rr *tsig_rr; |
|
363
|
0
|
|
|
|
|
|
ldns_rdf *key_name_rdf = ldns_rdf_new_frm_str(LDNS_RDF_TYPE_DNAME, key_name); |
|
364
|
0
|
|
|
|
|
|
ldns_rdf *fudge_rdf = NULL; |
|
365
|
0
|
|
|
|
|
|
ldns_rdf *orig_id_rdf = NULL; |
|
366
|
|
|
|
|
|
|
ldns_rdf *algorithm_rdf; |
|
367
|
0
|
|
|
|
|
|
ldns_rdf *error_rdf = NULL; |
|
368
|
0
|
|
|
|
|
|
ldns_rdf *mac_rdf = NULL; |
|
369
|
0
|
|
|
|
|
|
ldns_rdf *other_data_rdf = NULL; |
|
370
|
|
|
|
|
|
|
|
|
371
|
0
|
|
|
|
|
|
ldns_status status = LDNS_STATUS_OK; |
|
372
|
|
|
|
|
|
|
|
|
373
|
0
|
|
|
|
|
|
uint8_t *pkt_wire = NULL; |
|
374
|
|
|
|
|
|
|
size_t pkt_wire_len; |
|
375
|
|
|
|
|
|
|
|
|
376
|
|
|
|
|
|
|
struct timeval tv_time_signed; |
|
377
|
0
|
|
|
|
|
|
uint8_t *time_signed = NULL; |
|
378
|
0
|
|
|
|
|
|
ldns_rdf *time_signed_rdf = NULL; |
|
379
|
|
|
|
|
|
|
|
|
380
|
0
|
|
|
|
|
|
algorithm_rdf = ldns_rdf_new_frm_str(LDNS_RDF_TYPE_DNAME, algorithm_name); |
|
381
|
0
|
0
|
|
|
|
|
if(!key_name_rdf || !algorithm_rdf) { |
|
|
|
0
|
|
|
|
|
|
|
382
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
383
|
0
|
|
|
|
|
|
goto clean; |
|
384
|
|
|
|
|
|
|
} |
|
385
|
|
|
|
|
|
|
|
|
386
|
|
|
|
|
|
|
/* eww don't have create tsigtime rdf yet :( */ |
|
387
|
|
|
|
|
|
|
/* bleh :p */ |
|
388
|
0
|
0
|
|
|
|
|
if (gettimeofday(&tv_time_signed, NULL) == 0) { |
|
389
|
0
|
|
|
|
|
|
time_signed = LDNS_XMALLOC(uint8_t, 6); |
|
390
|
0
|
0
|
|
|
|
|
if(!time_signed) { |
|
391
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
392
|
0
|
|
|
|
|
|
goto clean; |
|
393
|
|
|
|
|
|
|
} |
|
394
|
0
|
|
|
|
|
|
ldns_write_uint64_as_uint48(time_signed, |
|
395
|
0
|
|
|
|
|
|
(uint64_t)tv_time_signed.tv_sec); |
|
396
|
|
|
|
|
|
|
} else { |
|
397
|
0
|
|
|
|
|
|
status = LDNS_STATUS_INTERNAL_ERR; |
|
398
|
0
|
|
|
|
|
|
goto clean; |
|
399
|
|
|
|
|
|
|
} |
|
400
|
|
|
|
|
|
|
|
|
401
|
0
|
|
|
|
|
|
time_signed_rdf = ldns_rdf_new(LDNS_RDF_TYPE_TSIGTIME, 6, time_signed); |
|
402
|
0
|
0
|
|
|
|
|
if(!time_signed_rdf) { |
|
403
|
0
|
|
|
|
|
|
LDNS_FREE(time_signed); |
|
404
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
405
|
0
|
|
|
|
|
|
goto clean; |
|
406
|
|
|
|
|
|
|
} |
|
407
|
|
|
|
|
|
|
|
|
408
|
0
|
|
|
|
|
|
fudge_rdf = ldns_native2rdf_int16(LDNS_RDF_TYPE_INT16, fudge); |
|
409
|
|
|
|
|
|
|
|
|
410
|
0
|
|
|
|
|
|
orig_id_rdf = ldns_native2rdf_int16(LDNS_RDF_TYPE_INT16, ldns_pkt_id(pkt)); |
|
411
|
|
|
|
|
|
|
|
|
412
|
0
|
|
|
|
|
|
error_rdf = ldns_native2rdf_int16(LDNS_RDF_TYPE_INT16, 0); |
|
413
|
|
|
|
|
|
|
|
|
414
|
0
|
|
|
|
|
|
other_data_rdf = ldns_native2rdf_int16_data(0, NULL); |
|
415
|
|
|
|
|
|
|
|
|
416
|
0
|
0
|
|
|
|
|
if(!fudge_rdf || !orig_id_rdf || !error_rdf || !other_data_rdf) { |
|
|
|
0
|
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
|
417
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
418
|
0
|
|
|
|
|
|
goto clean; |
|
419
|
|
|
|
|
|
|
} |
|
420
|
|
|
|
|
|
|
|
|
421
|
0
|
0
|
|
|
|
|
if (ldns_pkt2wire(&pkt_wire, pkt, &pkt_wire_len) != LDNS_STATUS_OK) { |
|
422
|
0
|
|
|
|
|
|
status = LDNS_STATUS_ERR; |
|
423
|
0
|
|
|
|
|
|
goto clean; |
|
424
|
|
|
|
|
|
|
} |
|
425
|
|
|
|
|
|
|
|
|
426
|
0
|
|
|
|
|
|
status = ldns_tsig_mac_new(&mac_rdf, pkt_wire, pkt_wire_len, |
|
427
|
|
|
|
|
|
|
key_data, key_name_rdf, fudge_rdf, algorithm_rdf, |
|
428
|
|
|
|
|
|
|
time_signed_rdf, error_rdf, other_data_rdf, query_mac, tsig_timers_only); |
|
429
|
|
|
|
|
|
|
|
|
430
|
0
|
0
|
|
|
|
|
if (!mac_rdf) { |
|
431
|
0
|
|
|
|
|
|
goto clean; |
|
432
|
|
|
|
|
|
|
} |
|
433
|
|
|
|
|
|
|
|
|
434
|
0
|
|
|
|
|
|
LDNS_FREE(pkt_wire); |
|
435
|
|
|
|
|
|
|
|
|
436
|
|
|
|
|
|
|
/* Create the TSIG RR */ |
|
437
|
0
|
|
|
|
|
|
tsig_rr = ldns_rr_new(); |
|
438
|
0
|
0
|
|
|
|
|
if(!tsig_rr) { |
|
439
|
0
|
|
|
|
|
|
status = LDNS_STATUS_MEM_ERR; |
|
440
|
0
|
|
|
|
|
|
goto clean; |
|
441
|
|
|
|
|
|
|
} |
|
442
|
0
|
|
|
|
|
|
ldns_rr_set_owner(tsig_rr, key_name_rdf); |
|
443
|
0
|
|
|
|
|
|
ldns_rr_set_class(tsig_rr, LDNS_RR_CLASS_ANY); |
|
444
|
0
|
|
|
|
|
|
ldns_rr_set_type(tsig_rr, LDNS_RR_TYPE_TSIG); |
|
445
|
0
|
|
|
|
|
|
ldns_rr_set_ttl(tsig_rr, 0); |
|
446
|
|
|
|
|
|
|
|
|
447
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, algorithm_rdf); |
|
448
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, time_signed_rdf); |
|
449
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, fudge_rdf); |
|
450
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, mac_rdf); |
|
451
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, orig_id_rdf); |
|
452
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, error_rdf); |
|
453
|
0
|
|
|
|
|
|
ldns_rr_push_rdf(tsig_rr, other_data_rdf); |
|
454
|
|
|
|
|
|
|
|
|
455
|
0
|
|
|
|
|
|
ldns_pkt_set_tsig(pkt, tsig_rr); |
|
456
|
|
|
|
|
|
|
|
|
457
|
0
|
|
|
|
|
|
return status; |
|
458
|
|
|
|
|
|
|
|
|
459
|
|
|
|
|
|
|
clean: |
|
460
|
0
|
|
|
|
|
|
LDNS_FREE(pkt_wire); |
|
461
|
0
|
|
|
|
|
|
ldns_rdf_free(key_name_rdf); |
|
462
|
0
|
|
|
|
|
|
ldns_rdf_free(algorithm_rdf); |
|
463
|
0
|
|
|
|
|
|
ldns_rdf_free(time_signed_rdf); |
|
464
|
0
|
|
|
|
|
|
ldns_rdf_free(fudge_rdf); |
|
465
|
0
|
|
|
|
|
|
ldns_rdf_free(orig_id_rdf); |
|
466
|
0
|
|
|
|
|
|
ldns_rdf_free(error_rdf); |
|
467
|
0
|
|
|
|
|
|
ldns_rdf_free(other_data_rdf); |
|
468
|
0
|
|
|
|
|
|
return status; |
|
469
|
|
|
|
|
|
|
} |
|
470
|
|
|
|
|
|
|
#endif /* HAVE_SSL */ |