|
|
95ea96 |
From 72517c7b316f7cba93a3b2cdc6e2c69dad63a8b1 Mon Sep 17 00:00:00 2001
|
|
|
2737e7 |
From: Christian Heimes <cheimes@redhat.com>
|
|
|
2737e7 |
Date: Fri, 6 Jul 2018 21:47:32 +0200
|
|
|
2737e7 |
Subject: [PATCH] Fix race condition in get_locations_records()
|
|
|
2737e7 |
|
|
|
2737e7 |
The method IPASystemRecords.get_locations_records() has a race condition.
|
|
|
2737e7 |
The IPASystemRecords object creates a mapping of server names to server
|
|
|
2737e7 |
data. get_locations_records() uses server_find() again to get a list of
|
|
|
2737e7 |
servers, but then operates on the cached dict of server names.
|
|
|
2737e7 |
|
|
|
2737e7 |
In parallel replication case, the second server_find() call in
|
|
|
2737e7 |
get_locations_records() can return additional servers. Since the rest of
|
|
|
2737e7 |
the code operates on the cached data, the method then fails with a KeyError.
|
|
|
2737e7 |
|
|
|
2737e7 |
server_data is now an OrderedDict to keep same sorting as with
|
|
|
2737e7 |
server_find().
|
|
|
2737e7 |
|
|
|
2737e7 |
Fixes: https://pagure.io/freeipa/issue/7566
|
|
|
2737e7 |
Signed-off-by: Christian Heimes <cheimes@redhat.com>
|
|
|
2737e7 |
Reviewed-By: Tibor Dudlak <tdudlak@redhat.com>
|
|
|
2737e7 |
---
|
|
|
2737e7 |
ipaserver/dns_data_management.py | 14 +++++---------
|
|
|
2737e7 |
1 file changed, 5 insertions(+), 9 deletions(-)
|
|
|
2737e7 |
|
|
|
2737e7 |
diff --git a/ipaserver/dns_data_management.py b/ipaserver/dns_data_management.py
|
|
|
95ea96 |
index 673397ef2b2252f431eec1f3e1f71dc45ff87511..90c4d8536478599e5a35462c7f00ea4c958ff63a 100644
|
|
|
2737e7 |
--- a/ipaserver/dns_data_management.py
|
|
|
2737e7 |
+++ b/ipaserver/dns_data_management.py
|
|
|
95ea96 |
@@ -8,7 +8,7 @@ import logging
|
|
|
2737e7 |
|
|
|
2737e7 |
import six
|
|
|
2737e7 |
|
|
|
2737e7 |
-from collections import defaultdict
|
|
|
2737e7 |
+from collections import defaultdict, OrderedDict
|
|
|
2737e7 |
from dns import (
|
|
|
2737e7 |
rdata,
|
|
|
2737e7 |
rdataclass,
|
|
|
95ea96 |
@@ -71,7 +71,7 @@ class IPASystemRecords(object):
|
|
|
2737e7 |
def __init__(self, api_instance, all_servers=False):
|
|
|
2737e7 |
self.api_instance = api_instance
|
|
|
2737e7 |
self.domain_abs = DNSName(self.api_instance.env.domain).make_absolute()
|
|
|
2737e7 |
- self.servers_data = {}
|
|
|
2737e7 |
+ self.servers_data = OrderedDict()
|
|
|
2737e7 |
self.__init_data(all_servers=all_servers)
|
|
|
2737e7 |
|
|
|
2737e7 |
def reload_data(self):
|
|
|
95ea96 |
@@ -93,7 +93,7 @@ class IPASystemRecords(object):
|
|
|
2737e7 |
return location + DNSName('_locations') + self.domain_abs
|
|
|
2737e7 |
|
|
|
2737e7 |
def __init_data(self, all_servers=False):
|
|
|
2737e7 |
- self.servers_data = {}
|
|
|
2737e7 |
+ self.servers_data.clear()
|
|
|
2737e7 |
|
|
|
2737e7 |
kwargs = dict(no_members=False)
|
|
|
2737e7 |
if not all_servers:
|
|
|
95ea96 |
@@ -328,7 +328,7 @@ class IPASystemRecords(object):
|
|
|
2737e7 |
|
|
|
2737e7 |
zone_obj = zone.Zone(self.domain_abs, relativize=False)
|
|
|
2737e7 |
if servers is None:
|
|
|
2737e7 |
- servers = self.servers_data.keys()
|
|
|
2737e7 |
+ servers = list(self.servers_data)
|
|
|
2737e7 |
|
|
|
2737e7 |
for server in servers:
|
|
|
2737e7 |
self._add_base_dns_records_for_server(zone_obj, server,
|
|
|
95ea96 |
@@ -351,11 +351,7 @@ class IPASystemRecords(object):
|
|
|
2737e7 |
"""
|
|
|
2737e7 |
zone_obj = zone.Zone(self.domain_abs, relativize=False)
|
|
|
2737e7 |
if servers is None:
|
|
|
2737e7 |
- servers_result = self.api_instance.Command.server_find(
|
|
|
2737e7 |
- pkey_only=True,
|
|
|
2737e7 |
- servrole=u"IPA master", # only fully installed masters
|
|
|
2737e7 |
- )['result']
|
|
|
2737e7 |
- servers = [s['cn'][0] for s in servers_result]
|
|
|
2737e7 |
+ servers = list(self.servers_data)
|
|
|
2737e7 |
|
|
|
2737e7 |
locations_result = self.api_instance.Command.location_find()['result']
|
|
|
2737e7 |
locations = [l['idnsname'][0] for l in locations_result]
|
|
|
2737e7 |
--
|
|
|
2737e7 |
2.17.1
|
|
|
2737e7 |
|