libabigail
Loading...
Searching...
No Matches
abg-cxx-compat.h
Go to the documentation of this file.
1// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
2// -*- Mode: C++ -*-
3//
4// Copyright (C) 2019-2024 Google, Inc.
5
6/// @file
7
8#ifndef __ABG_CXX_COMPAT_H
9#define __ABG_CXX_COMPAT_H
10
11// C++17 support (via custom implementations if compiled with earlier standard)
12
13#if __cplusplus >= 201703L
14
15#include <optional>
16
17#else
18
19#include <stdexcept> // for throwing std::runtime_error("bad_optional_access")
20
21#endif
22
23namespace abg_compat {
24
25#if __cplusplus >= 201703L
26
27using std::optional;
28
29#else
30
31// <optional>
32
33/// Simplified implementation of std::optional just enough to be used as a
34/// replacement for our purposes and when compiling with pre C++17.
35///
36/// The implementation intentionally does not support a whole lot of features
37/// to minimize the maintenance effort with this.
38template <typename T> class optional
39{
40 bool has_value_;
41 T value_;
42
43public:
44 optional() : has_value_(false), value_() {}
45 optional(const T& value) : has_value_(true), value_(value) {}
46
47 bool
48 has_value() const noexcept
49 {
50 return has_value_;
51 }
52
53 const T&
54 value() const
55 {
56 if (!has_value_)
57 throw std::runtime_error("bad_optional_access");
58 return value_;
59 }
60
61 const T
62 value_or(const T& default_value) const
63 {
64 if (!has_value_)
65 return default_value;
66 return value_;
67 }
68
69 const T&
70 operator*() const& noexcept
71 { return value_; }
72
73 T&
74 operator*() & noexcept
75 { return value_; }
76
77 const T*
78 operator->() const noexcept
79 { return &value_; }
80
81 T*
82 operator->() noexcept
83 { return &value_; }
84
86 operator=(const T& value)
87 {
88 has_value_ = true;
89 value_ = value;
90 return *this;
91 }
92
93 explicit operator bool() const noexcept { return has_value(); }
94};
95
96template <typename T, typename U>
97bool
98operator==(const optional<T>& lhs, const optional<U>& rhs)
99{
100 if (!lhs.has_value() && !rhs.has_value())
101 return true;
102 if (!lhs.has_value() || !rhs.has_value())
103 return false;
104 return lhs.value() == rhs.value();
105}
106
107template <typename T, typename U>
108bool
109operator!=(const optional<T>& lhs, const optional<U>& rhs)
110{
111 return !(lhs == rhs);
112}
113
114#endif
115}
116
117#endif // __ABG_CXX_COMPAT_H
Simplified implementation of std::optional just enough to be used as a replacement for our purposes a...