summaryrefslogtreecommitdiff
path: root/src/third_party/s2
diff options
context:
space:
mode:
authorBilly Donahue <billy.donahue@mongodb.com>2019-09-04 13:44:43 +0000
committerevergreen <evergreen@mongodb.com>2019-09-04 13:44:43 +0000
commite58bc0f552112f5c1c16f8092b771f7e562316fb (patch)
tree2c267cf35b71aec89fe8df5ac0426afeed55be37 /src/third_party/s2
parent0031fa41177db46789e411895a5bcd33b2847ed5 (diff)
downloadmongo-e58bc0f552112f5c1c16f8092b771f7e562316fb.tar.gz
SERVER-41648 remove mongo headers from s2 files.
Diffstat (limited to 'src/third_party/s2')
-rwxr-xr-xsrc/third_party/s2/base/SConscript5
-rwxr-xr-xsrc/third_party/s2/base/logging.cc35
-rwxr-xr-xsrc/third_party/s2/base/logging.h99
-rw-r--r--src/third_party/s2/base/logging_mongo.cc138
-rw-r--r--src/third_party/s2/s2cellid.cc28
-rw-r--r--src/third_party/s2/s2loop.cc16
-rw-r--r--src/third_party/s2/s2polygon.cc11
-rw-r--r--src/third_party/s2/s2polyline.cc7
-rw-r--r--src/third_party/s2/s2regioncoverer.cc20
9 files changed, 249 insertions, 110 deletions
diff --git a/src/third_party/s2/base/SConscript b/src/third_party/s2/base/SConscript
index 217cc864236..8e437001e0e 100755
--- a/src/third_party/s2/base/SConscript
+++ b/src/third_party/s2/base/SConscript
@@ -11,10 +11,11 @@ env.Library(
[
"int128.cc",
"logging.cc",
+ "logging_mongo.cc",
"stringprintf.cc",
"strtoint.cc",
],
- LIBDEPS=[
- '$BUILD_DIR/mongo/base',
+ LIBDEPS_PRIVATE=[
+ "$BUILD_DIR/mongo/base",
],
)
diff --git a/src/third_party/s2/base/logging.cc b/src/third_party/s2/base/logging.cc
index 238afb0eb6d..58d9cab0471 100755
--- a/src/third_party/s2/base/logging.cc
+++ b/src/third_party/s2/base/logging.cc
@@ -17,32 +17,19 @@
#include <utility>
-#include "mongo/util/assert_util.h"
-#include "mongo/util/log.h"
-#include "mongo/util/str.h"
+namespace s2_env {
-using ::mongo::logger::LogstreamBuilder;
+LoggingEnv::~LoggingEnv() = default;
-LogMessageBase::LogMessageBase(LogstreamBuilder builder, const char* file, int line) :
- _lsb(std::move(builder)) {
- _lsb.setBaseMessage(::mongo::str::stream() << file << ':' << line << ": ");
-}
+LogMessageSink::~LogMessageSink() = default;
-LogMessageBase::LogMessageBase(LogstreamBuilder builder) : _lsb(std::move(builder)) { }
+LogMessage::LogMessage(int verbosity)
+ : _sink(globalLoggingEnv().makeSink(verbosity)) { }
+LogMessage::LogMessage(Severity severity)
+ : _sink(globalLoggingEnv().makeSink(severity)) { }
+LogMessage::LogMessage(Severity severity, const char* file, int line)
+ : _sink(globalLoggingEnv().makeSink(severity, file, line)) { }
-LogMessageInfo::LogMessageInfo() : LogMessageBase(mongo::log()) { }
+LogMessage::~LogMessage() = default;
-LogMessageWarning::LogMessageWarning(const char* file, int line) :
- LogMessageBase(mongo::warning(), file, line) { }
-
-LogMessageFatal::LogMessageFatal(const char* file, int line) :
- LogMessageBase(mongo::severe(), file, line) { }
-
-#pragma warning(push)
-// C4722: 'LogMessageFatal::~LogMessageFatal': destructor never returns, potential memory leak
-#pragma warning(disable : 4722)
-LogMessageFatal::~LogMessageFatal() {
- _lsb.~LogstreamBuilder();
- fassertFailed(40048);
-}
-#pragma warning(pop)
+} // namespace s2_env
diff --git a/src/third_party/s2/base/logging.h b/src/third_party/s2/base/logging.h
index 4f40312141b..8dd7bdf6765 100755
--- a/src/third_party/s2/base/logging.h
+++ b/src/third_party/s2/base/logging.h
@@ -14,17 +14,14 @@
#ifndef BASE_LOGGING_H
#define BASE_LOGGING_H
-#include <iosfwd>
-
-#include "mongo/logger/log_severity.h"
-#include "mongo/logger/logger.h"
-#include "mongo/logger/logstream_builder.h"
-#include "mongo/util/concurrency/thread_name.h"
+#include <iostream>
+#include <sstream>
+#include <memory>
#include "macros.h"
// Always-on checking
-#define CHECK(x) if(x){}else LogMessageFatal(__FILE__, __LINE__).stream() << "Check failed: " #x
+#define CHECK(x) if(x){}else FATAL << "Check failed: " #x
#define CHECK_LT(x, y) CHECK((x) < (y))
#define CHECK_GT(x, y) CHECK((x) > (y))
#define CHECK_LE(x, y) CHECK((x) <= (y))
@@ -43,7 +40,7 @@
#define DCHECK_GE(val1, val2) CHECK_GE(val1, val2)
#define DCHECK_GT(val1, val2) CHECK_GT(val1, val2)
#else
-#define DCHECK(x) if(x){}else LogMessageWarning(__FILE__, __LINE__).stream() << "Check failed: " #x
+#define DCHECK(x) if(x){}else WARN << "Check failed: " #x
#define DCHECK_LT(x, y) DCHECK((x) < (y))
#define DCHECK_GT(x, y) DCHECK((x) > (y))
#define DCHECK_LE(x, y) DCHECK((x) <= (y))
@@ -53,56 +50,76 @@
#endif
#include "base/port.h"
-#define INFO LogMessageInfo().stream()
-#define WARN LogMessageWarning(__FILE__, __LINE__).stream()
-#define FATAL LogMessageFatal(__FILE__, __LINE__).stream()
-#define DFATAL LogMessageFatal(__FILE__, __LINE__).stream()
+#define INFO s2_env::LogMessage(s2_env::LogMessage::Severity::kInfo).stream()
+#define WARN s2_env::LogMessage(s2_env::LogMessage::Severity::kWarning, __FILE__, __LINE__).stream()
+#define FATAL s2_env::LogMessage(s2_env::LogMessage::Severity::kFatal, __FILE__, __LINE__).stream()
+#define DFATAL s2_env::LogMessage(s2_env::LogMessage::Severity::kFatal, __FILE__, __LINE__).stream()
-// VLOG messages will be logged at debug level 5 with the S2 log component.
#define S2LOG(x) x
-// Expansion of MONGO_LOG_COMPONENT defined in mongo/util/log.h
#define VLOG(x) \
- if (!(::mongo::logger::globalLogDomain())->shouldLog(::mongo::logger::LogComponent::kGeo, ::mongo::logger::LogSeverity::Debug(5))) {} \
- else ::mongo::logger::LogstreamBuilder(::mongo::logger::globalLogDomain(), ::mongo::getThreadName(), ::mongo::logger::LogSeverity::Debug(5), ::mongo::logger::LogComponent::kGeo)
+ if (s2_env::globalLoggingEnv().shouldVLog((int)x)) {} \
+ else s2_env::LogMessage(int(x)).stream()
+
+namespace s2_env {
-class LogMessageBase {
+class LogMessageSink {
public:
- LogMessageBase(::mongo::logger::LogstreamBuilder builder);
- LogMessageBase(::mongo::logger::LogstreamBuilder builder, const char* file, int line);
- virtual ~LogMessageBase() { };
- std::ostream& stream() { return _lsb.stream(); }
-protected:
- // Fatal message will deconstruct it before abort to flush final message.
- mongo::logger::LogstreamBuilder _lsb;
-private:
- DISALLOW_COPY_AND_ASSIGN(LogMessageBase);
+ virtual ~LogMessageSink();
+ virtual std::ostream& stream() = 0;
};
-class LogMessageInfo : public LogMessageBase {
+class LogMessage {
public:
- LogMessageInfo();
- virtual ~LogMessageInfo() { };
+ enum class Severity {
+ kInfo,
+ kWarning,
+ kFatal,
+ };
-private:
- DISALLOW_COPY_AND_ASSIGN(LogMessageInfo);
+ explicit LogMessage(int verbosity);
+ explicit LogMessage(Severity severity);
+ explicit LogMessage(Severity severity, const char* file, int line);
+
+ virtual ~LogMessage();
+
+ std::ostream& stream() {
+ return _sink->stream();
+ }
+
+protected:
+ std::unique_ptr<LogMessageSink> _sink;
};
-class LogMessageWarning : public LogMessageBase {
+class StringStream {
public:
- LogMessageWarning(const char* file, int line);
- virtual ~LogMessageWarning() { };
+ StringStream() = default;
+
+ template <typename T>
+ StringStream& operator<<(T&& t) {
+ _s << std::forward<T>(t);
+ return *this;
+ }
+
+ operator std::string() const {
+ return _s.str();
+ }
private:
- DISALLOW_COPY_AND_ASSIGN(LogMessageWarning);
+ std::ostringstream _s;
};
-class LogMessageFatal : public LogMessageBase {
+class LoggingEnv {
public:
- LogMessageFatal(const char* file, int line);
- virtual ~LogMessageFatal();
-
-private:
- DISALLOW_COPY_AND_ASSIGN(LogMessageFatal);
+ virtual ~LoggingEnv();
+ virtual bool shouldVLog(int verbosity) = 0;
+ virtual std::unique_ptr<LogMessageSink> makeSink(int verbosity) = 0;
+ virtual std::unique_ptr<LogMessageSink> makeSink(LogMessage::Severity severity) = 0;
+ virtual std::unique_ptr<LogMessageSink> makeSink(LogMessage::Severity severity,
+ const char* file, int line) = 0;
};
+// provided by logging_mongo.cc
+LoggingEnv& globalLoggingEnv();
+
+} // namespace s2_env
#endif // BASE_LOGGING_H
diff --git a/src/third_party/s2/base/logging_mongo.cc b/src/third_party/s2/base/logging_mongo.cc
new file mode 100644
index 00000000000..c9f73754dde
--- /dev/null
+++ b/src/third_party/s2/base/logging_mongo.cc
@@ -0,0 +1,138 @@
+/**
+ * Copyright (C) 2019-present MongoDB, Inc.
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the Server Side Public License, version 1,
+ * as published by MongoDB, Inc.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * Server Side Public License for more details.
+ *
+ * You should have received a copy of the Server Side Public License
+ * along with this program. If not, see
+ * <http://www.mongodb.com/licensing/server-side-public-license>.
+ *
+ * As a special exception, the copyright holders give permission to link the
+ * code of portions of this program with the OpenSSL library under certain
+ * conditions as described in each individual source file and distribute
+ * linked combinations including the program with the OpenSSL library. You
+ * must comply with the Server Side Public License in all respects for
+ * all of the code used other than as permitted herein. If you modify file(s)
+ * with this exception, you may extend this exception to your version of the
+ * file(s), but you are not obligated to do so. If you do not wish to do so,
+ * delete this exception statement from your version. If you delete this
+ * exception statement from all source files in the program, then also delete
+ * it in the license file.
+ */
+
+#define MONGO_LOG_DEFAULT_COMPONENT ::mongo::logger::LogComponent::kGeo
+
+#include "logging.h"
+
+#include <boost/optional.hpp>
+#include <utility>
+
+#include "mongo/logger/logger.h"
+#include "mongo/logger/log_severity.h"
+#include "mongo/logger/logstream_builder.h"
+#include "mongo/util/assert_util.h"
+#include "mongo/util/concurrency/thread_name.h"
+#include "mongo/util/log.h"
+
+namespace s2_mongo {
+
+namespace ml = mongo::logger;
+
+// VLOG messages will be logged at debug level 5 with the S2 log component.
+// Expansion of MONGO_LOG_COMPONENT defined in mongo/util/log.h
+class VLogSink : public s2_env::LogMessageSink {
+public:
+ explicit VLogSink(int verbosity)
+ : _v(verbosity),
+ _lsb(ml::globalLogDomain(),
+ mongo::getThreadName(),
+ ml::LogSeverity::Debug(5),
+ ml::LogComponent::kGeo) {}
+ std::ostream& stream() override { return _lsb.stream(); }
+private:
+ int _v;
+ ml::LogstreamBuilder _lsb;
+};
+
+class SeverityLogSink : public s2_env::LogMessageSink {
+public:
+ // Fatal message will deconstruct it before abort to flush final message.
+ explicit SeverityLogSink(s2_env::LogMessage::Severity severity, ml::LogstreamBuilder builder)
+ : _severity(severity),
+ _lsb(std::move(builder)) {}
+
+ SeverityLogSink(s2_env::LogMessage::Severity severity, ml::LogstreamBuilder builder,
+ const char* file, int line)
+ : _severity(severity),
+ _lsb(std::move(builder)) {
+ std::ostringstream os;
+ os << file << ":" << line << ": ";
+ _lsb->setBaseMessage(os.str());
+ }
+ ~SeverityLogSink() {
+ if (_severity == s2_env::LogMessage::Severity::kFatal) {
+ _lsb = {}; // killing _lsb early to force a log flush
+ fassertFailed(40048);
+ }
+ }
+
+ std::ostream& stream() override { return _lsb->stream(); }
+private:
+ s2_env::LogMessage::Severity _severity;
+ boost::optional<ml::LogstreamBuilder> _lsb;
+};
+
+template <typename...A>
+std::unique_ptr<s2_env::LogMessageSink> makeSinkImpl(s2_env::LogMessage::Severity severity, A&&...a) {
+ auto builder = [&] {
+ switch (severity) {
+ case s2_env::LogMessage::Severity::kInfo:
+ return mongo::log();
+ case s2_env::LogMessage::Severity::kWarning:
+ return mongo::warning();
+ case s2_env::LogMessage::Severity::kFatal:
+ default:
+ return mongo::severe();
+ }
+ };
+ return std::make_unique<SeverityLogSink>(severity, builder(), std::forward<A>(a)...);
+}
+
+class MongoLoggingEnv : public s2_env::LoggingEnv {
+public:
+ MongoLoggingEnv() = default;
+ ~MongoLoggingEnv() override {}
+ bool shouldVLog(int verbosity) override {
+ return ml::globalLogDomain()->shouldLog(
+ ml::LogComponent::kGeo,
+ ml::LogSeverity::Debug(5));
+ }
+ std::unique_ptr<s2_env::LogMessageSink> makeSink(int verbosity) override {
+ return std::make_unique<VLogSink>(verbosity);
+ }
+ std::unique_ptr<s2_env::LogMessageSink> makeSink(s2_env::LogMessage::Severity severity) override {
+ return makeSinkImpl(severity);
+ }
+ std::unique_ptr<s2_env::LogMessageSink> makeSink(s2_env::LogMessage::Severity severity,
+ const char* file, int line) override {
+ return makeSinkImpl(severity, file, line);
+ }
+};
+
+} // namespace s2_mongo
+
+namespace s2_env {
+
+LoggingEnv& globalLoggingEnv() {
+ static LoggingEnv *p = new s2_mongo::MongoLoggingEnv();
+ return *p;
+}
+
+} // namespace s2_env
diff --git a/src/third_party/s2/s2cellid.cc b/src/third_party/s2/s2cellid.cc
index 920725f72a0..2cc7969172f 100644
--- a/src/third_party/s2/s2cellid.cc
+++ b/src/third_party/s2/s2cellid.cc
@@ -15,6 +15,8 @@ using std::reverse;
#include <iomanip>
using std::setprecision;
+#include <mutex>
+
#include <vector>
using std::vector;
@@ -27,8 +29,6 @@ using std::vector;
#include "util/math/mathutil.h"
#include "util/math/vector2-inl.h"
-#include "mongo/base/init.h"
-
// The following lookup tables are used to convert efficiently between an
// (i,j) cell index and the corresponding position along the Hilbert curve.
// "lookup_pos" maps 4 bits of "i", 4 bits of "j", and 2 bits representing the
@@ -88,16 +88,16 @@ static void InitLookupCell(int level, int i, int j, int orig_orientation,
}
}
-static void Init() {
- InitLookupCell(0, 0, 0, 0, 0, 0);
- InitLookupCell(0, 0, 0, kSwapMask, 0, kSwapMask);
- InitLookupCell(0, 0, 0, kInvertMask, 0, kInvertMask);
- InitLookupCell(0, 0, 0, kSwapMask|kInvertMask, 0, kSwapMask|kInvertMask);
-}
-
-MONGO_INITIALIZER(S2CellIdInit)(mongo::InitializerContext *context) {
- Init();
- return mongo::Status::OK();
+// Modern s2geometry does this with std::call_once, so we will copy that technique.
+// https://github.com/google/s2geometry/blob/bec06921d7/src/s2/s2cell_id.cc#L102
+static std::once_flag flag;
+static void MaybeInit() {
+ std::call_once(flag, []{
+ InitLookupCell(0, 0, 0, 0, 0, 0);
+ InitLookupCell(0, 0, 0, kSwapMask, 0, kSwapMask);
+ InitLookupCell(0, 0, 0, kInvertMask, 0, kInvertMask);
+ InitLookupCell(0, 0, 0, kSwapMask|kInvertMask, 0, kSwapMask|kInvertMask);
+ });
}
int S2CellId::level() const {
@@ -211,6 +211,8 @@ inline int S2CellId::STtoIJ(double s) {
S2CellId S2CellId::FromFaceIJ(int face, int i, int j) {
+ MaybeInit();
+
// Optimization notes:
// - Non-overlapping bit fields can be combined with either "+" or "|".
// Generally "+" seems to produce better code, but not always.
@@ -270,6 +272,8 @@ S2CellId S2CellId::FromLatLng(S2LatLng const& ll) {
}
int S2CellId::ToFaceIJOrientation(int* pi, int* pj, int* orientation) const {
+ MaybeInit();
+
int i = 0, j = 0;
int face = this->face();
int bits = (face & kSwapMask);
diff --git a/src/third_party/s2/s2loop.cc b/src/third_party/s2/s2loop.cc
index d4087fab971..dc6c9b8a4d5 100644
--- a/src/third_party/s2/s2loop.cc
+++ b/src/third_party/s2/s2loop.cc
@@ -29,19 +29,16 @@ using std::make_pair;
#include "s2cell.h"
#include "s2edgeindex.h"
-#include "mongo/util/str.h"
-using mongo::str::stream;
-
static const unsigned char kCurrentEncodingVersionNumber = 1;
namespace {
- stream& operator<<(stream& strStream, const S1Angle& angle) {
+ s2_env::StringStream& operator<<(s2_env::StringStream& strStream, const S1Angle& angle) {
std::stringstream ss;
ss << angle;
return strStream << ss.str();
}
// Reverse the output order of Lat/Lng to Lng/Lat
- stream& operator<<(stream& strStream, const S2LatLng& ll) {
+ s2_env::StringStream& operator<<(s2_env::StringStream& strStream, const S2LatLng& ll) {
return strStream << "[" << ll.lng() << ", " << ll.lat() << "]";
}
}
@@ -118,7 +115,7 @@ bool S2Loop::IsValid(string* err) const {
for (int i = 0; i < num_vertices(); ++i) {
if (!S2::IsUnitLength(vertex(i))) {
VLOG(2) << "Vertex " << i << " is not unit length";
- if (err) *err = stream() << "Vertex " << i << " is not unit length";
+ if (err) *err = s2_env::StringStream() << "Vertex " << i << " is not unit length";
return false;
}
}
@@ -127,7 +124,8 @@ bool S2Loop::IsValid(string* err) const {
for (int i = 0; i < num_vertices(); ++i) {
if (!vmap.insert(make_pair(vertex(i), i)).second) {
VLOG(2) << "Duplicate vertices: " << vmap[vertex(i)] << " and " << i;
- if (err) *err = stream() << "Duplicate vertices: " << vmap[vertex(i)] << " and " << i;
+ if (err) *err = s2_env::StringStream() << "Duplicate vertices: " << vmap[vertex(i)]
+ << " and " << i;
return false;
}
}
@@ -152,14 +150,14 @@ bool S2Loop::IsValid(string* err) const {
if (crosses) {
VLOG(2) << "Edges " << i << " and " << ai << " cross";
// additional debugging information, reverse Lat/Lng order.
- string errDetail = stream()
+ string errDetail = s2_env::StringStream()
<< "Edge locations in degrees: "
<< S2LatLng(vertex(i)) << "-" << S2LatLng(vertex(i + 1))
<< " and "
<< S2LatLng(vertex(ai)) << "-" << S2LatLng(vertex(ai + 1));
VLOG(2) << errDetail;
if (NULL != err) {
- *err = stream()
+ *err = s2_env::StringStream()
<< "Edges " << i << " and " << ai << " cross. " << errDetail;
}
break;
diff --git a/src/third_party/s2/s2polygon.cc b/src/third_party/s2/s2polygon.cc
index afd18467c63..3762ce8c659 100644
--- a/src/third_party/s2/s2polygon.cc
+++ b/src/third_party/s2/s2polygon.cc
@@ -29,9 +29,6 @@ using std::vector;
#include "s2polygonbuilder.h"
#include "s2polyline.h"
-#include "mongo/util/str.h"
-using mongo::str::stream;
-
static const unsigned char kCurrentEncodingVersionNumber = 1;
typedef pair<S2Point, S2Point> S2Edge;
@@ -134,7 +131,7 @@ bool S2Polygon::IsValid(const vector<S2Loop*>& loops, string* err) {
VLOG(2) << "Duplicate edge: loop " << i << ", edge " << j
<< " and loop " << other.first << ", edge " << other.second;
if (err) {
- *err = stream() << "Duplicate edge: loop " << i << ", edge " << j
+ *err = s2_env::StringStream() << "Duplicate edge: loop " << i << ", edge " << j
<< " and loop " << other.first << ", edge " << other.second;
}
return false;
@@ -147,7 +144,7 @@ bool S2Polygon::IsValid(const vector<S2Loop*>& loops, string* err) {
for (size_t i = 0; i < loops.size(); ++i) {
if (!loops[i]->IsNormalized()) {
VLOG(2) << "Loop " << i << " encloses more than half the sphere";
- if (err) *err = stream() << "Loop " << i << " encloses more than half the sphere";
+ if (err) *err = s2_env::StringStream() << "Loop " << i << " encloses more than half the sphere";
return false;
}
for (size_t j = i + 1; j < loops.size(); ++j) {
@@ -155,7 +152,7 @@ bool S2Polygon::IsValid(const vector<S2Loop*>& loops, string* err) {
// cases where the two boundaries cross at a shared vertex.
if (loops[i]->ContainsOrCrosses(loops[j]) < 0) {
VLOG(2) << "Loop " << i << " crosses loop " << j;
- if (err) *err = stream() << "Loop " << i << " crosses loop " << j;
+ if (err) *err = s2_env::StringStream() << "Loop " << i << " crosses loop " << j;
return false;
}
}
@@ -1108,7 +1105,7 @@ bool S2Polygon::IsNormalized(string* err) const {
}
if (count > 1) {
if (err) {
- *err = stream() << "Loop " << i << " shares more than one vertex"
+ *err = s2_env::StringStream() << "Loop " << i << " shares more than one vertex"
<< " with its parent loop " << GetParent(i);
}
return false;
diff --git a/src/third_party/s2/s2polyline.cc b/src/third_party/s2/s2polyline.cc
index 08769555e4a..f23401e205b 100644
--- a/src/third_party/s2/s2polyline.cc
+++ b/src/third_party/s2/s2polyline.cc
@@ -18,9 +18,6 @@ using std::vector;
#include "s2latlng.h"
#include "s2edgeutil.h"
-#include "mongo/util/str.h"
-using mongo::str::stream;
-
static const unsigned char kCurrentEncodingVersionNumber = 1;
S2Polyline::S2Polyline()
@@ -80,7 +77,7 @@ bool S2Polyline::IsValid(vector<S2Point> const& v, string* err) {
if (!S2::IsUnitLength(v[i])) {
S2LOG(INFO) << "Vertex " << i << " is not unit length";
if (err) {
- *err = stream() << "Vertex " << i << " is not unit length";
+ *err = s2_env::StringStream() << "Vertex " << i << " is not unit length";
}
return false;
}
@@ -92,7 +89,7 @@ bool S2Polyline::IsValid(vector<S2Point> const& v, string* err) {
S2LOG(INFO) << "Vertices " << (i - 1) << " and " << i
<< " are identical or antipodal";
if (err) {
- *err = stream() << "Vertices " << (i - 1) << " and " << i
+ *err = s2_env::StringStream() << "Vertices " << (i - 1) << " and " << i
<< " are identical or antipodal";
}
return false;
diff --git a/src/third_party/s2/s2regioncoverer.cc b/src/third_party/s2/s2regioncoverer.cc
index 3c3337e27c7..d05499613a0 100644
--- a/src/third_party/s2/s2regioncoverer.cc
+++ b/src/third_party/s2/s2regioncoverer.cc
@@ -15,6 +15,8 @@ using std::reverse;
#include <functional>
using std::less;
+#include <mutex>
+
#include <queue>
using std::priority_queue;
@@ -26,7 +28,6 @@ using std::vector;
#include "s2.h"
#include "s2cap.h"
#include "s2cellunion.h"
-#include "mongo/base/init.h"
// Define storage for header file constants (the values are not needed here).
int const S2RegionCoverer::kDefaultMaxCells = 8;
@@ -44,15 +45,13 @@ struct S2RegionCoverer::CompareQueueEntries : public less<QueueEntry> {
static S2Cell face_cells[6];
-static void Init() {
- for (int face = 0; face < 6; ++face) {
- face_cells[face] = S2Cell::FromFacePosLevel(face, 0, 0);
- }
-}
-
-MONGO_INITIALIZER_WITH_PREREQUISITES(S2RegionCovererInit, ("S2CellIdInit"))(mongo::InitializerContext *context) {
- Init();
- return mongo::Status::OK();
+static std::once_flag flag;
+static void MaybeInit() {
+ std::call_once(flag, []{
+ for (int face = 0; face < 6; ++face) {
+ face_cells[face] = S2Cell::FromFacePosLevel(face, 0, 0);
+ }
+ });
}
S2RegionCoverer::S2RegionCoverer() :
@@ -225,6 +224,7 @@ void S2RegionCoverer::GetInitialCandidates() {
}
}
// Default: start with all six cube faces.
+ MaybeInit();
for (size_t face = 0; face < 6; ++face) {
AddCandidate(NewCandidate(face_cells[face]));
}