1a4de8b956
It might not fix all issues, but was detected by upstream using automated tool. Should not break anything new, but might fix issue triggered usually on ppc64le platform.
111 lines
3.3 KiB
Diff
111 lines
3.3 KiB
Diff
From 9c1f74400c04267dea4f1bd7f62de8ba5e8d2b0e Mon Sep 17 00:00:00 2001
|
|
From: Mark Andrews <marka@isc.org>
|
|
Date: Thu, 28 Nov 2019 10:24:12 +1100
|
|
Subject: [PATCH 4/4] rdataset_setownercase and rdataset_getownercase need to
|
|
obtain a node lock
|
|
|
|
(cherry picked from commit 637b2c4e517b466900a8c00b52f7a15727e12ae9)
|
|
(cherry picked from commit 1c61f129c3b12071723a2154d33f74628bf80998)
|
|
---
|
|
lib/dns/rbtdb.c | 35 ++++++++++++++++++++++++++++-------
|
|
1 file changed, 28 insertions(+), 7 deletions(-)
|
|
|
|
diff --git a/lib/dns/rbtdb.c b/lib/dns/rbtdb.c
|
|
index d3bb8d7fe7..199ff08011 100644
|
|
--- a/lib/dns/rbtdb.c
|
|
+++ b/lib/dns/rbtdb.c
|
|
@@ -10109,11 +10109,18 @@ setownercase(rdatasetheader_t *header, const dns_name_t *name) {
|
|
|
|
static void
|
|
rdataset_setownercase(dns_rdataset_t *rdataset, const dns_name_t *name) {
|
|
+ dns_rbtdb_t *rbtdb = rdataset->private1;
|
|
+ dns_rbtnode_t *rbtnode = rdataset->private2;
|
|
unsigned char *raw = rdataset->private3; /* RDATASLAB */
|
|
rdatasetheader_t *header;
|
|
|
|
header = (struct rdatasetheader *)(raw - sizeof(*header));
|
|
+
|
|
+ NODE_LOCK(&rbtdb->node_locks[rbtnode->locknum].lock,
|
|
+ isc_rwlocktype_write);
|
|
setownercase(header, name);
|
|
+ NODE_UNLOCK(&rbtdb->node_locks[rbtnode->locknum].lock,
|
|
+ isc_rwlocktype_write);
|
|
}
|
|
|
|
static const unsigned char charmask[] = {
|
|
@@ -10188,6 +10195,8 @@ static unsigned char maptolower[] = {
|
|
|
|
static void
|
|
rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
+ dns_rbtdb_t *rbtdb = rdataset->private1;
|
|
+ dns_rbtnode_t *rbtnode = rdataset->private2;
|
|
const unsigned char *raw = rdataset->private3; /* RDATASLAB */
|
|
const rdatasetheader_t *header;
|
|
unsigned int i, j;
|
|
@@ -10196,8 +10205,12 @@ rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
|
|
header = (const struct rdatasetheader *)(raw - sizeof(*header));
|
|
|
|
- if (!CASESET(header))
|
|
- return;
|
|
+ NODE_LOCK(&rbtdb->node_locks[rbtnode->locknum].lock,
|
|
+ isc_rwlocktype_read);
|
|
+
|
|
+ if (!CASESET(header)) {
|
|
+ goto unlock;
|
|
+ }
|
|
|
|
#if 0
|
|
/*
|
|
@@ -10210,10 +10223,13 @@ rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
*/
|
|
if (name->ndata[i] >= 0x61 && name->ndata[i] <= 0x7a &&
|
|
(header->upper[i/8] & (1 << (i%8))) != 0)
|
|
+ {
|
|
name->ndata[i] &= ~0x20; /* clear the lower case bit */
|
|
- else if (name->ndata[i] >= 0x41 && name->ndata[i] <= 0x5a &&
|
|
- (header->upper[i/8] & (1 << (i%8))) == 0)
|
|
+ } else if (name->ndata[i] >= 0x41 && name->ndata[i] <= 0x5a &&
|
|
+ (header->upper[i/8] & (1 << (i%8))) == 0)
|
|
+ {
|
|
name->ndata[i] |= 0x20; /* set the lower case bit */
|
|
+ }
|
|
}
|
|
#else
|
|
if (ISC_LIKELY(CASEFULLYLOWER(header))) {
|
|
@@ -10236,7 +10252,7 @@ rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
c = *bp;
|
|
*bp++ = maptolower[c];
|
|
}
|
|
- return;
|
|
+ goto unlock;
|
|
}
|
|
|
|
i = 0;
|
|
@@ -10257,8 +10273,9 @@ rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
}
|
|
}
|
|
|
|
- if (ISC_UNLIKELY(i == name->length))
|
|
- return;
|
|
+ if (ISC_UNLIKELY(i == name->length)) {
|
|
+ goto unlock;
|
|
+ }
|
|
|
|
bits = ~(header->upper[j]);
|
|
|
|
@@ -10272,6 +10289,10 @@ rdataset_getownercase(const dns_rdataset_t *rdataset, dns_name_t *name) {
|
|
bits >>= 1;
|
|
}
|
|
#endif
|
|
+
|
|
+ unlock:
|
|
+ NODE_UNLOCK(&rbtdb->node_locks[rbtnode->locknum].lock,
|
|
+ isc_rwlocktype_read);
|
|
}
|
|
|
|
/*%
|
|
--
|
|
2.21.0
|
|
|