Skip to main content

reflection.h File

C++ header file with declarations for the µTest++ reflection utilities. More...

Included Headers

#include <string_view> #include "inlines/reflection-inlines.h"

Namespaces Index

namespacemicro_os_plus

The primary namespace for the µOS++ framework. More...

namespacemicro_test_plus

Primary namespace for the µTest++ testing framework. More...

namespacereflection

Reflection utilities for the µTest++ testing framework. More...

Classes Index

classsource_location

Local implementation of source location information for diagnostics. More...

Functions Index

const char *short_name (const char *name) noexcept

Extract a short type or function name from a fully qualified name. More...

template <class T>
constexpr std::string_viewtype_name (void)

Extract the type name from the __PRETTY_FUNCTION__ macro. More...

Description

C++ header file with declarations for the µTest++ reflection utilities.

This header provides the declarations for the reflection utilities used within the µTest++ framework. It defines interfaces for obtaining source location information and extracting type names at compile time, supporting advanced diagnostics and reporting capabilities.

The reflection utilities include a local implementation of source_location for environments lacking C++20 standard support, as well as functions for extracting concise type names using compiler-specific macros such as __PRETTY_FUNCTION__. These facilities enable precise identification of code locations and types in test reports, enhancing the clarity and professionalism of diagnostic output.

All definitions reside within the micro_os_plus::micro_test_plus::reflection namespace, ensuring clear separation from user code and minimising the risk of naming conflicts.

The header files are organised within the include/micro-os-plus/micro-test-plus folder to maintain a structured and modular codebase.

This file is intended solely for internal use within the framework and should not be included directly by user code.

Functions

short_name()

const char * micro_os_plus::micro_test_plus::reflection::short_name (const char * name)
noexcept

Extract a short type or function name from a fully qualified name.

Parameters
name

The fully qualified name as a C-string.

Returns

A pointer to the short name within the input string.

This function extracts the short name from a given file path by locating the final folder separator ('/'). If a separator is found, it returns a pointer to the character immediately following it, effectively providing the file or folder name. If no separator is present, the original input string is returned. This utility is useful for reporting concise file or folder names in test output.

Definition at line 74 of file reflection.cpp.

74 short_name (const char* name) noexcept
75 {
76#if defined(__GNUC__)
77#pragma GCC diagnostic push
78
79#if defined(__clang__)
80#pragma clang diagnostic ignored "-Wunsafe-buffer-usage"
81#endif // defined(__clang__)
82#endif // defined(__GNUC__)
83
84 const char* p = strrchr (name, '/');
85 if (p != nullptr)
86 return p + 1;
87 else
88 return name;
89
90#if defined(__GNUC__)
91#pragma GCC diagnostic pop
92#endif // defined(__GNUC__)
93 }

Referenced by micro_os_plus::micro_test_plus::runner::abort, micro_os_plus::micro_test_plus::reporter_human::output_fail_prefix_ and micro_os_plus::micro_test_plus::reporter_tap::output_fail_suffix_.

type_name()

template <class T>
std::string_view micro_os_plus::micro_test_plus::reflection::type_name (void)
nodiscard constexpr

Extract the type name from the __PRETTY_FUNCTION__ macro.

This function template parses the compiler-specific __PRETTY_FUNCTION__ macro to extract a concise type name for the template parameter T.

Rather than relying on fixed character offsets (which are fragile across compiler versions and namespace changes), the implementation searches for well-known marker characters in the function signature string:

  • Clang formats the signature as "... [T = <typename>]", so the type name lies between the last '[' (skipping "[T = ") and the last ']'.
  • GCC formats the signature as "... [with T = <typename>]", so the type name lies between the last '=' (skipping the trailing space) and the last ']'.

This approach is resilient to namespace renaming, namespace nesting changes, and compiler format updates.

Template Parameters
T

The type whose name is to be extracted.

Parameters

None.

Returns

A std::string_view containing the extracted type name.

Definition at line 146 of file reflection-inlines.h.

146 type_name (void) -> std::string_view
147 {
148 const std::string_view sv = __PRETTY_FUNCTION__;
149#if defined(__clang__)
150 // Clang: "... [T = <typename>]"
151 // rfind('[') locates the opening bracket of "[T = ...]".
152 const auto start = sv.rfind ('[') + 5; // skip "[T = "
153 const auto end = sv.rfind (']');
154#elif defined(__GNUC__)
155 // GCC: "... [with T = <typename>]" or, on some versions,
156 // "... [with T = <typename>; std::string_view = ...]"
157 // Search for "T = " explicitly to avoid landing on a later '='.
158 const auto t_eq = sv.find ("T = ");
159 const auto start = t_eq + 4; // skip "T = "
160 const auto semi = sv.find (';', start);
161 const auto end
162 = (semi != std::string_view::npos) ? semi : sv.rfind (']');
163#else
164// Note: MSVC uses __FUNCSIG__ instead of __PRETTY_FUNCTION__.
165// MSVC is not a supported target for this framework.
166#error "Unsupported compiler"
167#endif // defined(__clang__) || defined(__GNUC__)
168 return sv.substr (start, end - start);
169 }

Referenced by micro_os_plus::micro_test_plus::detail::expression_formatter::operator<<.

File Listing

The file content with the documentation metadata removed is:

1/*
2 * This file is part of the µOS++ project (https://micro-os-plus.github.io/).
3 * Copyright (c) 2021-2026 Liviu Ionescu. All rights reserved.
4 *
5 * Permission to use, copy, modify, and/or distribute this software for any
6 * purpose is hereby granted, under the terms of the MIT license.
7 *
8 * If a copy of the license was not distributed with this file, it can be
9 * obtained from https://opensource.org/licenses/mit.
10 *
11 * Major parts of the code are inspired from v1.1.8 of the Boost UT project,
12 * released under the terms of the Boost Version 1 Software License,
13 * which can be obtained from https://www.boost.org/LICENSE_1_0.txt.
14 */
15
16// ----------------------------------------------------------------------------
17
47
48#ifndef MICRO_OS_PLUS_MICRO_TEST_PLUS_REFLECTION_H_
49#define MICRO_OS_PLUS_MICRO_TEST_PLUS_REFLECTION_H_
50
51// ----------------------------------------------------------------------------
52
53#if defined(__cplusplus)
54
55// ----------------------------------------------------------------------------
56
57#if __has_include("micro-os-plus/project-config.h")
58#include "micro-os-plus/project-config.h"
59#endif // __has_include("micro-os-plus/project-config.h")
60
61#if __has_include("micro-os-plus/micro-test-plus-defines.h")
62#include "micro-os-plus/micro-test-plus-defines.h"
63#endif // __has_include("micro-os-plus/micro-test-plus-defines.h")
64
65#include <string_view>
66
67#if defined(__cpp_lib_source_location)
68#include <source_location>
69#endif // defined(__cpp_lib_source_location)
70
71// ----------------------------------------------------------------------------
72
73#if defined(__GNUC__)
74#pragma GCC diagnostic push
75
76#pragma GCC diagnostic ignored "-Wpadded"
77#pragma GCC diagnostic ignored "-Waggregate-return"
78#if defined(__clang__)
79#pragma clang diagnostic ignored "-Wc++98-compat"
80#endif // defined(__clang__)
81#endif // defined(__GNUC__)
82
83// =============================================================================
84
86{
87 // --------------------------------------------------------------------------
88
106 namespace reflection
107 {
108 // ------------------------------------------------------------------------
109
110#if defined(__cpp_lib_source_location)
111
125 using source_location = std::source_location;
126
127#else
128
150 {
151 public:
159 [[nodiscard]] static constexpr source_location
160 current (
161#if (__has_builtin(__builtin_FILE) and __has_builtin(__builtin_LINE))
162 const char* file = __builtin_FILE (),
163 unsigned int line = __builtin_LINE ()
164#else
165 const char* file = "unknown", unsigned int line = {}
166#endif // (__has_builtin(__builtin_FILE) and __has_builtin(__builtin_LINE))
167 ) noexcept;
168
176 [[nodiscard]] constexpr auto
177 file_name (void) const noexcept;
178
186 [[nodiscard]] constexpr auto
187 line (void) const noexcept;
188
189 private:
193 const char* file_{ "unknown" };
194
198 unsigned int line_{};
199 };
200
201#endif // defined(__cpp_lib_source_location)
202
210 const char*
211 short_name (const char* name) noexcept;
212
222 template <class T>
223 [[nodiscard]] constexpr auto
224 type_name (void) -> std::string_view;
225
226 // ------------------------------------------------------------------------
227 } // namespace reflection
228
229 // --------------------------------------------------------------------------
230} // namespace micro_os_plus::micro_test_plus
231
232#if defined(__GNUC__)
233#pragma GCC diagnostic pop
234#endif // defined(__GNUC__)
235
236// ----------------------------------------------------------------------------
237
238#endif // defined(__cplusplus)
239
240// ============================================================================
241// Templates, inlines & constexpr implementations.
242
244
245// ----------------------------------------------------------------------------
246
247#endif // MICRO_OS_PLUS_MICRO_TEST_PLUS_REFLECTION_H_
248
249// ----------------------------------------------------------------------------

Generated via doxygen2docusaurus 2.2.2 by Doxygen 1.17.0.