diff options
| -rw-r--r-- | meta/recipes-connectivity/bind/bind/CVE-2015-8000.patch | 194 | ||||
| -rw-r--r-- | meta/recipes-connectivity/bind/bind_9.9.5.bb | 1 |
2 files changed, 195 insertions, 0 deletions
diff --git a/meta/recipes-connectivity/bind/bind/CVE-2015-8000.patch b/meta/recipes-connectivity/bind/bind/CVE-2015-8000.patch new file mode 100644 index 0000000000..b8d841206f --- /dev/null +++ b/meta/recipes-connectivity/bind/bind/CVE-2015-8000.patch | |||
| @@ -0,0 +1,194 @@ | |||
| 1 | responses with a malformed class attribute can trigger an | ||
| 2 | assertion failure in db.c | ||
| 3 | |||
| 4 | [security] | ||
| 5 | Insufficient testing when parsing a message allowed records with | ||
| 6 | an incorrect class to be be accepted, triggering a REQUIRE failure | ||
| 7 | when those records were subsequently cached. (CVE-2015-8000) [RT#4098] | ||
| 8 | |||
| 9 | Upstream-Status: Backport | ||
| 10 | |||
| 11 | [The patch is taken from BIND 9.9.4: | ||
| 12 | https://bugzilla.redhat.com/attachment.cgi?id=1105581] | ||
| 13 | |||
| 14 | Signed-off-by: Sona Sarmadi <sona.sarmadi@enea.com> | ||
| 15 | --- | ||
| 16 | diff --git a/lib/dns/include/dns/message.h b/lib/dns/include/dns/message.h | ||
| 17 | index a6862fa..d999e75 100644 | ||
| 18 | --- a/lib/dns/include/dns/message.h | ||
| 19 | +++ b/lib/dns/include/dns/message.h | ||
| 20 | @@ -210,6 +210,8 @@ struct dns_message { | ||
| 21 | unsigned int verify_attempted : 1; | ||
| 22 | unsigned int free_query : 1; | ||
| 23 | unsigned int free_saved : 1; | ||
| 24 | + unsigned int tkey : 1; | ||
| 25 | + unsigned int rdclass_set : 1; | ||
| 26 | |||
| 27 | unsigned int opt_reserved; | ||
| 28 | unsigned int sig_reserved; | ||
| 29 | @@ -1374,6 +1376,15 @@ dns_message_buildopt(dns_message_t *msg, dns_rdataset_t **opt, | ||
| 30 | * \li other. | ||
| 31 | */ | ||
| 32 | |||
| 33 | +void | ||
| 34 | +dns_message_setclass(dns_message_t *msg, dns_rdataclass_t rdclass); | ||
| 35 | +/*%< | ||
| 36 | + * Set the expected class of records in the response. | ||
| 37 | + * | ||
| 38 | + * Requires: | ||
| 39 | + * \li msg be a valid message with parsing intent. | ||
| 40 | + */ | ||
| 41 | + | ||
| 42 | ISC_LANG_ENDDECLS | ||
| 43 | |||
| 44 | #endif /* DNS_MESSAGE_H */ | ||
| 45 | diff --git a/lib/dns/message.c b/lib/dns/message.c | ||
| 46 | index 53efc5a..73def73 100644 | ||
| 47 | --- a/lib/dns/message.c | ||
| 48 | +++ b/lib/dns/message.c | ||
| 49 | @@ -436,6 +436,8 @@ msginit(dns_message_t *m) { | ||
| 50 | m->saved.base = NULL; | ||
| 51 | m->saved.length = 0; | ||
| 52 | m->free_saved = 0; | ||
| 53 | + m->tkey = 0; | ||
| 54 | + m->rdclass_set = 0; | ||
| 55 | m->querytsig = NULL; | ||
| 56 | } | ||
| 57 | |||
| 58 | @@ -1086,13 +1088,19 @@ getquestions(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx, | ||
| 59 | * If this class is different than the one we already read, | ||
| 60 | * this is an error. | ||
| 61 | */ | ||
| 62 | - if (msg->state == DNS_SECTION_ANY) { | ||
| 63 | - msg->state = DNS_SECTION_QUESTION; | ||
| 64 | + if (msg->rdclass_set == 0) { | ||
| 65 | msg->rdclass = rdclass; | ||
| 66 | + msg->rdclass_set = 1; | ||
| 67 | } else if (msg->rdclass != rdclass) | ||
| 68 | DO_FORMERR; | ||
| 69 | |||
| 70 | /* | ||
| 71 | + * Is this a TKEY query? | ||
| 72 | + */ | ||
| 73 | + if (rdtype == dns_rdatatype_tkey) | ||
| 74 | + msg->tkey = 1; | ||
| 75 | + | ||
| 76 | + /* | ||
| 77 | * Can't ask the same question twice. | ||
| 78 | */ | ||
| 79 | result = dns_message_find(name, rdclass, rdtype, 0, NULL); | ||
| 80 | @@ -1236,12 +1244,12 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx, | ||
| 81 | * If there was no question section, we may not yet have | ||
| 82 | * established a class. Do so now. | ||
| 83 | */ | ||
| 84 | - if (msg->state == DNS_SECTION_ANY && | ||
| 85 | + if (msg->rdclass_set == 0 && | ||
| 86 | rdtype != dns_rdatatype_opt && /* class is UDP SIZE */ | ||
| 87 | rdtype != dns_rdatatype_tsig && /* class is ANY */ | ||
| 88 | rdtype != dns_rdatatype_tkey) { /* class is undefined */ | ||
| 89 | msg->rdclass = rdclass; | ||
| 90 | - msg->state = DNS_SECTION_QUESTION; | ||
| 91 | + msg->rdclass_set = 1; | ||
| 92 | } | ||
| 93 | |||
| 94 | /* | ||
| 95 | @@ -1251,7 +1259,7 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx, | ||
| 96 | if (msg->opcode != dns_opcode_update | ||
| 97 | && rdtype != dns_rdatatype_tsig | ||
| 98 | && rdtype != dns_rdatatype_opt | ||
| 99 | - && rdtype != dns_rdatatype_dnskey /* in a TKEY query */ | ||
| 100 | + && rdtype != dns_rdatatype_key /* in a TKEY query */ | ||
| 101 | && rdtype != dns_rdatatype_sig /* SIG(0) */ | ||
| 102 | && rdtype != dns_rdatatype_tkey /* Win2000 TKEY */ | ||
| 103 | && msg->rdclass != dns_rdataclass_any | ||
| 104 | @@ -1259,6 +1267,16 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx, | ||
| 105 | DO_FORMERR; | ||
| 106 | |||
| 107 | /* | ||
| 108 | + * If this is not a TKEY query/response then the KEY | ||
| 109 | + * record's class needs to match. | ||
| 110 | + */ | ||
| 111 | + if (msg->opcode != dns_opcode_update && !msg->tkey && | ||
| 112 | + rdtype == dns_rdatatype_key && | ||
| 113 | + msg->rdclass != dns_rdataclass_any && | ||
| 114 | + msg->rdclass != rdclass) | ||
| 115 | + DO_FORMERR; | ||
| 116 | + | ||
| 117 | + /* | ||
| 118 | * Special type handling for TSIG, OPT, and TKEY. | ||
| 119 | */ | ||
| 120 | if (rdtype == dns_rdatatype_tsig) { | ||
| 121 | @@ -1372,6 +1390,10 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx, | ||
| 122 | skip_name_search = ISC_TRUE; | ||
| 123 | skip_type_search = ISC_TRUE; | ||
| 124 | issigzero = ISC_TRUE; | ||
| 125 | + } else { | ||
| 126 | + if (msg->rdclass != dns_rdataclass_any && | ||
| 127 | + msg->rdclass != rdclass) | ||
| 128 | + DO_FORMERR; | ||
| 129 | } | ||
| 130 | } else | ||
| 131 | covers = 0; | ||
| 132 | @@ -1610,6 +1632,7 @@ dns_message_parse(dns_message_t *msg, isc_buffer_t *source, | ||
| 133 | msg->counts[DNS_SECTION_ADDITIONAL] = isc_buffer_getuint16(source); | ||
| 134 | |||
| 135 | msg->header_ok = 1; | ||
| 136 | + msg->state = DNS_SECTION_QUESTION; | ||
| 137 | |||
| 138 | /* | ||
| 139 | * -1 means no EDNS. | ||
| 140 | @@ -3550,3 +3573,15 @@ dns_message_buildopt(dns_message_t *message, dns_rdataset_t **rdatasetp, | ||
| 141 | dns_message_puttemprdatalist(message, &rdatalist); | ||
| 142 | return (result); | ||
| 143 | } | ||
| 144 | + | ||
| 145 | +void | ||
| 146 | +dns_message_setclass(dns_message_t *msg, dns_rdataclass_t rdclass) { | ||
| 147 | + | ||
| 148 | + REQUIRE(DNS_MESSAGE_VALID(msg)); | ||
| 149 | + REQUIRE(msg->from_to_wire == DNS_MESSAGE_INTENTPARSE); | ||
| 150 | + REQUIRE(msg->state == DNS_SECTION_ANY); | ||
| 151 | + REQUIRE(msg->rdclass_set == 0); | ||
| 152 | + | ||
| 153 | + msg->rdclass = rdclass; | ||
| 154 | + msg->rdclass_set = 1; | ||
| 155 | +} | ||
| 156 | diff --git a/lib/dns/resolver.c b/lib/dns/resolver.c | ||
| 157 | index aa23b11..d220986 100644 | ||
| 158 | --- a/lib/dns/resolver.c | ||
| 159 | +++ b/lib/dns/resolver.c | ||
| 160 | @@ -6964,6 +6964,8 @@ resquery_response(isc_task_t *task, isc_event_t *event) { | ||
| 161 | goto done; | ||
| 162 | } | ||
| 163 | |||
| 164 | + dns_message_setclass(message, fctx->res->rdclass); | ||
| 165 | + | ||
| 166 | result = dns_message_parse(message, &devent->buffer, 0); | ||
| 167 | if (result != ISC_R_SUCCESS) { | ||
| 168 | switch (result) { | ||
| 169 | @@ -7036,6 +7038,12 @@ resquery_response(isc_task_t *task, isc_event_t *event) { | ||
| 170 | */ | ||
| 171 | log_packet(message, ISC_LOG_DEBUG(10), fctx->res->mctx); | ||
| 172 | |||
| 173 | + if (message->rdclass != fctx->res->rdclass) { | ||
| 174 | + resend = ISC_TRUE; | ||
| 175 | + FCTXTRACE("bad class"); | ||
| 176 | + goto done; | ||
| 177 | + } | ||
| 178 | + | ||
| 179 | /* | ||
| 180 | * Process receive opt record. | ||
| 181 | */ | ||
| 182 | diff --git a/lib/dns/xfrin.c b/lib/dns/xfrin.c | ||
| 183 | index 9ad8960..938373a 100644 | ||
| 184 | --- a/lib/dns/xfrin.c | ||
| 185 | +++ b/lib/dns/xfrin.c | ||
| 186 | @@ -1241,6 +1241,8 @@ xfrin_recv_done(isc_task_t *task, isc_event_t *ev) { | ||
| 187 | msg->tsigctx = xfr->tsigctx; | ||
| 188 | xfr->tsigctx = NULL; | ||
| 189 | |||
| 190 | + dns_message_setclass(msg, xfr->rdclass); | ||
| 191 | + | ||
| 192 | if (xfr->nmsg > 0) | ||
| 193 | msg->tcp_continuation = 1; | ||
| 194 | |||
diff --git a/meta/recipes-connectivity/bind/bind_9.9.5.bb b/meta/recipes-connectivity/bind/bind_9.9.5.bb index ee940112f7..6e4878d06b 100644 --- a/meta/recipes-connectivity/bind/bind_9.9.5.bb +++ b/meta/recipes-connectivity/bind/bind_9.9.5.bb | |||
| @@ -22,6 +22,7 @@ SRC_URI = "ftp://ftp.isc.org/isc/bind9/${PV}/${BPN}-${PV}.tar.gz \ | |||
| 22 | file://CVE-2015-1349.patch \ | 22 | file://CVE-2015-1349.patch \ |
| 23 | file://CVE-2015-4620.patch \ | 23 | file://CVE-2015-4620.patch \ |
| 24 | file://CVE-2015-5722.patch \ | 24 | file://CVE-2015-5722.patch \ |
| 25 | file://CVE-2015-8000.patch \ | ||
| 25 | " | 26 | " |
| 26 | 27 | ||
| 27 | SRC_URI[md5sum] = "e676c65cad5234617ee22f48e328c24e" | 28 | SRC_URI[md5sum] = "e676c65cad5234617ee22f48e328c24e" |
