| // Copyright 2016 The Chromium Authors. All rights reserved. | |
| // Use of this source code is governed by a BSD-style license that can be | |
| // found in the LICENSE file. | |
| #ifndef {{"_".join(config.protocol.namespace)}}_Maybe_h | |
| #define {{"_".join(config.protocol.namespace)}}_Maybe_h | |
| // This macro allows to test for the version of the GNU C++ compiler. | |
| // Note that this also applies to compilers that masquerade as GCC, | |
| // for example clang and the Intel C++ compiler for Linux. | |
| // Use like: | |
| // #if IP_GNUC_PREREQ(4, 3, 1) | |
| // ... | |
| // #endif | |
| #if defined(__GNUC__) && defined(__GNUC_MINOR__) && defined(__GNUC_PATCHLEVEL__) | |
| #define IP_GNUC_PREREQ(major, minor, patchlevel) \ | |
| ((__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) >= \ | |
| ((major)*10000 + (minor)*100 + (patchlevel))) | |
| #elif defined(__GNUC__) && defined(__GNUC_MINOR__) | |
| #define IP_GNUC_PREREQ(major, minor, patchlevel) \ | |
| ((__GNUC__ * 10000 + __GNUC_MINOR__ * 100) >= \ | |
| ((major)*10000 + (minor)*100 + (patchlevel))) | |
| #else | |
| #define IP_GNUC_PREREQ(major, minor, patchlevel) 0 | |
| #endif | |
| #if defined(__mips64) | |
| #define IP_TARGET_ARCH_MIPS64 1 | |
| #elif defined(__MIPSEB__) || defined(__MIPSEL__) | |
| #define IP_TARGET_ARCH_MIPS 1 | |
| #endif | |
| // Allowing the use of noexcept by removing the keyword on older compilers that | |
| // do not support adding noexcept to default members. | |
| #if ((IP_GNUC_PREREQ(4, 9, 0) && !defined(IP_TARGET_ARCH_MIPS) && \ | |
| !defined(IP_TARGET_ARCH_MIPS64)) || \ | |
| (defined(__clang__) && __cplusplus > 201300L)) | |
| #define IP_NOEXCEPT noexcept | |
| #else | |
| #define IP_NOEXCEPT | |
| #endif | |
| //#include "Forward.h" | |
| {% for namespace in config.protocol.namespace %} | |
| namespace {{namespace}} { | |
| {% endfor %} | |
| template<typename T> | |
| class Maybe { | |
| public: | |
| Maybe() : m_value() { } | |
| Maybe(std::unique_ptr<T> value) : m_value(std::move(value)) { } | |
| Maybe(Maybe&& other) IP_NOEXCEPT : m_value(std::move(other.m_value)) {} | |
| void operator=(std::unique_ptr<T> value) { m_value = std::move(value); } | |
| T* fromJust() const { DCHECK(m_value); return m_value.get(); } | |
| T* fromMaybe(T* defaultValue) const { return m_value ? m_value.get() : defaultValue; } | |
| bool isJust() const { return !!m_value; } | |
| std::unique_ptr<T> takeJust() { DCHECK(m_value); return std::move(m_value); } | |
| private: | |
| std::unique_ptr<T> m_value; | |
| }; | |
| template<typename T> | |
| class MaybeBase { | |
| public: | |
| MaybeBase() : m_isJust(false) { } | |
| MaybeBase(T value) : m_isJust(true), m_value(value) { } | |
| MaybeBase(MaybeBase&& other) IP_NOEXCEPT | |
| : m_isJust(other.m_isJust), | |
| m_value(std::move(other.m_value)) {} | |
| void operator=(T value) { m_value = value; m_isJust = true; } | |
| T fromJust() const { DCHECK(m_isJust); return m_value; } | |
| T fromMaybe(const T& defaultValue) const { return m_isJust ? m_value : defaultValue; } | |
| bool isJust() const { return m_isJust; } | |
| T takeJust() { DCHECK(m_isJust); return m_value; } | |
| protected: | |
| bool m_isJust; | |
| T m_value; | |
| }; | |
| template<> | |
| class Maybe<bool> : public MaybeBase<bool> { | |
| public: | |
| Maybe() { } | |
| Maybe(bool value) : MaybeBase(value) { } | |
| Maybe(Maybe&& other) IP_NOEXCEPT : MaybeBase(std::move(other)) {} | |
| using MaybeBase::operator=; | |
| }; | |
| template<> | |
| class Maybe<int> : public MaybeBase<int> { | |
| public: | |
| Maybe() { } | |
| Maybe(int value) : MaybeBase(value) { } | |
| Maybe(Maybe&& other) IP_NOEXCEPT : MaybeBase(std::move(other)) {} | |
| using MaybeBase::operator=; | |
| }; | |
| template<> | |
| class Maybe<double> : public MaybeBase<double> { | |
| public: | |
| Maybe() { } | |
| Maybe(double value) : MaybeBase(value) { } | |
| Maybe(Maybe&& other) IP_NOEXCEPT : MaybeBase(std::move(other)) {} | |
| using MaybeBase::operator=; | |
| }; | |
| template<> | |
| class Maybe<String> : public MaybeBase<String> { | |
| public: | |
| Maybe() { } | |
| Maybe(const String& value) : MaybeBase(value) { } | |
| Maybe(Maybe&& other) IP_NOEXCEPT : MaybeBase(std::move(other)) {} | |
| using MaybeBase::operator=; | |
| }; | |
| {% for namespace in config.protocol.namespace %} | |
| } // namespace {{namespace}} | |
| {% endfor %} | |
| #undef IP_GNUC_PREREQ | |
| #undef IP_TARGET_ARCH_MIPS64 | |
| #undef IP_TARGET_ARCH_MIPS | |
| #undef IP_NOEXCEPT | |
| #endif // !defined({{"_".join(config.protocol.namespace)}}_Maybe_h) |