Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
What's new
10
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Open sidebar
ISC Open Source Projects
BIND
Commits
0f80bfec
Commit
0f80bfec
authored
May 30, 2000
by
Brian Wellington
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
The message code now has functions to manipulate TSIG and SIG(0), and the
callers use these functions. Also a lot of TSIG cleanup.
parent
4bf54f18
Changes
7
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
522 additions
and
250 deletions
+522
-250
bin/named/xfrout.c
bin/named/xfrout.c
+15
-21
lib/dns/include/dns/message.h
lib/dns/include/dns/message.h
+85
-5
lib/dns/message.c
lib/dns/message.c
+261
-41
lib/dns/request.c
lib/dns/request.c
+9
-11
lib/dns/resolver.c
lib/dns/resolver.c
+30
-16
lib/dns/tsig.c
lib/dns/tsig.c
+110
-128
lib/dns/xfrin.c
lib/dns/xfrin.c
+12
-28
No files found.
bin/named/xfrout.c
View file @
0f80bfec
...
...
@@ -15,7 +15,7 @@
* SOFTWARE.
*/
/* $Id: xfrout.c,v 1.6
3
2000/05/
26 00:16:35
bwelling Exp $ */
/* $Id: xfrout.c,v 1.6
4
2000/05/
30 23:14:48
bwelling Exp $ */
#include <config.h>
...
...
@@ -26,6 +26,7 @@
#include <dns/db.h>
#include <dns/dbiterator.h>
#include <dns/fixedname.h>
#include <dns/journal.h>
#include <dns/message.h>
#include <dns/peer.h>
...
...
@@ -741,7 +742,7 @@ typedef struct {
unsigned
int
txmemlen
;
unsigned
int
nmsg
;
/* Number of messages sent */
dns_tsigkey_t
*
tsigkey
;
/* Key used to create TSIG */
dns_rdata_any_tsig_t
*
lasttsig
;
/* the last TSIG */
isc_buffer_t
*
lasttsig
;
/* the last TSIG */
isc_boolean_t
many_answers
;
int
sends
;
/* Send in progress */
isc_boolean_t
shuttingdown
;
...
...
@@ -752,7 +753,7 @@ xfrout_ctx_create(isc_mem_t *mctx, ns_client_t *client,
unsigned
int
id
,
dns_name_t
*
qname
,
dns_rdatatype_t
qtype
,
dns_db_t
*
db
,
dns_dbversion_t
*
ver
,
isc_quota_t
*
quota
,
rrstream_t
*
stream
,
dns_tsigkey_t
*
tsigkey
,
dns_rdata_any_tsig
_t
*
lasttsig
,
isc_buffer
_t
*
lasttsig
,
unsigned
int
maxtime
,
unsigned
int
idletime
,
isc_boolean_t
many_answers
,
...
...
@@ -810,6 +811,7 @@ ns_xfr_start(ns_client_t *client, dns_rdatatype_t reqtype) {
dns_transfer_format_t
format
=
client
->
view
->
transfer_format
;
isc_netaddr_t
na
;
dns_peer_t
*
peer
=
NULL
;
isc_buffer_t
*
tsigbuf
=
NULL
;
switch
(
reqtype
)
{
case
dns_rdatatype_axfr
:
...
...
@@ -1022,13 +1024,15 @@ ns_xfr_start(ns_client_t *client, dns_rdatatype_t reqtype) {
data_stream
=
NULL
;
have_stream:
CHECK
(
dns_message_getquerytsig
(
request
,
mctx
,
&
tsigbuf
));
/*
* Create the xfrout context object. This transfers the ownership
* of "stream", "db", "ver", and "quota" to the xfrout context object.
*/
CHECK
(
xfrout_ctx_create
(
mctx
,
client
,
request
->
id
,
question_name
,
reqtype
,
db
,
ver
,
quota
,
stream
,
dns_message_gettsigkey
(
request
),
request
->
tsig
,
dns_message_gettsigkey
(
request
),
tsigbuf
,
dns_zone_getmaxxfrout
(
zone
),
dns_zone_getidleout
(
zone
),
(
format
==
dns_many_answers
)
?
...
...
@@ -1084,7 +1088,7 @@ xfrout_ctx_create(isc_mem_t *mctx, ns_client_t *client, unsigned int id,
dns_name_t
*
qname
,
dns_rdatatype_t
qtype
,
dns_db_t
*
db
,
dns_dbversion_t
*
ver
,
isc_quota_t
*
quota
,
rrstream_t
*
stream
,
dns_tsigkey_t
*
tsigkey
,
dns_rdata_any_tsig
_t
*
lasttsig
,
unsigned
int
maxtime
,
isc_buffer
_t
*
lasttsig
,
unsigned
int
maxtime
,
unsigned
int
idletime
,
isc_boolean_t
many_answers
,
xfrout_ctx_t
**
xfrp
)
{
...
...
@@ -1215,7 +1219,9 @@ sendstream(xfrout_ctx_t *xfr) {
if
((
xfr
->
client
->
attributes
&
NS_CLIENTATTR_RA
)
!=
0
)
msg
->
flags
|=
DNS_MESSAGEFLAG_RA
;
dns_message_settsigkey
(
msg
,
xfr
->
tsigkey
);
msg
->
querytsig
=
xfr
->
lasttsig
;
CHECK
(
dns_message_setquerytsig
(
msg
,
xfr
->
lasttsig
));
if
(
xfr
->
lasttsig
!=
NULL
)
isc_buffer_free
(
&
xfr
->
lasttsig
);
/*
* Include a question section in the first message only.
...
...
@@ -1384,17 +1390,7 @@ sendstream(xfrout_ctx_t *xfr) {
}
/* Advance lasttsig to be the last TSIG generated */
xfr
->
lasttsig
=
msg
->
tsig
;
/* Clear this field so the TSIG is not destroyed */
msg
->
tsig
=
NULL
;
/*
* If this is the first message, clear this too, since this is
* also pointed to by the request.
*/
if
(
xfr
->
nmsg
==
0
)
msg
->
querytsig
=
NULL
;
CHECK
(
dns_message_getquerytsig
(
msg
,
xfr
->
mctx
,
&
xfr
->
lasttsig
));
xfr
->
nmsg
++
;
...
...
@@ -1426,10 +1422,8 @@ xfrout_ctx_destroy(xfrout_ctx_t **xfrp) {
isc_mem_put
(
xfr
->
mctx
,
xfr
->
buf
.
base
,
xfr
->
buf
.
length
);
if
(
xfr
->
txmem
!=
NULL
)
isc_mem_put
(
xfr
->
mctx
,
xfr
->
txmem
,
xfr
->
txmemlen
);
if
(
xfr
->
lasttsig
!=
NULL
)
{
dns_rdata_freestruct
(
xfr
->
lasttsig
);
isc_mem_put
(
xfr
->
mctx
,
xfr
->
lasttsig
,
sizeof
(
*
xfr
->
lasttsig
));
}
if
(
xfr
->
lasttsig
!=
NULL
)
isc_buffer_free
(
&
xfr
->
lasttsig
);
if
(
xfr
->
quota
!=
NULL
)
isc_quota_detach
(
&
xfr
->
quota
);
if
(
xfr
->
ver
!=
NULL
)
...
...
lib/dns/include/dns/message.h
View file @
0f80bfec
...
...
@@ -26,7 +26,6 @@
#include <isc/magic.h>
#include <dns/compress.h>
#include <dns/rdatastruct.h>
#include <dns/types.h>
#include <dst/dst.h>
...
...
@@ -178,6 +177,7 @@ struct dns_message {
unsigned
int
verify_attempted
:
1
;
unsigned
int
opt_reserved
;
unsigned
int
sig_reserved
;
unsigned
int
reserved
;
/* reserved space (render) */
isc_buffer_t
*
buffer
;
...
...
@@ -199,8 +199,7 @@ struct dns_message {
dns_rcode_t
tsigstatus
;
dns_rcode_t
querytsigstatus
;
dns_name_t
*
tsigname
;
dns_rdata_any_tsig_t
*
tsig
;
dns_rdata_any_tsig_t
*
querytsig
;
dns_rdataset_t
*
querytsigset
;
dns_tsigkey_t
*
tsigkey
;
void
*
tsigctx
;
int
sigstart
;
...
...
@@ -952,7 +951,7 @@ dns_message_gettsig(dns_message_t *msg, dns_name_t **owner);
* The TSIG rdataset of 'msg', or NULL if there isn't one.
*/
void
isc_result_t
dns_message_settsigkey
(
dns_message_t
*
msg
,
dns_tsigkey_t
*
key
);
/*
* Set the tsig key for 'msg'. This is only necessary for when rendering a
...
...
@@ -961,8 +960,16 @@ dns_message_settsigkey(dns_message_t *msg, dns_tsigkey_t *key);
*
* Requires:
*
* 'msg' is a valid message
* 'msg' is a valid message with rendering intent,
* dns_message_renderbegin() has been called, and no sections have been
* rendered.
* 'key' is a valid tsig key or NULL.
*
* Returns:
*
* ISC_R_SUCCESS -- all is well.
*
* ISC_R_NOSPACE -- there is no space for the TSIG record.
*/
dns_tsigkey_t
*
...
...
@@ -975,6 +982,50 @@ dns_message_gettsigkey(dns_message_t *msg);
* 'msg' is a valid message
*/
isc_result_t
dns_message_setquerytsig
(
dns_message_t
*
msg
,
isc_buffer_t
*
querytsig
);
/*
* Indicates that 'querytsig' is the TSIG from the signed query for which
* 'msg' is the response. This is also used for chained TSIGs in TCP
* responses.
*
* Requires:
*
* 'querytsig' is a valid buffer as returned by dns_message_getquerytsig()
* or NULL
*
* 'msg' is a valid message
*
* Returns:
*
* ISC_R_SUCCESS
* ISC_R_NOMEMORY
*/
isc_result_t
dns_message_getquerytsig
(
dns_message_t
*
msg
,
isc_mem_t
*
mctx
,
isc_buffer_t
**
querytsig
);
/*
* Gets the tsig from the TSIG from the signed query 'msg'. This is also used
* for chained TSIGs in TCP responses. Unlike dns_message_gettsig, this makes
* a copy of the data, so can be used if the message is destroyed.
*
* Requires:
*
* 'msg' is a valid signed message
* 'mctx' is a valid memory context
* querytsig != NULL && *querytsig == NULL
*
* Returns:
*
* ISC_R_SUCCESS
* ISC_R_NOMEMORY
*
* Ensures:
* 'tsig' points to NULL or an allocated buffer which must be freed
* by the caller.
*/
dns_rdataset_t
*
dns_message_getsig0
(
dns_message_t
*
msg
,
dns_name_t
**
owner
);
/*
...
...
@@ -990,6 +1041,35 @@ dns_message_getsig0(dns_message_t *msg, dns_name_t **owner);
* The SIG(0) rdataset of 'msg', or NULL if there isn't one.
*/
isc_result_t
dns_message_setsig0key
(
dns_message_t
*
msg
,
dst_key_t
*
key
);
/*
* Set the SIG(0) key for 'msg'.
*
* Requires:
*
* 'msg' is a valid message with rendering intent,
* dns_message_renderbegin() has been called, and no sections have been
* rendered.
* 'key' is a valid sig key or NULL.
*
* Returns:
*
* ISC_R_SUCCESS -- all is well.
*
* ISC_R_NOSPACE -- there is no space for the SIG(0) record.
*/
dst_key_t
*
dns_message_getsig0key
(
dns_message_t
*
msg
);
/*
* Gets the SIG(0) key for 'msg'.
*
* Requires:
*
* 'msg' is a valid message
*/
void
dns_message_takebuffer
(
dns_message_t
*
msg
,
isc_buffer_t
**
buffer
);
/*
...
...
lib/dns/message.c
View file @
0f80bfec
...
...
@@ -32,6 +32,7 @@
#include <dns/rdata.h>
#include <dns/rdatalist.h>
#include <dns/rdataset.h>
#include <dns/rdatastruct.h>
#include <dns/result.h>
#include <dns/tsig.h>
#include <dns/view.h>
...
...
@@ -325,6 +326,7 @@ msginitprivate(dns_message_t *m) {
m
->
tsigname
=
NULL
;
m
->
state
=
DNS_SECTION_ANY
;
/* indicate nothing parsed or rendered */
m
->
opt_reserved
=
0
;
m
->
sig_reserved
=
0
;
m
->
reserved
=
0
;
m
->
buffer
=
NULL
;
m
->
need_cctx_cleanup
=
0
;
...
...
@@ -332,8 +334,8 @@ msginitprivate(dns_message_t *m) {
static
inline
void
msginittsig
(
dns_message_t
*
m
)
{
m
->
tsigstatus
=
m
->
querytsigstatus
=
dns_rcode_noerror
;
m
->
tsig
=
m
->
querytsig
=
NULL
;
m
->
tsigstatus
=
dns_rcode_noerror
;
m
->
querytsigstatus
=
dns_rcode_noerror
;
m
->
tsigkey
=
NULL
;
m
->
tsigctx
=
NULL
;
m
->
sigstart
=
-
1
;
...
...
@@ -341,6 +343,7 @@ msginittsig(dns_message_t *m) {
m
->
sig0status
=
dns_rcode_noerror
;
m
->
query
=
NULL
;
m
->
saved
=
NULL
;
m
->
querytsigset
=
NULL
;
}
/*
...
...
@@ -406,12 +409,26 @@ msgresetopt(dns_message_t *msg)
}
static
void
msgresetsigs
(
dns_message_t
*
msg
)
{
msgresetsigs
(
dns_message_t
*
msg
,
isc_boolean_t
replying
)
{
if
(
msg
->
sig_reserved
>
0
)
{
dns_message_renderrelease
(
msg
,
msg
->
sig_reserved
);
msg
->
sig_reserved
=
0
;
}
if
(
msg
->
tsigset
!=
NULL
)
{
INSIST
(
dns_rdataset_isassociated
(
msg
->
tsigset
));
INSIST
(
msg
->
namepool
!=
NULL
);
dns_rdataset_disassociate
(
msg
->
tsigset
);
isc_mempool_put
(
msg
->
rdspool
,
msg
->
tsigset
);
if
(
replying
)
{
INSIST
(
msg
->
querytsigset
==
NULL
);
msg
->
querytsigset
=
msg
->
tsigset
;
}
else
{
dns_rdataset_disassociate
(
msg
->
tsigset
);
isc_mempool_put
(
msg
->
rdspool
,
msg
->
tsigset
);
if
(
msg
->
querytsigset
!=
NULL
)
{
dns_rdataset_disassociate
(
msg
->
querytsigset
);
isc_mempool_put
(
msg
->
rdspool
,
msg
->
querytsigset
);
}
}
isc_mempool_put
(
msg
->
namepool
,
msg
->
tsigname
);
msg
->
tsigset
=
NULL
;
msg
->
tsigname
=
NULL
;
...
...
@@ -440,7 +457,7 @@ msgreset(dns_message_t *msg, isc_boolean_t everything) {
msgresetnames
(
msg
,
0
);
msgresetopt
(
msg
);
msgresetsigs
(
msg
);
msgresetsigs
(
msg
,
ISC_FALSE
);
/*
* Clean up linked lists.
...
...
@@ -507,20 +524,6 @@ msgreset(dns_message_t *msg, isc_boolean_t everything) {
if
(
msg
->
need_cctx_cleanup
==
1
)
dns_compress_invalidate
(
&
msg
->
cctx
);
if
(
msg
->
tsig
!=
NULL
)
{
dns_rdata_freestruct
(
msg
->
tsig
);
isc_mem_put
(
msg
->
mctx
,
msg
->
tsig
,
sizeof
(
dns_rdata_any_tsig_t
));
msg
->
tsig
=
NULL
;
}
if
(
msg
->
querytsig
!=
NULL
)
{
dns_rdata_freestruct
(
msg
->
querytsig
);
isc_mem_put
(
msg
->
mctx
,
msg
->
querytsig
,
sizeof
(
dns_rdata_any_tsig_t
));
msg
->
querytsig
=
NULL
;
}
if
(
msg
->
tsigkey
!=
NULL
)
{
dns_tsigkey_detach
(
&
msg
->
tsigkey
);
msg
->
tsigkey
=
NULL
;
...
...
@@ -556,6 +559,43 @@ msgreset(dns_message_t *msg, isc_boolean_t everything) {
msginit
(
msg
);
}
static
unsigned
int
spacefortsig
(
dns_tsigkey_t
*
key
,
int
otherlen
)
{
isc_region_t
r1
,
r2
;
unsigned
int
x
;
isc_result_t
result
;
/*
* The space required for an TSIG record is:
*
* n1 bytes for the name
* 2 bytes for the type
* 2 bytes for the class
* 4 bytes for the ttl
* 6 bytes for the time signed
* 2 bytes for the fudge
* 2 bytes for the MAC size
* x bytes for the MAC
* 2 bytes for the original id
* 2 bytes for the error
* 2 bytes for the other data length
* y bytes for the other data (at most)
* ---------------------------------
* 30 + n1 + n2 + x + y bytes
*/
dns_name_toregion
(
&
key
->
name
,
&
r1
);
dns_name_toregion
(
&
key
->
algorithm
,
&
r2
);
if
(
key
->
key
==
NULL
)
x
=
0
;
else
{
result
=
dst_key_sigsize
(
key
->
key
,
&
x
);
if
(
result
!=
ISC_R_SUCCESS
)
x
=
0
;
}
return
(
24
+
r1
.
length
+
r2
.
length
+
x
+
otherlen
);
}
isc_result_t
dns_message_create
(
isc_mem_t
*
mctx
,
unsigned
int
intent
,
dns_message_t
**
msgp
)
{
...
...
@@ -1486,6 +1526,9 @@ dns_message_renderbegin(dns_message_t *msg, isc_buffer_t *buffer) {
isc_buffer_availableregion
(
buffer
,
&
r
);
REQUIRE
(
r
.
length
>=
DNS_MESSAGE_HEADERLEN
);
if
(
r
.
length
<
msg
->
reserved
)
return
(
ISC_R_NOSPACE
);
result
=
dns_compress_init
(
&
msg
->
cctx
,
-
1
,
msg
->
mctx
);
if
(
result
!=
ISC_R_SUCCESS
)
return
(
result
);
...
...
@@ -1533,7 +1576,6 @@ dns_message_renderchangebuffer(dns_message_t *msg, isc_buffer_t *buffer) {
void
dns_message_renderrelease
(
dns_message_t
*
msg
,
unsigned
int
space
)
{
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
(
msg
->
buffer
!=
NULL
);
REQUIRE
(
space
<=
msg
->
reserved
);
msg
->
reserved
-=
space
;
...
...
@@ -1544,11 +1586,12 @@ dns_message_renderreserve(dns_message_t *msg, unsigned int space) {
isc_region_t
r
;
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
(
msg
->
buffer
!=
NULL
);
isc_buffer_availableregion
(
msg
->
buffer
,
&
r
);
if
(
r
.
length
<
(
space
+
msg
->
reserved
))
return
(
ISC_R_NOSPACE
);
if
(
msg
->
buffer
!=
NULL
)
{
isc_buffer_availableregion
(
msg
->
buffer
,
&
r
);
if
(
r
.
length
<
(
space
+
msg
->
reserved
))
return
(
ISC_R_NOSPACE
);
}
msg
->
reserved
+=
space
;
...
...
@@ -1772,7 +1815,8 @@ dns_message_renderend(dns_message_t *msg) {
}
if
(
msg
->
tsigkey
!=
NULL
)
{
REQUIRE
(
msg
->
tsig
==
NULL
);
dns_message_renderrelease
(
msg
,
msg
->
sig_reserved
);
msg
->
sig_reserved
=
0
;
result
=
dns_tsig_sign
(
msg
);
if
(
result
!=
ISC_R_SUCCESS
)
return
(
result
);
...
...
@@ -1785,6 +1829,8 @@ dns_message_renderend(dns_message_t *msg) {
}
else
if
(
msg
->
sig0key
!=
NULL
)
{
dns_message_renderrelease
(
msg
,
msg
->
sig_reserved
);
msg
->
sig_reserved
=
0
;
result
=
dns_dnssec_signmessage
(
msg
,
msg
->
sig0key
);
if
(
result
!=
ISC_R_SUCCESS
)
return
(
result
);
...
...
@@ -2100,6 +2146,7 @@ dns_message_peekheader(isc_buffer_t *source, dns_messageid_t *idp,
isc_result_t
dns_message_reply
(
dns_message_t
*
msg
,
isc_boolean_t
want_question_section
)
{
unsigned
int
first_section
;
isc_result_t
result
;
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
((
msg
->
flags
&
DNS_MESSAGEFLAG_QR
)
==
0
);
...
...
@@ -2118,7 +2165,7 @@ dns_message_reply(dns_message_t *msg, isc_boolean_t want_question_section) {
msg
->
from_to_wire
=
DNS_MESSAGE_INTENTRENDER
;
msgresetnames
(
msg
,
first_section
);
msgresetopt
(
msg
);
msgresetsigs
(
msg
);
msgresetsigs
(
msg
,
ISC_TRUE
);
msginitprivate
(
msg
);
/*
* We now clear most flags and then set QR, ensuring that the
...
...
@@ -2128,15 +2175,21 @@ dns_message_reply(dns_message_t *msg, isc_boolean_t want_question_section) {
msg
->
flags
|=
DNS_MESSAGEFLAG_QR
;
/*
* This saves the query TSIG information for later use, if there is
* any. This only happens once - that is, if dns_message_reply
* has already moved the variables, this has no effect.
* This saves the query TSIG status, if the query was signed, and
* reserves space in the reply for the TSIG.
*/
if
(
msg
->
tsig
!=
NULL
)
{
msg
->
querytsig
=
msg
->
tsig
;
msg
->
tsig
=
NULL
;
if
(
msg
->
querytsigset
!=
NULL
)
{
unsigned
int
otherlen
=
0
;
msg
->
querytsigstatus
=
msg
->
tsigstatus
;
msg
->
tsigstatus
=
dns_rcode_noerror
;
if
(
msg
->
querytsigstatus
==
dns_tsigerror_badtime
)
otherlen
=
6
;
msg
->
sig_reserved
=
spacefortsig
(
msg
->
tsigkey
,
otherlen
);
result
=
dns_message_renderreserve
(
msg
,
msg
->
sig_reserved
);
if
(
result
!=
ISC_R_SUCCESS
)
{
msg
->
sig_reserved
=
0
;
return
(
result
);
}
}
if
(
msg
->
saved
!=
NULL
)
{
msg
->
query
=
msg
->
saved
;
...
...
@@ -2188,7 +2241,6 @@ dns_message_setopt(dns_message_t *msg, dns_rdataset_t *opt) {
REQUIRE
(
msg
->
state
==
DNS_SECTION_ANY
);
msgresetopt
(
msg
);
msgresetsigs
(
msg
);
result
=
dns_rdataset_first
(
opt
);
if
(
result
!=
ISC_R_SUCCESS
)
...
...
@@ -2220,18 +2272,31 @@ dns_message_gettsig(dns_message_t *msg, dns_name_t **owner) {
return
(
msg
->
tsigset
);
}
void
isc_result_t
dns_message_settsigkey
(
dns_message_t
*
msg
,
dns_tsigkey_t
*
key
)
{
isc_result_t
result
;
/*
* Set the TSIG key for 'msg'
*/
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
(
msg
->
tsigkey
==
NULL
);
REQUIRE
(
msg
->
state
==
DNS_SECTION_ANY
);
REQUIRE
(
msg
->
tsigkey
==
NULL
&&
msg
->
sig0key
==
NULL
);
if
(
key
!=
NULL
)
if
(
key
!=
NULL
)
{
dns_tsigkey_attach
(
key
,
&
msg
->
tsigkey
);
if
(
msg
->
from_to_wire
==
DNS_MESSAGE_INTENTRENDER
)
{
msg
->
sig_reserved
=
spacefortsig
(
msg
->
tsigkey
,
0
);
result
=
dns_message_renderreserve
(
msg
,
msg
->
sig_reserved
);
if
(
result
!=
ISC_R_SUCCESS
)
{
msg
->
sig_reserved
=
0
;
return
(
result
);
}
}
}
return
(
ISC_R_SUCCESS
);
}
dns_tsigkey_t
*
...
...
@@ -2246,6 +2311,88 @@ dns_message_gettsigkey(dns_message_t *msg) {
return
(
msg
->
tsigkey
);
}
isc_result_t
dns_message_setquerytsig
(
dns_message_t
*
msg
,
isc_buffer_t
*
querytsig
)
{
dns_rdata_t
*
rdata
=
NULL
;
dns_rdatalist_t
*
list
=
NULL
;
dns_rdataset_t
*
set
=
NULL
;
isc_buffer_t
*
buf
=
NULL
;
isc_region_t
r
;
isc_result_t
result
;
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
(
msg
->
querytsigset
==
NULL
);
if
(
querytsig
==
NULL
)
return
(
ISC_R_SUCCESS
);
result
=
dns_message_gettemprdata
(
msg
,
&
rdata
);
if
(
result
!=
ISC_R_SUCCESS
)
goto
cleanup
;
result
=
dns_message_gettemprdatalist
(
msg
,
&
list
);
if
(
result
!=
ISC_R_SUCCESS
)
goto
cleanup
;
result
=
dns_message_gettemprdataset
(
msg
,
&
set
);
if
(
result
!=
ISC_R_SUCCESS
)
goto
cleanup
;
isc_buffer_usedregion
(
querytsig
,
&
r
);
result
=
isc_buffer_allocate
(
msg
->
mctx
,
&
buf
,
r
.
length
);
if
(
result
!=
ISC_R_SUCCESS
)
goto
cleanup
;
isc_buffer_putmem
(
buf
,
r
.
base
,
r
.
length
);
isc_buffer_usedregion
(
buf
,
&
r
);
dns_rdata_init
(
rdata
);
dns_rdata_fromregion
(
rdata
,
dns_rdataclass_any
,
dns_rdatatype_tsig
,
&
r
);
dns_message_takebuffer
(
msg
,
&
buf
);
ISC_LIST_INIT
(
list
->
rdata
);
ISC_LIST_APPEND
(
list
->
rdata
,
rdata
,
link
);
result
=
dns_rdatalist_tordataset
(
list
,
set
);
if
(
result
!=
ISC_R_SUCCESS
)
goto
cleanup
;
msg
->
querytsigset
=
set
;
return
(
result
);
cleanup:
if
(
rdata
!=
NULL
)
dns_message_puttemprdata
(
msg
,
&
rdata
);
if
(
list
!=
NULL
)
dns_message_puttemprdatalist
(
msg
,
&
list
);
if
(
set
!=
NULL
)
dns_message_puttemprdataset
(
msg
,
&
set
);
return
(
ISC_R_NOMEMORY
);
}
isc_result_t
dns_message_getquerytsig
(
dns_message_t
*
msg
,
isc_mem_t
*
mctx
,
isc_buffer_t
**
querytsig
)
{
isc_result_t
result
;
dns_rdata_t
rdata
;
isc_region_t
r
;
REQUIRE
(
DNS_MESSAGE_VALID
(
msg
));
REQUIRE
(
mctx
!=
NULL
);
REQUIRE
(
querytsig
!=
NULL
&&
*
querytsig
==
NULL
);
if
(
msg
->
tsigset
==
NULL
)
return
(
ISC_R_SUCCESS
);
result
=
dns_rdataset_first
(
msg
->
tsigset
);
if
(
result
!=
ISC_R_SUCCESS
)
return
(
result
);
dns_rdataset_current
(
msg
->
tsigset
,
&
rdata
);
dns_rdata_toregion
(
&
rdata
,
&
r
);
result
=
isc_buffer_allocate
(
mctx
,
querytsig
,
r
.
length
);
if
(
result
!=
ISC_R_SUCCESS
)
return
(
result
);
isc_buffer_putmem
(
*
querytsig
,
r
.
base
,
r
.
length
);
return
(
ISC_R_SUCCESS
);
}
dns_rdataset_t
*
dns_message_getsig0
(
dns_message_t
*
msg
,
dns_name_t
**
owner
)
{
...
...
@@ -2272,6 +2419,71 @@ dns_message_getsig0(dns_message_t *msg, dns_name_t **owner) {
}
}
isc_result_t
dns_message_setsig0key
(
dns_message_t
*
msg
,
dst_key_t
*
key
)
{
isc_region_t
r
;
unsigned
int
x
;
isc_result_t
result
;
/*
* Set the SIG(0) key for 'msg'
*/
/*
* The space required for an SIG(0) record is:
*
* 1 byte for the name
* 2 bytes for the type
* 2 bytes for the class
* 4 bytes for the ttl
* 2 bytes for the type covered
* 1 byte for the algorithm
* 1 bytes for the labels
* 4 bytes for the original ttl
* 4 bytes for the signature expiration
* 4 bytes for the signature inception
* 2 bytes for the key tag