Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add nostd::make_unique #3097

Closed
wants to merge 6 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions api/include/opentelemetry/nostd/unique_ptr.h
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,12 @@ bool operator!=(std::nullptr_t, const unique_ptr<T> &rhs) noexcept
{
return nullptr != rhs.get();
}

template <class T, class... Args>
unique_ptr<T> make_unique(Args &&...args)
{
return unique_ptr<T>(new T(std::forward<Args>(args)...));
}
} // namespace nostd
OPENTELEMETRY_END_NAMESPACE
#endif /* OPENTELEMETRY_HAVE_STD_UNIQUE_PTR */
11 changes: 11 additions & 0 deletions api/include/opentelemetry/std/unique_ptr.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,5 +18,16 @@ namespace nostd
template <class... _Types>
using unique_ptr = std::unique_ptr<_Types...>;

#if (defined(__cplusplus) && __cplusplus >= 201402L) || \
(defined(_MSVC_LANG) && _MSVC_LANG >= 201402L)
using std::make_unique;
#else
template <class T, class... Args>
unique_ptr<T> make_unique(Args &&...args)
{
return unique_ptr<T>(new T(std::forward<Args>(args)...));
}
#endif

} // namespace nostd
OPENTELEMETRY_END_NAMESPACE
2 changes: 1 addition & 1 deletion examples/multi_processor/main.cc
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ void CleanupTracer()
trace_api::Provider::SetTracerProvider(none);
}

void dumpSpans(std::vector<std::unique_ptr<trace_sdk::SpanData>> &spans)
void dumpSpans(std::vector<opentelemetry::nostd::unique_ptr<trace_sdk::SpanData>> &spans)
{
char span_buf[trace_api::SpanId::kSize * 2];
char trace_buf[trace_api::TraceId::kSize * 2];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,24 +27,24 @@ class InMemoryData
/**
* @param data a required unique pointer to the data to add to the CircularBuffer
*/
void Add(std::unique_ptr<T> data) noexcept { data_.Add(data); }
void Add(nostd::unique_ptr<T> data) noexcept { data_.Add(data); }

/**
* @return Returns a vector of unique pointers containing all the data in the
* CircularBuffer. This operation will empty the Buffer, which is why the data
* is returned as unique pointers
*/
std::vector<std::unique_ptr<T>> Get() noexcept
std::vector<nostd::unique_ptr<T>> Get() noexcept
{
std::vector<std::unique_ptr<T>> res;
std::vector<nostd::unique_ptr<T>> res;

// Pointer swap is required because the Consume function requires that the
// AtomicUniquePointer be set to null
data_.Consume(
data_.size(), [&](opentelemetry::sdk::common::CircularBufferRange<
opentelemetry::sdk::common::AtomicUniquePtr<T>> range) noexcept {
range.ForEach([&](opentelemetry::sdk::common::AtomicUniquePtr<T> &ptr) noexcept {
std::unique_ptr<T> swap_ptr = nullptr;
nostd::unique_ptr<T> swap_ptr = nullptr;
ptr.Swap(swap_ptr);
res.push_back(std::move(swap_ptr));
return true;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include <tuple>

#include "opentelemetry/exporters/memory/in_memory_data.h"
#include "opentelemetry/nostd/unique_ptr.h"
#include "opentelemetry/sdk/metrics/data/metric_data.h"

OPENTELEMETRY_BEGIN_NAMESPACE
Expand Down Expand Up @@ -37,7 +38,7 @@ class InMemoryMetricData
InMemoryMetricData &operator=(const InMemoryMetricData &) = delete;
InMemoryMetricData &operator=(InMemoryMetricData &&) = delete;

virtual void Add(std::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) = 0;
virtual void Add(nostd::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) = 0;
};

/// An implementation of InMemoryMetricData that stores full-fidelity data points in a circular
Expand All @@ -48,7 +49,7 @@ class CircularBufferInMemoryMetricData final : public InMemoryMetricData,
{
public:
explicit CircularBufferInMemoryMetricData(size_t buffer_size);
void Add(std::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) override;
void Add(nostd::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) override;
};

/// An implementation of InMemoryMetricData that stores only the most recent data point in each time
Expand All @@ -59,7 +60,7 @@ class SimpleAggregateInMemoryMetricData final : public InMemoryMetricData
using AttributeToPoint = std::map<opentelemetry::sdk::metrics::PointAttributes,
opentelemetry::sdk::metrics::PointType>;

void Add(std::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) override;
void Add(nostd::unique_ptr<sdk::metrics::ResourceMetrics> resource_metrics) override;
const AttributeToPoint &Get(const std::string &scope, const std::string &metric);
void Clear();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ class InMemorySpanData final : public exporter::memory::InMemoryData<sdk::trace:
: exporter::memory::InMemoryData<sdk::trace::SpanData>(buffer_size)
{}

std::vector<std::unique_ptr<sdk::trace::SpanData>> GetSpans() noexcept { return Get(); }
std::vector<nostd::unique_ptr<sdk::trace::SpanData>> GetSpans() noexcept { return Get(); }
};
} // namespace memory
} // namespace exporter
Expand Down
9 changes: 5 additions & 4 deletions exporters/memory/src/in_memory_metric_data.cc
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,12 @@ CircularBufferInMemoryMetricData::CircularBufferInMemoryMetricData(size_t buffer
: InMemoryData(buffer_size)
{}

void CircularBufferInMemoryMetricData::Add(std::unique_ptr<ResourceMetrics> resource_metrics)
void CircularBufferInMemoryMetricData::Add(nostd::unique_ptr<ResourceMetrics> resource_metrics)
{
InMemoryData::Add(std::move(resource_metrics));
}

void SimpleAggregateInMemoryMetricData::Add(std::unique_ptr<ResourceMetrics> resource_metrics)
void SimpleAggregateInMemoryMetricData::Add(nostd::unique_ptr<ResourceMetrics> resource_metrics)
{
for (const auto &sm : resource_metrics->scope_metric_data_)
{
Expand All @@ -31,7 +31,8 @@ void SimpleAggregateInMemoryMetricData::Add(std::unique_ptr<ResourceMetrics> res
const auto &metric = m.instrument_descriptor.name_;
for (const auto &pda : m.point_data_attr_)
{
data_[{scope, metric}].insert({pda.attributes, pda.point_data});
data_[std::tuple<std::string, std::string>{scope, metric}].insert(
{pda.attributes, pda.point_data});
}
}
}
Expand All @@ -41,7 +42,7 @@ const SimpleAggregateInMemoryMetricData::AttributeToPoint &SimpleAggregateInMemo
const std::string &scope,
const std::string &metric)
{
return data_[{scope, metric}];
return data_[std::tuple<std::string, std::string>{scope, metric}];
}

void SimpleAggregateInMemoryMetricData::Clear()
Expand Down
8 changes: 5 additions & 3 deletions exporters/memory/src/in_memory_metric_exporter_factory.cc
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

#include "opentelemetry/exporters/memory/in_memory_metric_exporter_factory.h"
#include "opentelemetry/exporters/memory/in_memory_metric_data.h"
#include "opentelemetry/nostd/unique_ptr.h"
#include "opentelemetry/sdk/common/global_log_handler.h"
#include "opentelemetry/sdk/metrics/export/metric_producer.h"
#include "opentelemetry/sdk/metrics/push_metric_exporter.h"
Expand Down Expand Up @@ -49,7 +50,7 @@ class InMemoryMetricExporter final : public sdk::metrics::PushMetricExporter
OTEL_INTERNAL_LOG_ERROR("[In Memory Metric Exporter] Exporting failed, exporter is shutdown");
return ExportResult::kFailure;
}
data_->Add(std::make_unique<ResourceMetrics>(data));
data_->Add(opentelemetry::nostd::make_unique<ResourceMetrics>(data));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This opens a whole new can of worms (see CI), because now data_ is a std::shared_ptr and the code wants to add an nostd::unique_ptr to it, instead of a std::unique_ptr.

How about a simpler solution without new nostd helpers, like:

data_->Add(std::unique_ptr<ResourceMetrics>(new ResourceMetrics(data)));

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, I modified the parameter type of this API but kept std::unique_ptr in the exported APIs for ABI compatibility.

return ExportResult::kSuccess;
}

Expand Down Expand Up @@ -78,14 +79,15 @@ class InMemoryMetricExporter final : public sdk::metrics::PushMetricExporter
std::unique_ptr<PushMetricExporter> InMemoryMetricExporterFactory::Create(
const std::shared_ptr<InMemoryMetricData> &data)
{
return Create(data, [](auto) { return AggregationTemporality::kCumulative; });
return Create(data,
[](sdk::metrics::InstrumentType) { return AggregationTemporality::kCumulative; });
}

std::unique_ptr<PushMetricExporter> InMemoryMetricExporterFactory::Create(
const std::shared_ptr<InMemoryMetricData> &data,
const AggregationTemporalitySelector &temporality)
{
return std::make_unique<InMemoryMetricExporter>(data, temporality);
return std::unique_ptr<InMemoryMetricExporter>(new InMemoryMetricExporter{data, temporality});
}

} // namespace memory
Expand Down
5 changes: 3 additions & 2 deletions exporters/memory/test/in_memory_metric_data_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
// SPDX-License-Identifier: Apache-2.0

#include "opentelemetry/exporters/memory/in_memory_metric_data.h"
#include "opentelemetry/nostd/unique_ptr.h"
#include "opentelemetry/sdk/instrumentationscope/instrumentation_scope.h"
#include "opentelemetry/sdk/metrics/export/metric_producer.h"
#include "opentelemetry/sdk/resource/resource.h"
Expand All @@ -23,7 +24,7 @@ TEST(InMemoryMetricDataTest, CircularBuffer)
{
CircularBufferInMemoryMetricData buf(10);
Resource resource = Resource::GetEmpty();
buf.Add(std::make_unique<ResourceMetrics>(
buf.Add(opentelemetry::nostd::make_unique<ResourceMetrics>(
&resource, std::vector<ScopeMetrics>{{nullptr, std::vector<MetricData>{}}}));
EXPECT_EQ((*buf.Get().begin())->resource_, &resource);
}
Expand All @@ -45,7 +46,7 @@ TEST(InMemoryMetricDataTest, SimpleAggregate)
md.instrument_descriptor.name_ = "my-metric";
md.point_data_attr_.push_back(pda);

agg.Add(std::make_unique<ResourceMetrics>(
agg.Add(opentelemetry::nostd::make_unique<ResourceMetrics>(
&resource, std::vector<ScopeMetrics>{{scope.get(), std::vector<MetricData>{md}}}));
auto it = agg.Get("my-scope", "my-metric").begin();

Expand Down
32 changes: 32 additions & 0 deletions sdk/include/opentelemetry/sdk/common/atomic_unique_ptr.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include <atomic>
#include <memory>

#include "opentelemetry/nostd/unique_ptr.h"
#include "opentelemetry/version.h"

OPENTELEMETRY_BEGIN_NAMESPACE
Expand All @@ -25,6 +26,10 @@ class AtomicUniquePtr

explicit AtomicUniquePtr(std::unique_ptr<T> &&other) noexcept : ptr_(other.release()) {}

#if !defined(OPENTELEMETRY_HAVE_STD_UNIQUE_PTR)
explicit AtomicUniquePtr(nostd::unique_ptr<T> &&other) noexcept : ptr_(other.release()) {}
#endif

~AtomicUniquePtr() noexcept { Reset(); }

T &operator*() const noexcept { return *Get(); }
Expand Down Expand Up @@ -66,6 +71,33 @@ class AtomicUniquePtr
*/
void Swap(std::unique_ptr<T> &other) noexcept { other.reset(ptr_.exchange(other.release())); }

#if !defined(OPENTELEMETRY_HAVE_STD_UNIQUE_PTR)
/**
* Atomically swap the pointer only if it's null.
* @param owner the pointer to swap with
* @return true if the swap was successful
*/
bool SwapIfNull(nostd::unique_ptr<T> &owner) noexcept
{
auto ptr = owner.get();
T *expected = nullptr;
auto was_successful = ptr_.compare_exchange_weak(expected, ptr, std::memory_order_release,
std::memory_order_relaxed);
if (was_successful)
{
owner.release();
return true;
}
return false;
}

/**
* Atomically swap the pointer with another.
* @param ptr the pointer to swap with
*/
void Swap(nostd::unique_ptr<T> &other) noexcept { other.reset(ptr_.exchange(other.release())); }
#endif

/**
* Set the pointer to a new value and delete the current value if non-null.
* @param ptr the new pointer value to set
Expand Down
18 changes: 16 additions & 2 deletions sdk/include/opentelemetry/sdk/common/circular_buffer.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
#include <memory>

#include "opentelemetry/nostd/span.h"
#include "opentelemetry/nostd/unique_ptr.h"
#include "opentelemetry/sdk/common/atomic_unique_ptr.h"
#include "opentelemetry/sdk/common/circular_buffer_range.h"
#include "opentelemetry/version.h"
Expand Down Expand Up @@ -83,7 +84,7 @@ class CircularBuffer
* @param ptr a pointer to the element to add
* @return true if the element was successfully added; false, otherwise.
*/
bool Add(std::unique_ptr<T> &ptr) noexcept
bool Add(nostd::unique_ptr<T> &ptr) noexcept
{
while (true)
{
Expand Down Expand Up @@ -118,14 +119,27 @@ class CircularBuffer
}
}

bool Add(std::unique_ptr<T> &&ptr) noexcept
bool Add(nostd::unique_ptr<T> &&ptr) noexcept
{
// rvalue to lvalue reference
bool result = Add(std::ref(ptr));
ptr.reset();
return result;
}

#if !defined(OPENTELEMETRY_HAVE_STD_UNIQUE_PTR)
bool Add(std::unique_ptr<T> &ptr) noexcept
{
nostd::unique_ptr<T> convert_ptr{std::move(ptr)};

bool result = Add(convert_ptr);
ptr.reset(convert_ptr.release());
return result;
}

bool Add(std::unique_ptr<T> &&ptr) noexcept { return Add(nostd::unique_ptr<T>{std::move(ptr)}); }
#endif

/**
* Clear the circular buffer.
*
Expand Down