Skip to content

Commit

Permalink
Mark RTTI methods as const / pure, so compiler could optimize subsequ…
Browse files Browse the repository at this point in the history
…ent calls, if necessary. (#5049)

* Mark RTTI methods as const / pure, so compiler could optimize subsequent calls, if necessary.

Signed-off-by: Anton Korobeynikov <[email protected]>

* Add some explanation to RTTI boilerplate

Signed-off-by: Anton Korobeynikov <[email protected]>

---------

Signed-off-by: Anton Korobeynikov <[email protected]>
  • Loading branch information
asl authored Dec 13, 2024
1 parent b0f775c commit 5dc7f87
Showing 1 changed file with 20 additions and 12 deletions.
32 changes: 20 additions & 12 deletions lib/rtti.h
Original file line number Diff line number Diff line change
Expand Up @@ -296,18 +296,26 @@ struct Base {
}; \
DECLARE_TYPEINFO_COMMON(T, ##__VA_ARGS__)

#define DECLARE_TYPEINFO_COMMON(T, ...) \
public: \
static constexpr T *rttiEnabledMarker(T *); \
using TypeInfo = P4::RTTI::TypeInfo<T, ##__VA_ARGS__>; \
[[nodiscard]] P4::RTTI::TypeId typeId() const noexcept override { return TypeInfo::id(); } \
[[nodiscard]] bool isA(P4::RTTI::TypeId typeId) const noexcept override { \
return TypeInfo::isA(typeId); \
} \
\
protected: \
[[nodiscard]] const void *toImpl(P4::RTTI::TypeId typeId) const noexcept override { \
return TypeInfo::isA(typeId) ? TypeInfo::dyn_cast(typeId, this) : nullptr; \
// Common typeinfo boilerplate methods. Note that they are marked pure / const, so consecutive
// calls to is<> / to<> on the same pointer could be eliminated by a compiler.
// - typeId() / isA are const as they do not access any global state, they
// always return the same value (for same input arguments)
// - toImpl() is pure. It only access global state via its arguments (this pointer). So for
// the same `this` the result is also the same.
#define DECLARE_TYPEINFO_COMMON(T, ...) \
public: \
static constexpr T *rttiEnabledMarker(T *); \
using TypeInfo = P4::RTTI::TypeInfo<T, ##__VA_ARGS__>; \
[[nodiscard, gnu::const]] P4::RTTI::TypeId typeId() const noexcept override { \
return TypeInfo::id(); \
} \
[[nodiscard, gnu::const]] bool isA(P4::RTTI::TypeId typeId) const noexcept override { \
return TypeInfo::isA(typeId); \
} \
\
protected: \
[[nodiscard, gnu::pure]] const void *toImpl(P4::RTTI::TypeId typeId) const noexcept override { \
return TypeInfo::isA(typeId) ? TypeInfo::dyn_cast(typeId, this) : nullptr; \
}

#endif /* LIB_RTTI_H_ */

0 comments on commit 5dc7f87

Please sign in to comment.