diff --git a/common/adc_value.h b/common/adc_value.h index 3edb80d..5ae05f8 100644 --- a/common/adc_value.h +++ b/common/adc_value.h @@ -47,7 +47,7 @@ namespace adc struct AdcValueHolderErrorCategory : public std::error_category { AdcValueHolderErrorCategory() : std::error_category() {} - const char* name() const noexcept { return "ADC_VALUEHOLDER_CATEGORY"; } + const char* name() const noexcept { return "ADC_VALUE_HOLDER_CATEGORY"; } std::string message(int ec) const { @@ -273,7 +273,7 @@ public: template - operator UT() + operator UT() const { // using v_t = std::remove_reference_t; // using val_t = std::conditional_t, std::add_pointer_t>, v_t>; @@ -422,6 +422,8 @@ public: AdcValueHolder::setupTrivialConvertFunc>(); } + AdcSerializingValueHolder(const AdcSerializingValueHolder&) = default; + AdcSerializingValueHolder(AdcSerializingValueHolder&&) = default; virtual ~AdcSerializingValueHolder() = default; @@ -474,7 +476,24 @@ public: void deserialize(const SerializedT& sval) { _deserializerWrapper(sval); } - using AdcValueHolder::operator=; + AdcSerializingValueHolder& operator=(const AdcSerializingValueHolder&) = default; + AdcSerializingValueHolder& operator=(AdcSerializingValueHolder&&) = default; + + template + AdcSerializingValueHolder& operator=(UT&& value) + { + AdcValueHolder::operator=(std::forward(value)); + + return *this; + } + + // using AdcValueHolder::operator=; + + // template + // operator UT() + // { + // return AdcValueHolder::operator UT(); + // } }; diff --git a/device/adc_device_attribute.h b/device/adc_device_attribute.h index 4fdd8c2..8a1ae45 100644 --- a/device/adc_device_attribute.h +++ b/device/adc_device_attribute.h @@ -13,10 +13,68 @@ namespace adc { -template -class AdcDeviceAttribute : public AdcSerializingValueHolder +// error codes +enum class AdcDeviceAttributeErrorCode : int { ERROR_OK, ERROR_READ_ONLY, ERROR_WRITE_ONLY }; + +} // namespace adc + + +namespace std { - using base_t = AdcSerializingValueHolder; + +template <> +class is_error_code_enum : public true_type +{ +}; + +} // namespace std + + + +namespace adc +{ + +// error category +struct AdcDeviceAttributeErrorCategory : public std::error_category { + AdcDeviceAttributeErrorCategory() : std::error_category() {} + + const char* name() const noexcept { return "ADC_DEVICE_ATTRIBUTE_CATEGORY"; } + + std::string message(int ec) const + { + AdcDeviceAttributeErrorCode err = static_cast(ec); + + switch (err) { + case AdcDeviceAttributeErrorCode::ERROR_OK: + return "OK"; + case AdcDeviceAttributeErrorCode::ERROR_READ_ONLY: + return "device attribute is read-only"; + case AdcDeviceAttributeErrorCode::ERROR_WRITE_ONLY: + return "device attribute is write-only"; + default: + return "UNKNOWN"; + } + } + + static const AdcDeviceAttributeErrorCategory& get() + { + static const AdcDeviceAttributeErrorCategory constInst; + return constInst; + } +}; + + +inline std::error_code make_error_code(AdcDeviceAttributeErrorCode ec) +{ + return std::error_code(static_cast(ec), AdcDeviceAttributeErrorCategory::get()); +} + + + +template +class AdcDeviceAttribute : protected AdcSerializingValueHolder +{ + typedef AdcSerializingValueHolder base_t; template using ret_value_t = base_t::template ret_value_t; @@ -142,6 +200,9 @@ public: } + AdcDeviceAttribute(const AdcDeviceAttribute&) = default; + AdcDeviceAttribute(AdcDeviceAttribute&&) = default; + virtual ~AdcDeviceAttribute() = default; @@ -149,7 +210,31 @@ public: AccessType accessType() const { return _accessType; } - using base_t::operator=; + template + operator UT() const + { + if (_accessType == WriteOnly) { + throw std::system_error(AdcDeviceAttributeErrorCode::ERROR_WRITE_ONLY); + } + + return base_t::operator UT(); + } + + AdcDeviceAttribute& operator=(const AdcDeviceAttribute&) = default; + AdcDeviceAttribute& operator=(AdcDeviceAttribute&&) = default; + + template + AdcDeviceAttribute& operator=(UT&& value) + { + if (_accessType == ReadOnly) { + throw std::system_error(AdcDeviceAttributeErrorCode::ERROR_READ_ONLY); + } + + base_t::operator=(std::forward(value)); + + return *this; + } + protected: IdentT _ident;