Mark always_inline functions inline.

You would think always_inline implies inline, but GCC complains loudly if the always_inline attribute is not also accompanied by the normal inline keyword.
pull/37834/head
Benjamin Peterson 2 months ago
parent 9a12ec91e1
commit 3ecfaa6d50
  1. 2
      src/core/lib/promise/all_ok.h
  2. 8
      src/core/lib/promise/cancel_callback.h
  3. 8
      src/core/lib/promise/context.h
  4. 8
      src/core/lib/promise/detail/promise_factory.h
  5. 2
      src/core/lib/promise/detail/promise_like.h
  6. 6
      src/core/lib/promise/detail/status.h
  7. 3
      src/core/lib/promise/for_each.h
  8. 11
      src/core/lib/promise/if.h
  9. 6
      src/core/lib/promise/join.h
  10. 2
      src/core/lib/promise/loop.h
  11. 6
      src/core/lib/promise/map.h
  12. 6
      src/core/lib/promise/poll.h
  13. 6
      src/core/lib/promise/promise.h
  14. 4
      src/core/lib/promise/race.h
  15. 16
      src/core/lib/promise/seq.h
  16. 5
      src/core/lib/promise/try_join.h
  17. 16
      src/core/lib/promise/try_seq.h
  18. 2
      src/core/lib/resource_quota/arena.h
  19. 5
      src/core/util/construct_destruct.h
  20. 4
      src/core/util/down_cast.h

@ -78,7 +78,7 @@ class AllOk {
// If any fail, cancel the rest and return the failure.
// If all succeed, return Ok.
template <typename Result, typename... Promises>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto AllOk(Promises... promises) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto AllOk(Promises... promises) {
return promise_detail::AllOk<Result, Promises...>(std::move(promises)...);
}

@ -69,8 +69,8 @@ class Handler {
// completion.
// Returns a promise with the same result type as main_fn.
template <typename MainFn, typename CancelFn>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto OnCancel(MainFn main_fn,
CancelFn cancel_fn) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto OnCancel(MainFn main_fn,
CancelFn cancel_fn) {
return [on_cancel =
cancel_callback_detail::Handler<CancelFn>(std::move(cancel_fn)),
main_fn = promise_detail::PromiseLike<MainFn>(
@ -87,8 +87,8 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto OnCancel(MainFn main_fn,
// resulting promise. If the factory is dropped without being called, cancel_fn
// is called.
template <typename MainFn, typename CancelFn>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto OnCancelFactory(MainFn main_fn,
CancelFn cancel_fn) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto OnCancelFactory(
MainFn main_fn, CancelFn cancel_fn) {
return [on_cancel =
cancel_callback_detail::Handler<CancelFn>(std::move(cancel_fn)),
main_fn = std::move(main_fn)]() mutable {

@ -106,13 +106,13 @@ class WithContext {
// Return true if a context of type T is currently active.
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION bool HasContext() {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline bool HasContext() {
return promise_detail::Context<T>::get() != nullptr;
}
// Retrieve the current value of a context, or abort if the value is unset.
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION T* GetContext() {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline T* GetContext() {
auto* p = promise_detail::Context<T>::get();
DCHECK_NE(p, nullptr);
return p;
@ -120,12 +120,12 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION T* GetContext() {
// Retrieve the current value of a context, or nullptr if the value is unset.
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION T* MaybeGetContext() {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline T* MaybeGetContext() {
return promise_detail::Context<T>::get();
}
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION void SetContext(T* p) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline void SetContext(T* p) {
promise_detail::Context<T>::set(p);
}

@ -125,7 +125,7 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION
// Promote a callable() -> T|Poll<T> to a PromiseFactory(A) -> Promise<T>
// by dropping the argument passed to the factory.
template <typename A, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION absl::enable_if_t<
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline absl::enable_if_t<
!IsVoidCallable<ResultOf<F()>>::value, PromiseLike<RemoveCVRef<F>>>
PromiseFactoryImpl(F f, A&&) {
return PromiseLike<F>(std::move(f));
@ -133,7 +133,7 @@ PromiseFactoryImpl(F f, A&&) {
// Promote a callable() -> T|Poll<T> to a PromiseFactory() -> Promise<T>
template <typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION absl::enable_if_t<
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline absl::enable_if_t<
!IsVoidCallable<ResultOf<F()>>::value, PromiseLike<RemoveCVRef<F>>>
PromiseFactoryImpl(F f) {
return PromiseLike<F>(std::move(f));
@ -141,7 +141,7 @@ PromiseFactoryImpl(F f) {
// Given a callable(A) -> Promise<T>, name it a PromiseFactory and use it.
template <typename A, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION absl::enable_if_t<
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline absl::enable_if_t<
IsVoidCallable<ResultOf<F(A)>>::value,
PromiseLike<decltype(std::declval<F>()(std::declval<A>()))>>
PromiseFactoryImpl(F&& f, A&& arg) {
@ -150,7 +150,7 @@ PromiseFactoryImpl(F&& f, A&& arg) {
// Given a callable(A) -> Promise<T>, name it a PromiseFactory and use it.
template <typename A, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION absl::enable_if_t<
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline absl::enable_if_t<
IsVoidCallable<ResultOf<F(A)>>::value,
PromiseLike<decltype(std::declval<F>()(std::declval<A>()))>>
PromiseFactoryImpl(F& f, A&& arg) {

@ -64,7 +64,7 @@ struct PollWrapper<Poll<T>> {
};
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto WrapInPoll(T&& x)
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto WrapInPoll(T&& x)
-> decltype(PollWrapper<T>::Wrap(std::forward<T>(x))) {
return PollWrapper<T>::Wrap(std::forward<T>(x));
}

@ -30,7 +30,7 @@ namespace promise_detail {
// Convert with a move the input status to an absl::Status.
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION absl::Status IntoStatus(
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline absl::Status IntoStatus(
absl::StatusOr<T>* status) {
return std::move(status->status());
}
@ -103,7 +103,7 @@ struct StatusCastImpl<absl::Status, const absl::StatusOr<T>&> {
// For cases where the status is guaranteed to be a failure (and hence not
// needing to preserve values) see FailureStatusCast<> below.
template <typename To, typename From>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION To StatusCast(From&& from) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline To StatusCast(From&& from) {
return StatusCastImpl<To, From>::Cast(std::forward<From>(from));
}
@ -127,7 +127,7 @@ struct FailureStatusCastImpl<absl::StatusOr<T>, const absl::Status&> {
};
template <typename To, typename From>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION To FailureStatusCast(From&& from) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline To FailureStatusCast(From&& from) {
DCHECK(!IsStatusOk(from));
return FailureStatusCastImpl<To, From>::Cast(std::forward<From>(from));
}

@ -231,7 +231,8 @@ class ForEach {
/// For each item acquired by calling Reader::Next, run the promise Action.
template <typename Reader, typename Action>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION for_each_detail::ForEach<Reader, Action>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline for_each_detail::ForEach<Reader,
Action>
ForEach(Reader reader, Action action, DebugLocation whence = {}) {
return for_each_detail::ForEach<Reader, Action>(std::move(reader),
std::move(action), whence);

@ -33,8 +33,8 @@ namespace grpc_core {
namespace promise_detail {
template <typename CallPoll, typename T, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION typename CallPoll::PollResult ChooseIf(
CallPoll call_poll, bool result, T* if_true, F* if_false) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline typename CallPoll::PollResult
ChooseIf(CallPoll call_poll, bool result, T* if_true, F* if_false) {
if (result) {
auto promise = if_true->Make();
return call_poll(promise);
@ -45,8 +45,9 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION typename CallPoll::PollResult ChooseIf(
}
template <typename CallPoll, typename T, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION typename CallPoll::PollResult ChooseIf(
CallPoll call_poll, absl::StatusOr<bool> result, T* if_true, F* if_false) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline typename CallPoll::PollResult
ChooseIf(CallPoll call_poll, absl::StatusOr<bool> result, T* if_true,
F* if_false) {
if (!result.ok()) {
return typename CallPoll::PollResult(result.status());
} else if (*result) {
@ -200,7 +201,7 @@ class If<bool, T, F> {
// This makes it safe to capture lambda arguments in the promise factory by
// reference.
template <typename C, typename T, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::If<C, T, F> If(
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::If<C, T, F> If(
C condition, T if_true, F if_false) {
return promise_detail::If<C, T, F>(std::move(condition), std::move(if_true),
std::move(if_false));

@ -76,13 +76,13 @@ struct WrapInTuple {
/// Combinator to run all promises to completion, and return a tuple
/// of their results.
template <typename... Promise>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Join<Promise...> Join(
Promise... promises) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Join<Promise...>
Join(Promise... promises) {
return promise_detail::Join<Promise...>(std::move(promises)...);
}
template <typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto Join(F promise) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto Join(F promise) {
return Map(std::move(promise), promise_detail::WrapInTuple{});
}

@ -141,7 +141,7 @@ class Loop {
// Expects F returns LoopCtl<T> - if it's Continue, then run the loop again -
// otherwise yield the returned value as the result of the loop.
template <typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Loop<F> Loop(F f) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Loop<F> Loop(F f) {
return promise_detail::Loop<F>(std::move(f));
}

@ -68,8 +68,8 @@ class Map {
// Takes a promise, and a synchronous function to mutate its result, and
// returns a promise.
template <typename Promise, typename Fn>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Map<Promise, Fn> Map(
Promise promise, Fn fn) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Map<Promise, Fn>
Map(Promise promise, Fn fn) {
return promise_detail::Map<Promise, Fn>(std::move(promise), std::move(fn));
}
@ -77,7 +77,7 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Map<Promise, Fn> Map(
// and a bool indicating whether there was ever a Pending{} value observed from
// polling.
template <typename Promise>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto CheckDelayed(Promise promise) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto CheckDelayed(Promise promise) {
using P = promise_detail::PromiseLike<Promise>;
return [delayed = false, promise = P(std::move(promise))]() mutable
-> Poll<std::tuple<typename P::Result, bool>> {

@ -223,8 +223,8 @@ struct PollTraits<Poll<T>> {
};
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION bool operator==(const Poll<T>& a,
const Poll<T>& b) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline bool operator==(const Poll<T>& a,
const Poll<T>& b) {
if (a.pending() && b.pending()) return true;
if (a.ready() && b.ready()) return a.value() == b.value();
return false;
@ -263,7 +263,7 @@ struct PollCastImpl<T, Poll<T>> {
};
template <typename T, typename U>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION Poll<T> poll_cast(U poll) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline Poll<T> poll_cast(U poll) {
return PollCastImpl<T, U>::Cast(std::move(poll));
}

@ -72,8 +72,8 @@ class Immediate {
// Return \a value immediately
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Immediate<T> Immediate(
T value) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Immediate<T>
Immediate(T value) {
return promise_detail::Immediate<T>(std::move(value));
}
@ -90,7 +90,7 @@ struct ImmediateOkStatus {
// should fail to compile. When modifying this code these should be uncommented
// and their miscompilation verified.
template <typename T, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto WithResult(F f) ->
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto WithResult(F f) ->
typename std::enable_if<std::is_same<decltype(f()), Poll<T>>::value,
F>::type {
return f;

@ -74,8 +74,8 @@ class Race<Promise> {
/// If two results are simultaneously available, bias towards the first result
/// listed.
template <typename... Promises>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Race<Promises...> Race(
Promises... promises) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Race<Promises...>
Race(Promises... promises) {
return promise_detail::Race<Promises...>(std::move(promises)...);
}

@ -107,32 +107,33 @@ struct SeqIterResultTraits {
// etc
// Return the final value.
template <typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION F Seq(F functor) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline F Seq(F functor) {
return functor;
}
template <typename F0, typename F1>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Seq<F0, F1> Seq(
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Seq<F0, F1> Seq(
F0 f0, F1 f1, DebugLocation whence = {}) {
return promise_detail::Seq<F0, F1>(std::move(f0), std::move(f1), whence);
}
template <typename F0, typename F1, typename F2>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Seq<F0, F1, F2> Seq(
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Seq<F0, F1, F2> Seq(
F0 f0, F1 f1, F2 f2, DebugLocation whence = {}) {
return promise_detail::Seq<F0, F1, F2>(std::move(f0), std::move(f1),
std::move(f2), whence);
}
template <typename F0, typename F1, typename F2, typename F3>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Seq<F0, F1, F2, F3> Seq(
F0 f0, F1 f1, F2 f2, F3 f3, DebugLocation whence = {}) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Seq<F0, F1, F2, F3>
Seq(F0 f0, F1 f1, F2 f2, F3 f3, DebugLocation whence = {}) {
return promise_detail::Seq<F0, F1, F2, F3>(
std::move(f0), std::move(f1), std::move(f2), std::move(f3), whence);
}
template <typename F0, typename F1, typename F2, typename F3, typename F4>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Seq<F0, F1, F2, F3, F4>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Seq<F0, F1, F2, F3,
F4>
Seq(F0 f0, F1 f1, F2 f2, F3 f3, F4 f4, DebugLocation whence = {}) {
return promise_detail::Seq<F0, F1, F2, F3, F4>(std::move(f0), std::move(f1),
std::move(f2), std::move(f3),
@ -141,7 +142,8 @@ Seq(F0 f0, F1 f1, F2 f2, F3 f3, F4 f4, DebugLocation whence = {}) {
template <typename F0, typename F1, typename F2, typename F3, typename F4,
typename F5>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::Seq<F0, F1, F2, F3, F4, F5>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::Seq<F0, F1, F2, F3,
F4, F5>
Seq(F0 f0, F1 f1, F2 f2, F3 f3, F4 f4, F5 f5, DebugLocation whence = {}) {
return promise_detail::Seq<F0, F1, F2, F3, F4, F5>(
std::move(f0), std::move(f1), std::move(f2), std::move(f3), std::move(f4),

@ -134,13 +134,14 @@ struct WrapInStatusOrTuple {
// If any fail, cancel the rest and return the failure.
// If all succeed, return Ok(tuple-of-results).
template <template <typename> class R, typename... Promises>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::TryJoin<R, Promises...>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::TryJoin<R,
Promises...>
TryJoin(Promises... promises) {
return promise_detail::TryJoin<R, Promises...>(std::move(promises)...);
}
template <template <typename> class R, typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION auto TryJoin(F promise) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline auto TryJoin(F promise) {
return Map(promise, promise_detail::WrapInStatusOrTuple<R>{});
}

@ -278,32 +278,34 @@ struct TrySeqIterResultTraits {
// Status to indicate only success/failure. In the case of returning Status,
// the construction functors take no arguments.
template <typename F>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION F TrySeq(F functor) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline F TrySeq(F functor) {
return functor;
}
template <typename F0, typename F1>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::TrySeq<F0, F1> TrySeq(
F0 f0, F1 f1, DebugLocation whence = {}) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::TrySeq<F0, F1>
TrySeq(F0 f0, F1 f1, DebugLocation whence = {}) {
return promise_detail::TrySeq<F0, F1>(std::move(f0), std::move(f1), whence);
}
template <typename F0, typename F1, typename F2>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::TrySeq<F0, F1, F2> TrySeq(
F0 f0, F1 f1, F2 f2, DebugLocation whence = {}) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::TrySeq<F0, F1, F2>
TrySeq(F0 f0, F1 f1, F2 f2, DebugLocation whence = {}) {
return promise_detail::TrySeq<F0, F1, F2>(std::move(f0), std::move(f1),
std::move(f2), whence);
}
template <typename F0, typename F1, typename F2, typename F3>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::TrySeq<F0, F1, F2, F3>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::TrySeq<F0, F1, F2,
F3>
TrySeq(F0 f0, F1 f1, F2 f2, F3 f3, DebugLocation whence = {}) {
return promise_detail::TrySeq<F0, F1, F2, F3>(
std::move(f0), std::move(f1), std::move(f2), std::move(f3), whence);
}
template <typename F0, typename F1, typename F2, typename F3, typename F4>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION promise_detail::TrySeq<F0, F1, F2, F3, F4>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline promise_detail::TrySeq<F0, F1, F2,
F3, F4>
TrySeq(F0 f0, F1 f1, F2 f2, F3 f3, F4 f4, DebugLocation whence = {}) {
return promise_detail::TrySeq<F0, F1, F2, F3, F4>(
std::move(f0), std::move(f1), std::move(f2), std::move(f3), std::move(f4),

@ -94,7 +94,7 @@ class ArenaContextTraits : public BaseArenaContextTraits {
};
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION void DestroyArenaContext(void* p) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline void DestroyArenaContext(void* p) {
ArenaContextType<T>::Destroy(static_cast<T*>(p));
}

@ -24,14 +24,15 @@ namespace grpc_core {
// Call the destructor of p without having to name the type of p.
template <typename T>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION void Destruct(T* p) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline void Destruct(T* p) {
p->~T();
}
// Call the constructor of p without having to name the type of p and forward
// any arguments
template <typename T, typename... Args>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION void Construct(T* p, Args&&... args) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline void Construct(T* p,
Args&&... args) {
new (p) T(std::forward<Args>(args)...);
}

@ -25,7 +25,7 @@
namespace grpc_core {
template <typename To, typename From>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION To DownCast(From* f) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline To DownCast(From* f) {
static_assert(
std::is_base_of<From, typename std::remove_pointer<To>::type>::value,
"DownCast requires a base-to-derived relationship");
@ -39,7 +39,7 @@ GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION To DownCast(From* f) {
}
template <typename To, typename From>
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION To DownCast(From& f) {
GPR_ATTRIBUTE_ALWAYS_INLINE_FUNCTION inline To DownCast(From& f) {
return *DownCast<typename std::remove_reference<To>::type*>(&f);
}

Loading…
Cancel
Save