From cd64d6c89ad0e987cf82637fd4d8c417f1f7d22c Mon Sep 17 00:00:00 2001 From: John Brownlee Date: Wed, 30 May 2018 15:32:49 -0700 Subject: [PATCH 01/21] Update documentation for 5.2.2 release. --- documentation/sphinx/source/downloads.rst | 24 +++++++++---------- documentation/sphinx/source/release-notes.rst | 9 +++++++ packaging/msi/FDBInstaller.wxs | 2 +- 3 files changed, 22 insertions(+), 13 deletions(-) diff --git a/documentation/sphinx/source/downloads.rst b/documentation/sphinx/source/downloads.rst index 38b23a1ea6..b2afdf4528 100644 --- a/documentation/sphinx/source/downloads.rst +++ b/documentation/sphinx/source/downloads.rst @@ -10,38 +10,38 @@ macOS The macOS installation package is supported on macOS 10.7+. It includes the client and (optionally) the server. -* `FoundationDB-5.2.1.pkg `_ +* `FoundationDB-5.2.2.pkg `_ Ubuntu ------ The Ubuntu packages are supported on 64-bit Ubuntu 12.04+, but beware of the Linux kernel bug in Ubuntu 12.x. -* `foundationdb-clients-5.2.1-1_amd64.deb `_ -* `foundationdb-server-5.2.1-1_amd64.deb `_ (depends on the clients package) +* `foundationdb-clients-5.2.2-1_amd64.deb `_ +* `foundationdb-server-5.2.2-1_amd64.deb `_ (depends on the clients package) RHEL/CentOS EL6 --------------- The RHEL/CentOS EL6 packages are supported on 64-bit RHEL/CentOS 6.x. -* `foundationdb-clients-5.2.1-1.el6.x86_64.rpm `_ -* `foundationdb-server-5.2.1-1.el6.x86_64.rpm `_ (depends on the clients package) +* `foundationdb-clients-5.2.2-1.el6.x86_64.rpm `_ +* `foundationdb-server-5.2.2-1.el6.x86_64.rpm `_ (depends on the clients package) RHEL/CentOS EL7 --------------- The RHEL/CentOS EL7 packages are supported on 64-bit RHEL/CentOS 7.x. -* `foundationdb-clients-5.2.1-1.el7.x86_64.rpm `_ -* `foundationdb-server-5.2.1-1.el7.x86_64.rpm `_ (depends on the clients package) +* `foundationdb-clients-5.2.2-1.el7.x86_64.rpm `_ +* `foundationdb-server-5.2.2-1.el7.x86_64.rpm `_ (depends on the clients package) Windows ------- The Windows installer is supported on 64-bit Windows XP and later. It includes the client and (optionally) the server. -* `foundationdb-5.2.1-x64.msi `_ +* `foundationdb-5.2.2-x64.msi `_ API Language Bindings ===================== @@ -58,18 +58,18 @@ On macOS and Windows, the FoundationDB Python API bindings are installed as part If you need to use the FoundationDB Python API from other Python installations or paths, download the Python package: -* `foundationdb-5.2.1.tar.gz `_ +* `foundationdb-5.2.2.tar.gz `_ Ruby 1.9.3/2.0.0+ ----------------- -* `fdb-5.2.1.gem `_ +* `fdb-5.2.2.gem `_ Java 8+ ------- -* `fdb-java-5.2.1.jar `_ -* `fdb-java-5.2.1-javadoc.jar `_ +* `fdb-java-5.2.2.jar `_ +* `fdb-java-5.2.2-javadoc.jar `_ Go 1.1+ ------- diff --git a/documentation/sphinx/source/release-notes.rst b/documentation/sphinx/source/release-notes.rst index 1ad4a2450a..910d2bd2c4 100644 --- a/documentation/sphinx/source/release-notes.rst +++ b/documentation/sphinx/source/release-notes.rst @@ -2,6 +2,15 @@ Release Notes ############# +5.2.2 +===== + +Fixes +----- + +* Build would fail on recent versions of Clang +* Clusters running with TLS plugin would fail to start when client and server certificates used different validation rules + 5.2.1 ===== diff --git a/packaging/msi/FDBInstaller.wxs b/packaging/msi/FDBInstaller.wxs index 384fe90df1..2bc67c8ac8 100644 --- a/packaging/msi/FDBInstaller.wxs +++ b/packaging/msi/FDBInstaller.wxs @@ -32,7 +32,7 @@ Date: Wed, 30 May 2018 16:22:42 -0700 Subject: [PATCH 02/21] Fix docs wording --- .../sphinx/source/old-release-notes/release-notes-450.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/documentation/sphinx/source/old-release-notes/release-notes-450.rst b/documentation/sphinx/source/old-release-notes/release-notes-450.rst index 0b4e594f48..439777f620 100644 --- a/documentation/sphinx/source/old-release-notes/release-notes-450.rst +++ b/documentation/sphinx/source/old-release-notes/release-notes-450.rst @@ -83,7 +83,7 @@ Fixes * A multi-version API external client that was a duplicate could cause a crash at client shutdown. * A multi-version API external client that failed to load would cause a crash at client shutdown. * Status could report an incorrect database size in rare scenarios. -* Data distribution would stopped working (both exclude and new recruitment) if a call to commit on the storage server could hang indefinitely. +* Data distribution would stop working (both exclude and new recruitment) if a call to commit on the storage server could hang indefinitely. * ``fdbcli`` would quit on some commands that were not errors or continue after some real errors when run with ``--exec``. * Trace files generated by clients using the multi-version API could have name collisions. From 070366ca7076fa238ba84158de69637d207416b1 Mon Sep 17 00:00:00 2001 From: Balachandar Namasivayam Date: Wed, 30 May 2018 16:48:04 -0700 Subject: [PATCH 03/21] Optimize client and server connection times to cluster controller, especially in multi DC configurations. A majority(quorum) answer from co-ordinators was required to connect to cluster controller. Now a cluster controller is optimistically selected to connect even if there is no quorum. --- fdbclient/MonitorLeader.actor.cpp | 73 ++++++++++++++++-------------- fdbserver/LeaderElection.actor.cpp | 32 ++++++------- 2 files changed, 55 insertions(+), 50 deletions(-) diff --git a/fdbclient/MonitorLeader.actor.cpp b/fdbclient/MonitorLeader.actor.cpp index e21abb5704..ac95e0c915 100644 --- a/fdbclient/MonitorLeader.actor.cpp +++ b/fdbclient/MonitorLeader.actor.cpp @@ -325,45 +325,50 @@ ACTOR Future monitorNominee( Key key, ClientLeaderRegInterface coord, Asyn } // Also used in fdbserver/LeaderElection.actor.cpp! -Optional getLeader( vector> nominees ) { +// bool represents if the LeaderInfo is a majority answer or not. +Optional> getLeader( vector> nominees ) { // If any coordinator says that the quorum is forwarded, then it is for(int i=0; i(nominees[i].get(), true); if(!nominees.size()) - return Optional(); - // There is a leader if a majority of the nominees are the same. - // If there is a majority, the median item is in it. + return Optional>(); + + std::sort(nominees.begin(), nominees.end(), + [](const Optional& l, const Optional& r) { + if (!l.present()) + return true; + if (!r.present()) + return false; + return UID(l.get().changeID.first() & l.get().mask, l.get().changeID.second()) < UID(r.get().changeID.first() & r.get().mask, r.get().changeID.second()); + }); + int bestCount = 0; + Optional bestNominee; Optional currentNominee; - for(int i=0; i 0) { - bestCount--; - } else { - bestCount = 1; - currentNominee = nominees[i]; + int curCount = 0; + for (int i = 0; i < nominees.size(); i++) { + if (nominees[i].present()) { + if (currentNominee.present() && currentNominee.get().equalInternalId(nominees[i].get())) { + curCount++; + } + else { + currentNominee = nominees[i]; + curCount = 1; + } + if (curCount > bestCount) { + bestNominee = currentNominee; + bestCount = curCount; } - } else { - bestCount++; } } - if(!currentNominee.present()) - return Optional(); - - int amountBest = 0; - for(int i=0; i= nominees.size()/2 + 1) { - return currentNominee; - } - return Optional(); + if (bestCount >= nominees.size() / 2 + 1) + return std::pair(bestNominee.get(), true); + if (bestNominee.present()) + return std::pair(bestNominee.get(), false); + return Optional>(); } struct MonitorLeaderInfo { @@ -389,12 +394,12 @@ ACTOR Future monitorLeaderOneGeneration( Reference leader = getLeader(nominees); - TraceEvent("MonitorLeaderChange").detail("NewLeader", leader.present() ? leader.get().changeID : UID(1,1)); + Optional> leader = getLeader(nominees); + TraceEvent("MonitorLeaderChange").detail("NewLeader", leader.present() ? leader.get().first.changeID : UID(1,1)); if (leader.present()) { - if( leader.get().forward ) { - TraceEvent("MonitorLeaderForwarding").detail("NewConnStr", leader.get().serializedInfo.toString()).detail("OldConnStr", info.intermediateConnFile->getConnectionString().toString()); - info.intermediateConnFile = Reference(new ClusterConnectionFile(connFile->getFilename(), ClusterConnectionString(leader.get().serializedInfo.toString()))); + if( leader.get().first.forward ) { + TraceEvent("MonitorLeaderForwarding").detail("NewConnStr", leader.get().first.serializedInfo.toString()).detail("OldConnStr", info.intermediateConnFile->getConnectionString().toString()); + info.intermediateConnFile = Reference(new ClusterConnectionFile(connFile->getFilename(), ClusterConnectionString(leader.get().first.serializedInfo.toString()))); return info; } if(connFile != info.intermediateConnFile) { @@ -410,7 +415,7 @@ ACTOR Future monitorLeaderOneGeneration( ReferencenotifyConnected(); - outSerializedLeaderInfo->set( leader.get().serializedInfo ); + outSerializedLeaderInfo->set( leader.get().first.serializedInfo ); } Void _ = wait( nomineeChange.onTrigger() || allActors ); } diff --git a/fdbserver/LeaderElection.actor.cpp b/fdbserver/LeaderElection.actor.cpp index c68d64b6e1..1a2a3f1d83 100644 --- a/fdbserver/LeaderElection.actor.cpp +++ b/fdbserver/LeaderElection.actor.cpp @@ -25,7 +25,7 @@ #include "fdbserver/CoordinationInterface.h" #include "fdbclient/MonitorLeader.h" -extern Optional getLeader( vector> nominees ); +Optional> getLeader( vector> nominees ); ACTOR Future submitCandidacy( Key key, LeaderElectionRegInterface coord, LeaderInfo myInfo, UID prevChangeID, Reference>>> nominees, int index ) { loop { @@ -106,44 +106,44 @@ ACTOR Future tryBecomeLeaderInternal( ServerCoordinators coordinators, Val candidacies = waitForAll(cand); loop { - state Optional leader = getLeader( nominees->get() ); - if( leader.present() && leader.get().forward ) { + state Optional> leader = getLeader( nominees->get() ); + if( leader.present() && leader.get().first.forward ) { // TODO: Check if it is fine to not check bool // These coordinators are forwarded to another set. But before we change our own cluster file, we need to make // sure that a majority of coordinators know that. // SOMEDAY: Wait briefly to see if other coordinators will tell us they already know, to save communication? - Void _ = wait( changeLeaderCoordinators( coordinators, leader.get().serializedInfo ) ); + Void _ = wait( changeLeaderCoordinators( coordinators, leader.get().first.serializedInfo ) ); if(!hasConnected) { TraceEvent(SevWarnAlways, "IncorrectClusterFileContentsAtConnection").detail("Filename", coordinators.ccf->getFilename()) .detail("ConnectionStringFromFile", coordinators.ccf->getConnectionString().toString()) - .detail("CurrentConnectionString", leader.get().serializedInfo.toString()); + .detail("CurrentConnectionString", leader.get().first.serializedInfo.toString()); } - coordinators.ccf->setConnectionString( ClusterConnectionString( leader.get().serializedInfo.toString() ) ); + coordinators.ccf->setConnectionString( ClusterConnectionString( leader.get().first.serializedInfo.toString() ) ); TraceEvent("LeaderForwarding").detail("ConnStr", coordinators.ccf->getConnectionString().toString()); throw coordinators_changed(); } - if (leader.present()) { + if (leader.present() && leader.get().second) { hasConnected = true; coordinators.ccf->notifyConnected(); } - if (leader.present() && leader.get().changeID == myInfo.changeID) { + if (leader.present() && leader.get().second && leader.get().first.changeID == myInfo.changeID) { TraceEvent("BecomingLeader", myInfo.changeID); - ASSERT( leader.get().serializedInfo == proposedSerializedInterface ); - outSerializedLeader->set( leader.get().serializedInfo ); + ASSERT( leader.get().first.serializedInfo == proposedSerializedInterface ); + outSerializedLeader->set( leader.get().first.serializedInfo ); iAmLeader = true; break; } - if (leader.present()) { - TraceEvent("LeaderChanged", myInfo.changeID).detail("ToID", leader.get().changeID); - if (leader.get().serializedInfo != proposedSerializedInterface) // We never set outSerializedLeader to our own interface unless we are ready to become leader! - outSerializedLeader->set( leader.get().serializedInfo ); + if (leader.present() && leader.get().second) { + TraceEvent("LeaderChanged", myInfo.changeID).detail("ToID", leader.get().first.changeID); + if (leader.get().first.serializedInfo != proposedSerializedInterface) // We never set outSerializedLeader to our own interface unless we are ready to become leader! + outSerializedLeader->set( leader.get().first.serializedInfo ); } // If more than 2*SERVER_KNOBS->POLLING_FREQUENCY elapses while we are nominated by some coordinator but there is no leader, // we might be breaking the leader election process for someone with better communications but lower ID, so change IDs. - if (!leader.present() && std::count( nominees->get().begin(), nominees->get().end(), myInfo )) { + if ((!leader.present() || !leader.get().second) && std::count( nominees->get().begin(), nominees->get().end(), myInfo )) { if (!badCandidateTimeout.isValid()) badCandidateTimeout = delay( SERVER_KNOBS->POLLING_FREQUENCY*2, TaskCoordinationReply ); } else @@ -211,4 +211,4 @@ ACTOR Future tryBecomeLeaderInternal( ServerCoordinators coordinators, Val if (SERVER_KNOBS->BUGGIFY_ALL_COORDINATION || BUGGIFY) Void _ = wait( delay( SERVER_KNOBS->BUGGIFIED_EVENTUAL_CONSISTENCY * g_random->random01() ) ); return Void(); // We are no longer leader -} \ No newline at end of file +} From 10bcba4dbaf7988f1c80fe09cb19c596d86dd65a Mon Sep 17 00:00:00 2001 From: John Brownlee Date: Thu, 31 May 2018 11:23:09 -0700 Subject: [PATCH 04/21] Bump versions.target --- packaging/msi/FDBInstaller.wxs | 2 +- versions.target | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/packaging/msi/FDBInstaller.wxs b/packaging/msi/FDBInstaller.wxs index 2bc67c8ac8..9be55b35bf 100644 --- a/packaging/msi/FDBInstaller.wxs +++ b/packaging/msi/FDBInstaller.wxs @@ -32,7 +32,7 @@ - 5.2.2 + 5.2.3 5.2 From 9f55ccd4a5433b33a6645bcb433c7c19e03799d8 Mon Sep 17 00:00:00 2001 From: Balachandar Namasivayam Date: Thu, 31 May 2018 15:32:47 -0700 Subject: [PATCH 05/21] Remove extraneous comments. --- fdbserver/LeaderElection.actor.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fdbserver/LeaderElection.actor.cpp b/fdbserver/LeaderElection.actor.cpp index 1a2a3f1d83..7ccba12b52 100644 --- a/fdbserver/LeaderElection.actor.cpp +++ b/fdbserver/LeaderElection.actor.cpp @@ -107,7 +107,7 @@ ACTOR Future tryBecomeLeaderInternal( ServerCoordinators coordinators, Val loop { state Optional> leader = getLeader( nominees->get() ); - if( leader.present() && leader.get().first.forward ) { // TODO: Check if it is fine to not check bool + if( leader.present() && leader.get().first.forward ) { // These coordinators are forwarded to another set. But before we change our own cluster file, we need to make // sure that a majority of coordinators know that. // SOMEDAY: Wait briefly to see if other coordinators will tell us they already know, to save communication? From 3ea5fc72f0ab74b1deccd3fd00bf9ab27286d9f7 Mon Sep 17 00:00:00 2001 From: "A.J. Beamon" Date: Thu, 31 May 2018 15:34:17 -0700 Subject: [PATCH 06/21] Rename trace file logGroup attribute to LogGroup --- documentation/sphinx/source/release-notes.rst | 1 + fdbclient/vexillographer/fdb.options | 4 ++-- flow/Trace.cpp | 8 ++++---- 3 files changed, 7 insertions(+), 6 deletions(-) diff --git a/documentation/sphinx/source/release-notes.rst b/documentation/sphinx/source/release-notes.rst index c56f079c92..4ba2fb01c3 100644 --- a/documentation/sphinx/source/release-notes.rst +++ b/documentation/sphinx/source/release-notes.rst @@ -29,6 +29,7 @@ Other Changes ------------- * Does not support upgrades from any version older than 5.0. +* Renamed the trace log attribute ``logGroup`` to ``LogGroup``. Earlier release notes --------------------- diff --git a/fdbclient/vexillographer/fdb.options b/fdbclient/vexillographer/fdb.options index e443cee944..33ee913ba9 100644 --- a/fdbclient/vexillographer/fdb.options +++ b/fdbclient/vexillographer/fdb.options @@ -46,8 +46,8 @@ description is not currently required but encouraged. paramType="Int" paramDescription="max total size of trace files" description="Sets the maximum size of all the trace output files put together. This value should be in the range ``[0, INT64_MAX]``. If the value is set to 0, there is no limit on the total size of the files. The default is a maximum size of 104,857,600 bytes. If the default roll size is used, this means that a maximum of 10 trace files will be written at a time."/>