From 67a1b01efc37ba6093b3e3bf41b50f072deb21a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jonathan=20M=C3=BCller?= Date: Thu, 26 Jan 2017 17:34:59 +0100 Subject: [PATCH] Add simple cpp_template_parameter implementations --- include/cppast/cpp_entity_kind.hpp | 3 + include/cppast/cpp_function.hpp | 5 +- include/cppast/cpp_member_variable.hpp | 7 +- include/cppast/cpp_template_parameter.hpp | 105 ++++++++++++++++++++++ include/cppast/cpp_variable.hpp | 6 +- include/cppast/cpp_variable_base.hpp | 12 +-- src/cpp_entity_kind.cpp | 7 ++ src/cpp_template_parameter.cpp | 52 +++++++++++ src/visitor.cpp | 2 + 9 files changed, 187 insertions(+), 12 deletions(-) create mode 100644 include/cppast/cpp_template_parameter.hpp create mode 100644 src/cpp_template_parameter.cpp diff --git a/include/cppast/cpp_entity_kind.hpp b/include/cppast/cpp_entity_kind.hpp index 68f672d..5e8489e 100644 --- a/include/cppast/cpp_entity_kind.hpp +++ b/include/cppast/cpp_entity_kind.hpp @@ -41,6 +41,9 @@ namespace cppast constructor_t, destructor_t, + template_type_parameter_t, + non_type_template_parameter_t, + count, }; diff --git a/include/cppast/cpp_function.hpp b/include/cppast/cpp_function.hpp index afb6a9f..a7458b3 100644 --- a/include/cppast/cpp_function.hpp +++ b/include/cppast/cpp_function.hpp @@ -5,6 +5,7 @@ #ifndef CPPAST_CPP_FUNCTION_HPP_INCLUDED #define CPPAST_CPP_FUNCTION_HPP_INCLUDED +#include #include #include #include @@ -12,7 +13,7 @@ namespace cppast { /// A [cppast::cpp_entity]() modelling a function parameter. - class cpp_function_parameter final : public cpp_variable_base + class cpp_function_parameter final : public cpp_entity, public cpp_variable_base { public: /// \returns A newly created and registered function parameter. @@ -23,7 +24,7 @@ namespace cppast private: cpp_function_parameter(std::string name, std::unique_ptr type, std::unique_ptr def) - : cpp_variable_base(std::move(name), std::move(type), std::move(def)) + : cpp_entity(std::move(name)), cpp_variable_base(std::move(type), std::move(def)) { } diff --git a/include/cppast/cpp_member_variable.hpp b/include/cppast/cpp_member_variable.hpp index 438cc73..ed1a440 100644 --- a/include/cppast/cpp_member_variable.hpp +++ b/include/cppast/cpp_member_variable.hpp @@ -5,12 +5,13 @@ #ifndef CPPAST_CPP_MEMBER_VARIABLE_HPP_INCLUDED #define CPPAST_CPP_MEMBER_VARIABLE_HPP_INCLUDED +#include #include namespace cppast { /// Base class for all kinds of member variables. - class cpp_member_variable_base : public cpp_variable_base + class cpp_member_variable_base : public cpp_entity, public cpp_variable_base { public: /// \returns Whether or not the member variable is declared `mutable`. @@ -22,7 +23,9 @@ namespace cppast protected: cpp_member_variable_base(std::string name, std::unique_ptr type, std::unique_ptr def, bool is_mutable) - : cpp_variable_base(std::move(name), std::move(type), std::move(def)), mutable_(is_mutable) + : cpp_entity(std::move(name)), + cpp_variable_base(std::move(type), std::move(def)), + mutable_(is_mutable) { } diff --git a/include/cppast/cpp_template_parameter.hpp b/include/cppast/cpp_template_parameter.hpp new file mode 100644 index 0000000..8217b98 --- /dev/null +++ b/include/cppast/cpp_template_parameter.hpp @@ -0,0 +1,105 @@ +// Copyright (C) 2017 Jonathan Müller +// This file is subject to the license terms in the LICENSE file +// found in the top-level directory of this distribution. + +#ifndef CPPAST_CPP_TEMPLATE_PARAMETER_HPP_INCLUDED +#define CPPAST_CPP_TEMPLATE_PARAMETER_HPP_INCLUDED + +#include +#include + +namespace cppast +{ + /// Base class for all entities modelling a template parameter of some kind. + class cpp_template_parameter : public cpp_entity + { + public: + /// \returns Whether or not the parameter is variadic. + bool is_variadic() const noexcept + { + return variadic_; + } + + protected: + cpp_template_parameter(std::string name, bool variadic) + : cpp_entity(std::move(name)), variadic_(variadic) + { + } + + private: + bool variadic_; + }; + + /// The kind of keyword used in a template parameter. + enum class cpp_template_keyword + { + keyword_class, + keyword_typename + }; + + /// \returns The string associated of the keyword. + const char* to_string(cpp_template_keyword kw) noexcept; + + /// A [cppast::cpp_entity]() modelling a C++ template type parameter. + class cpp_template_type_parameter final : public cpp_template_parameter + { + public: + /// \returns A newly created and registered template type parameter. + /// \notes The `default_type` may be `nullptr` in which case the parameter has no default. + static std::unique_ptr build( + const cpp_entity_index& idx, cpp_entity_id id, std::string name, + cpp_template_keyword kw, bool variadic, + std::unique_ptr default_type = nullptr); + + /// \returns A [ts::optional_ref]() to the default type. + type_safe::optional_ref default_type() const noexcept + { + return type_safe::opt_cref(default_type_.get()); + } + + /// \returns The keyword used in the template parameter. + cpp_template_keyword keyword() const noexcept + { + return keyword_; + } + + private: + cpp_template_type_parameter(std::string name, cpp_template_keyword kw, bool variadic, + std::unique_ptr default_type) + : cpp_template_parameter(std::move(name), variadic), + default_type_(std::move(default_type)), + keyword_(kw) + { + } + + cpp_entity_kind do_get_entity_kind() const noexcept override; + + std::unique_ptr default_type_; + cpp_template_keyword keyword_; + }; + + /// A [cppast::cpp_entity]() modelling a non-type template parameter. + class cpp_non_type_template_parameter final : public cpp_template_parameter, + public cpp_variable_base + { + public: + /// \returns A newly created and registered non type template parameter. + /// \notes The `default_value` may be `nullptr` in which case the parameter has no default. + static std::unique_ptr build( + const cpp_entity_index& idx, cpp_entity_id id, std::string name, + std::unique_ptr type, bool is_variadic, + std::unique_ptr default_value = nullptr); + + private: + cpp_non_type_template_parameter(std::string name, std::unique_ptr type, + bool variadic, std::unique_ptr def) + : cpp_template_parameter(std::move(name), variadic), + cpp_variable_base(std::move(type), std::move(def)) + { + } + + cpp_entity_kind do_get_entity_kind() const noexcept override; + }; +} // namespace cppast + +#endif // CPPAST_CPP_TEMPLATE_PARAMETER_HPP_INCLUDED diff --git a/include/cppast/cpp_variable.hpp b/include/cppast/cpp_variable.hpp index 6e3663d..631cb95 100644 --- a/include/cppast/cpp_variable.hpp +++ b/include/cppast/cpp_variable.hpp @@ -5,6 +5,7 @@ #ifndef CPPAST_CPP_VARIABLE_HPP_INCLUDED #define CPPAST_CPP_VARIABLE_HPP_INCLUDED +#include #include #include @@ -13,7 +14,7 @@ namespace cppast /// A [cppast::cpp_entity]() modelling a C++ variable. /// \notes This is not a member variable, /// use [cppast::cpp_member_variable]() for that. - class cpp_variable final : public cpp_variable_base + class cpp_variable final : public cpp_entity, public cpp_variable_base { public: /// \returns A newly created and registered variable. @@ -39,7 +40,8 @@ namespace cppast cpp_variable(std::string name, std::unique_ptr type, std::unique_ptr def, cpp_storage_specifiers spec, bool is_constexpr) - : cpp_variable_base(std::move(name), std::move(type), std::move(def)), + : cpp_entity(std::move(name)), + cpp_variable_base(std::move(type), std::move(def)), storage_(spec), is_constexpr_(is_constexpr) { diff --git a/include/cppast/cpp_variable_base.hpp b/include/cppast/cpp_variable_base.hpp index 98b54c4..394c374 100644 --- a/include/cppast/cpp_variable_base.hpp +++ b/include/cppast/cpp_variable_base.hpp @@ -5,17 +5,16 @@ #ifndef CPPAST_CPP_VARIABLE_BASE_HPP_INCLUDED #define CPPAST_CPP_VARIABLE_BASE_HPP_INCLUDED -#include #include #include namespace cppast { - /// Base class for all [cppast::cpp_entity]() modelling some kind of variable. + /// Additional base class for all [cppast::cpp_entity]() modelling some kind of variable. /// /// Examples are [cppast::cpp_variable]() or [cppast::cpp_function_parameter](), /// or anything that is name/type/default-value triple. - class cpp_variable_base : public cpp_entity + class cpp_variable_base { public: /// \returns A reference to the [cppast::cpp_type]() of the variable. @@ -31,12 +30,13 @@ namespace cppast } protected: - cpp_variable_base(std::string name, std::unique_ptr type, - std::unique_ptr def) - : cpp_entity(std::move(name)), type_(std::move(type)), default_(std::move(def)) + cpp_variable_base(std::unique_ptr type, std::unique_ptr def) + : type_(std::move(type)), default_(std::move(def)) { } + ~cpp_variable_base() noexcept = default; + private: std::unique_ptr type_; std::unique_ptr default_; diff --git a/src/cpp_entity_kind.cpp b/src/cpp_entity_kind.cpp index 4577978..f3edc00 100644 --- a/src/cpp_entity_kind.cpp +++ b/src/cpp_entity_kind.cpp @@ -60,6 +60,11 @@ const char* cppast::to_string(cpp_entity_kind kind) noexcept case cpp_entity_kind::destructor_t: return "destructor"; + case cpp_entity_kind::template_type_parameter_t: + return "template type parameter"; + case cpp_entity_kind::non_type_template_parameter_t: + return "non type template parameter"; + case cpp_entity_kind::count: break; } @@ -94,6 +99,8 @@ bool cppast::is_type(cpp_entity_kind kind) noexcept case cpp_entity_kind::conversion_op_t: case cpp_entity_kind::constructor_t: case cpp_entity_kind::destructor_t: + case cpp_entity_kind::template_type_parameter_t: + case cpp_entity_kind::non_type_template_parameter_t: case cpp_entity_kind::count: break; } diff --git a/src/cpp_template_parameter.cpp b/src/cpp_template_parameter.cpp new file mode 100644 index 0000000..e1248a7 --- /dev/null +++ b/src/cpp_template_parameter.cpp @@ -0,0 +1,52 @@ +// Copyright (C) 2017 Jonathan Müller +// This file is subject to the license terms in the LICENSE file +// found in the top-level directory of this distribution. + +#include +#include + +using namespace cppast; + +const char* cppast::to_string(cpp_template_keyword kw) noexcept +{ + switch (kw) + { + case cpp_template_keyword::keyword_class: + return "class"; + case cpp_template_keyword::keyword_typename: + return "typename"; + } + + return "should not get here"; +} + +std::unique_ptr cpp_template_type_parameter::build( + const cpp_entity_index& idx, cpp_entity_id id, std::string name, cpp_template_keyword kw, + bool variadic, std::unique_ptr default_type) +{ + std::unique_ptr result( + new cpp_template_type_parameter(std::move(name), kw, variadic, std::move(default_type))); + idx.register_entity(std::move(id), type_safe::cref(*result)); + return result; +} + +cpp_entity_kind cpp_template_type_parameter::do_get_entity_kind() const noexcept +{ + return cpp_entity_kind::template_type_parameter_t; +} + +std::unique_ptr cpp_non_type_template_parameter::build( + const cpp_entity_index& idx, cpp_entity_id id, std::string name, std::unique_ptr type, + bool is_variadic, std::unique_ptr default_value) +{ + std::unique_ptr result( + new cpp_non_type_template_parameter(std::move(name), std::move(type), is_variadic, + std::move(default_value))); + idx.register_entity(std::move(id), type_safe::cref(*result)); + return result; +} + +cpp_entity_kind cpp_non_type_template_parameter::do_get_entity_kind() const noexcept +{ + return cpp_entity_kind::non_type_template_parameter_t; +} diff --git a/src/visitor.cpp b/src/visitor.cpp index 6b2a3bb..28f7421 100644 --- a/src/visitor.cpp +++ b/src/visitor.cpp @@ -70,6 +70,8 @@ bool detail::visit(const cpp_entity& e, detail::visitor_callback_t cb, void* fun case cpp_entity_kind::bitfield_t: case cpp_entity_kind::function_parameter_t: case cpp_entity_kind::destructor_t: + case cpp_entity_kind::template_type_parameter_t: + case cpp_entity_kind::non_type_template_parameter_t: return cb(functor, e, visitor_info::leaf_entity); case cpp_entity_kind::count: