#![allow(
clippy::all,
clippy::pedantic,
dead_code,
unreachable_pub,
unused_imports
)]
use crate::datatypes::SemanticTagStruct;
use crate::error::ClusterError;
use crate::types::Nullable;
use matter_codec::{ContainerKind, Element, Tag, TlvReader, TlvWriter, Value};
pub const CLUSTER_ID: u32 = 0x0090;
pub const CLUSTER_REVISION: u16 = 3;
pub mod command_id {}
pub mod attribute_id {
pub const POWER_MODE: u32 = 0x0000;
pub const NUMBER_OF_MEASUREMENT_TYPES: u32 = 0x0001;
pub const ACCURACY: u32 = 0x0002;
pub const RANGES: u32 = 0x0003;
pub const VOLTAGE: u32 = 0x0004;
pub const ACTIVE_CURRENT: u32 = 0x0005;
pub const REACTIVE_CURRENT: u32 = 0x0006;
pub const APPARENT_CURRENT: u32 = 0x0007;
pub const ACTIVE_POWER: u32 = 0x0008;
pub const REACTIVE_POWER: u32 = 0x0009;
pub const APPARENT_POWER: u32 = 0x000A;
pub const RMS_VOLTAGE: u32 = 0x000B;
pub const RMS_CURRENT: u32 = 0x000C;
pub const RMS_POWER: u32 = 0x000D;
pub const FREQUENCY: u32 = 0x000E;
pub const HARMONIC_CURRENTS: u32 = 0x000F;
pub const HARMONIC_PHASES: u32 = 0x0010;
pub const POWER_FACTOR: u32 = 0x0011;
pub const NEUTRAL_CURRENT: u32 = 0x0012;
}
bitflags::bitflags! {
#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
pub struct Feature: u32 {
const DIRC = 1 << 0;
const ALTC = 1 << 1;
const POLY = 1 << 2;
const HARM = 1 << 3;
const PWRQ = 1 << 4;
}
}
#[derive(Clone, Debug, PartialEq)]
#[non_exhaustive]
pub struct HarmonicMeasurementStruct {
pub order: u8,
pub measurement: Nullable<i64>,
}
#[derive(Clone, Debug, PartialEq)]
#[non_exhaustive]
pub struct MeasurementAccuracyRangeStruct {
pub range_min: i64,
pub range_max: i64,
pub percent_max: Option<u16>,
pub percent_min: Option<u16>,
pub percent_typical: Option<u16>,
pub fixed_max: Option<u64>,
pub fixed_min: Option<u64>,
pub fixed_typical: Option<u64>,
}
#[derive(Clone, Debug, PartialEq)]
#[non_exhaustive]
pub struct MeasurementAccuracyStruct {
pub measurement_type: MeasurementTypeEnum,
pub measured: bool,
pub min_measured_value: i64,
pub max_measured_value: i64,
pub accuracy_ranges: Vec<MeasurementAccuracyRangeStruct>,
}
#[derive(Clone, Debug, PartialEq)]
#[non_exhaustive]
pub struct MeasurementRangeStruct {
pub measurement_type: MeasurementTypeEnum,
pub min: i64,
pub max: i64,
pub start_timestamp: Option<u32>,
pub end_timestamp: Option<u32>,
pub min_timestamp: Option<u32>,
pub max_timestamp: Option<u32>,
pub start_systime: Option<u64>,
pub end_systime: Option<u64>,
pub min_systime: Option<u64>,
pub max_systime: Option<u64>,
}
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum MeasurementTypeEnum {
Unspecified,
Voltage,
ActiveCurrent,
ReactiveCurrent,
ApparentCurrent,
ActivePower,
ReactivePower,
ApparentPower,
RmsVoltage,
RmsCurrent,
RmsPower,
Frequency,
PowerFactor,
NeutralCurrent,
ElectricalEnergy,
ReactiveEnergy,
ApparentEnergy,
Unknown(u16),
}
impl MeasurementTypeEnum {
#[must_use]
pub fn from_raw(v: u16) -> Self {
match v {
0 => Self::Unspecified,
1 => Self::Voltage,
2 => Self::ActiveCurrent,
3 => Self::ReactiveCurrent,
4 => Self::ApparentCurrent,
5 => Self::ActivePower,
6 => Self::ReactivePower,
7 => Self::ApparentPower,
8 => Self::RmsVoltage,
9 => Self::RmsCurrent,
10 => Self::RmsPower,
11 => Self::Frequency,
12 => Self::PowerFactor,
13 => Self::NeutralCurrent,
14 => Self::ElectricalEnergy,
15 => Self::ReactiveEnergy,
16 => Self::ApparentEnergy,
other => Self::Unknown(other),
}
}
#[must_use]
pub fn to_raw(self) -> u16 {
match self {
Self::Unspecified => 0,
Self::Voltage => 1,
Self::ActiveCurrent => 2,
Self::ReactiveCurrent => 3,
Self::ApparentCurrent => 4,
Self::ActivePower => 5,
Self::ReactivePower => 6,
Self::ApparentPower => 7,
Self::RmsVoltage => 8,
Self::RmsCurrent => 9,
Self::RmsPower => 10,
Self::Frequency => 11,
Self::PowerFactor => 12,
Self::NeutralCurrent => 13,
Self::ElectricalEnergy => 14,
Self::ReactiveEnergy => 15,
Self::ApparentEnergy => 16,
Self::Unknown(v) => v,
}
}
}
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum PowerModeEnum {
Unknown,
Dc,
Ac,
Unrecognized(u8),
}
impl PowerModeEnum {
#[must_use]
pub fn from_raw(v: u8) -> Self {
match v {
0 => Self::Unknown,
1 => Self::Dc,
2 => Self::Ac,
other => Self::Unrecognized(other),
}
}
#[must_use]
pub fn to_raw(self) -> u8 {
match self {
Self::Unknown => 0,
Self::Dc => 1,
Self::Ac => 2,
Self::Unrecognized(v) => v,
}
}
}
impl HarmonicMeasurementStruct {
pub fn decode_from(r: &mut TlvReader<'_>) -> Result<Self, ClusterError> {
let mut f_order: Option<u8> = None;
let mut f_measurement: Option<Nullable<i64>> = None;
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::Scalar {
tag: Tag::Context(0),
value: Value::Uint(v),
}) => {
f_order =
Some(u8::try_from(v).map_err(|_| ClusterError::InvalidLength("Order"))?)
}
Some(Element::Scalar {
tag: Tag::Context(1),
value: Value::Null,
}) => f_measurement = Some(Nullable::Null),
Some(Element::Scalar {
tag: Tag::Context(1),
value: Value::Int(v),
}) => {
f_measurement = Some(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("Measurement"))?,
))
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Self {
order: f_order.ok_or(ClusterError::MissingField("Order"))?,
measurement: f_measurement.ok_or(ClusterError::MissingField("Measurement"))?,
})
}
pub fn decode(tlv: &[u8]) -> Result<Self, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "HarmonicMeasurementStruct",
})
}
}
Self::decode_from(&mut r)
}
#[allow(clippy::expect_used)] pub fn write_fields(&self, w: &mut TlvWriter<'_>) {
w.put_uint(Tag::Context(0), u64::from(self.order))
.expect("infallible: vec writer");
match &self.measurement {
Nullable::Null => w.put_null(Tag::Context(1)).expect("infallible: vec writer"),
Nullable::Value(measurement) => {
w.put_int(Tag::Context(1), i64::from(*measurement))
.expect("infallible: vec writer");
}
}
}
#[must_use]
#[allow(clippy::expect_used)] pub fn encode(&self) -> Vec<u8> {
let mut buf = Vec::new();
let mut w = TlvWriter::new(&mut buf);
w.start_structure(Tag::Anonymous)
.expect("infallible: vec writer");
self.write_fields(&mut w);
w.end_container().expect("infallible: vec writer");
buf
}
}
impl MeasurementAccuracyRangeStruct {
pub fn decode_from(r: &mut TlvReader<'_>) -> Result<Self, ClusterError> {
let mut f_range_min: Option<i64> = None;
let mut f_range_max: Option<i64> = None;
let mut f_percent_max: Option<u16> = None;
let mut f_percent_min: Option<u16> = None;
let mut f_percent_typical: Option<u16> = None;
let mut f_fixed_max: Option<u64> = None;
let mut f_fixed_min: Option<u64> = None;
let mut f_fixed_typical: Option<u64> = None;
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::Scalar {
tag: Tag::Context(0),
value: Value::Int(v),
}) => {
f_range_min = Some(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("RangeMin"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(1),
value: Value::Int(v),
}) => {
f_range_max = Some(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("RangeMax"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(2),
value: Value::Uint(v),
}) => {
f_percent_max = Some(
u16::try_from(v).map_err(|_| ClusterError::InvalidLength("PercentMax"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(3),
value: Value::Uint(v),
}) => {
f_percent_min = Some(
u16::try_from(v).map_err(|_| ClusterError::InvalidLength("PercentMin"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(4),
value: Value::Uint(v),
}) => {
f_percent_typical = Some(
u16::try_from(v)
.map_err(|_| ClusterError::InvalidLength("PercentTypical"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(5),
value: Value::Uint(v),
}) => {
f_fixed_max = Some(
u64::try_from(v).map_err(|_| ClusterError::InvalidLength("FixedMax"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(6),
value: Value::Uint(v),
}) => {
f_fixed_min = Some(
u64::try_from(v).map_err(|_| ClusterError::InvalidLength("FixedMin"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(7),
value: Value::Uint(v),
}) => {
f_fixed_typical = Some(
u64::try_from(v)
.map_err(|_| ClusterError::InvalidLength("FixedTypical"))?,
)
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Self {
range_min: f_range_min.ok_or(ClusterError::MissingField("RangeMin"))?,
range_max: f_range_max.ok_or(ClusterError::MissingField("RangeMax"))?,
percent_max: f_percent_max,
percent_min: f_percent_min,
percent_typical: f_percent_typical,
fixed_max: f_fixed_max,
fixed_min: f_fixed_min,
fixed_typical: f_fixed_typical,
})
}
pub fn decode(tlv: &[u8]) -> Result<Self, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "MeasurementAccuracyRangeStruct",
})
}
}
Self::decode_from(&mut r)
}
#[allow(clippy::expect_used)] pub fn write_fields(&self, w: &mut TlvWriter<'_>) {
w.put_int(Tag::Context(0), i64::from(self.range_min))
.expect("infallible: vec writer");
w.put_int(Tag::Context(1), i64::from(self.range_max))
.expect("infallible: vec writer");
if let Some(percent_max) = &self.percent_max {
w.put_uint(Tag::Context(2), u64::from(*percent_max))
.expect("infallible: vec writer");
}
if let Some(percent_min) = &self.percent_min {
w.put_uint(Tag::Context(3), u64::from(*percent_min))
.expect("infallible: vec writer");
}
if let Some(percent_typical) = &self.percent_typical {
w.put_uint(Tag::Context(4), u64::from(*percent_typical))
.expect("infallible: vec writer");
}
if let Some(fixed_max) = &self.fixed_max {
w.put_uint(Tag::Context(5), u64::from(*fixed_max))
.expect("infallible: vec writer");
}
if let Some(fixed_min) = &self.fixed_min {
w.put_uint(Tag::Context(6), u64::from(*fixed_min))
.expect("infallible: vec writer");
}
if let Some(fixed_typical) = &self.fixed_typical {
w.put_uint(Tag::Context(7), u64::from(*fixed_typical))
.expect("infallible: vec writer");
}
}
#[must_use]
#[allow(clippy::expect_used)] pub fn encode(&self) -> Vec<u8> {
let mut buf = Vec::new();
let mut w = TlvWriter::new(&mut buf);
w.start_structure(Tag::Anonymous)
.expect("infallible: vec writer");
self.write_fields(&mut w);
w.end_container().expect("infallible: vec writer");
buf
}
}
impl MeasurementAccuracyStruct {
pub fn decode_from(r: &mut TlvReader<'_>) -> Result<Self, ClusterError> {
let mut f_measurement_type: Option<MeasurementTypeEnum> = None;
let mut f_measured: Option<bool> = None;
let mut f_min_measured_value: Option<i64> = None;
let mut f_max_measured_value: Option<i64> = None;
let mut f_accuracy_ranges: Option<Vec<MeasurementAccuracyRangeStruct>> = None;
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::Scalar {
tag: Tag::Context(0),
value: Value::Uint(v),
}) => {
f_measurement_type = Some(MeasurementTypeEnum::from_raw(
u16::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MeasurementType"))?,
))
}
Some(Element::Scalar {
tag: Tag::Context(1),
value: Value::Bool(v),
}) => f_measured = Some(v),
Some(Element::Scalar {
tag: Tag::Context(2),
value: Value::Int(v),
}) => {
f_min_measured_value = Some(
i64::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MinMeasuredValue"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(3),
value: Value::Int(v),
}) => {
f_max_measured_value = Some(
i64::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MaxMeasuredValue"))?,
)
}
Some(Element::ContainerStart {
tag: Tag::Context(4),
kind: ContainerKind::Array,
}) => {
let mut out = Vec::new();
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {
out.push(MeasurementAccuracyRangeStruct::decode_from(r)?);
}
None => {
return Err(ClusterError::Tlv(
matter_codec::Error::UnclosedContainer,
))
}
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
f_accuracy_ranges = Some(out);
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Self {
measurement_type: f_measurement_type
.ok_or(ClusterError::MissingField("MeasurementType"))?,
measured: f_measured.ok_or(ClusterError::MissingField("Measured"))?,
min_measured_value: f_min_measured_value
.ok_or(ClusterError::MissingField("MinMeasuredValue"))?,
max_measured_value: f_max_measured_value
.ok_or(ClusterError::MissingField("MaxMeasuredValue"))?,
accuracy_ranges: f_accuracy_ranges
.ok_or(ClusterError::MissingField("AccuracyRanges"))?,
})
}
pub fn decode(tlv: &[u8]) -> Result<Self, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "MeasurementAccuracyStruct",
})
}
}
Self::decode_from(&mut r)
}
}
impl MeasurementRangeStruct {
pub fn decode_from(r: &mut TlvReader<'_>) -> Result<Self, ClusterError> {
let mut f_measurement_type: Option<MeasurementTypeEnum> = None;
let mut f_min: Option<i64> = None;
let mut f_max: Option<i64> = None;
let mut f_start_timestamp: Option<u32> = None;
let mut f_end_timestamp: Option<u32> = None;
let mut f_min_timestamp: Option<u32> = None;
let mut f_max_timestamp: Option<u32> = None;
let mut f_start_systime: Option<u64> = None;
let mut f_end_systime: Option<u64> = None;
let mut f_min_systime: Option<u64> = None;
let mut f_max_systime: Option<u64> = None;
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::Scalar {
tag: Tag::Context(0),
value: Value::Uint(v),
}) => {
f_measurement_type = Some(MeasurementTypeEnum::from_raw(
u16::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MeasurementType"))?,
))
}
Some(Element::Scalar {
tag: Tag::Context(1),
value: Value::Int(v),
}) => {
f_min = Some(i64::try_from(v).map_err(|_| ClusterError::InvalidLength("Min"))?)
}
Some(Element::Scalar {
tag: Tag::Context(2),
value: Value::Int(v),
}) => {
f_max = Some(i64::try_from(v).map_err(|_| ClusterError::InvalidLength("Max"))?)
}
Some(Element::Scalar {
tag: Tag::Context(3),
value: Value::Uint(v),
}) => {
f_start_timestamp = Some(
u32::try_from(v)
.map_err(|_| ClusterError::InvalidLength("StartTimestamp"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(4),
value: Value::Uint(v),
}) => {
f_end_timestamp = Some(
u32::try_from(v)
.map_err(|_| ClusterError::InvalidLength("EndTimestamp"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(5),
value: Value::Uint(v),
}) => {
f_min_timestamp = Some(
u32::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MinTimestamp"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(6),
value: Value::Uint(v),
}) => {
f_max_timestamp = Some(
u32::try_from(v)
.map_err(|_| ClusterError::InvalidLength("MaxTimestamp"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(7),
value: Value::Uint(v),
}) => {
f_start_systime = Some(
u64::try_from(v)
.map_err(|_| ClusterError::InvalidLength("StartSystime"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(8),
value: Value::Uint(v),
}) => {
f_end_systime = Some(
u64::try_from(v).map_err(|_| ClusterError::InvalidLength("EndSystime"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(9),
value: Value::Uint(v),
}) => {
f_min_systime = Some(
u64::try_from(v).map_err(|_| ClusterError::InvalidLength("MinSystime"))?,
)
}
Some(Element::Scalar {
tag: Tag::Context(10),
value: Value::Uint(v),
}) => {
f_max_systime = Some(
u64::try_from(v).map_err(|_| ClusterError::InvalidLength("MaxSystime"))?,
)
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Self {
measurement_type: f_measurement_type
.ok_or(ClusterError::MissingField("MeasurementType"))?,
min: f_min.ok_or(ClusterError::MissingField("Min"))?,
max: f_max.ok_or(ClusterError::MissingField("Max"))?,
start_timestamp: f_start_timestamp,
end_timestamp: f_end_timestamp,
min_timestamp: f_min_timestamp,
max_timestamp: f_max_timestamp,
start_systime: f_start_systime,
end_systime: f_end_systime,
min_systime: f_min_systime,
max_systime: f_max_systime,
})
}
pub fn decode(tlv: &[u8]) -> Result<Self, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "MeasurementRangeStruct",
})
}
}
Self::decode_from(&mut r)
}
#[allow(clippy::expect_used)] pub fn write_fields(&self, w: &mut TlvWriter<'_>) {
w.put_uint(Tag::Context(0), u64::from(self.measurement_type.to_raw()))
.expect("infallible: vec writer");
w.put_int(Tag::Context(1), i64::from(self.min))
.expect("infallible: vec writer");
w.put_int(Tag::Context(2), i64::from(self.max))
.expect("infallible: vec writer");
if let Some(start_timestamp) = &self.start_timestamp {
w.put_uint(Tag::Context(3), u64::from(*start_timestamp))
.expect("infallible: vec writer");
}
if let Some(end_timestamp) = &self.end_timestamp {
w.put_uint(Tag::Context(4), u64::from(*end_timestamp))
.expect("infallible: vec writer");
}
if let Some(min_timestamp) = &self.min_timestamp {
w.put_uint(Tag::Context(5), u64::from(*min_timestamp))
.expect("infallible: vec writer");
}
if let Some(max_timestamp) = &self.max_timestamp {
w.put_uint(Tag::Context(6), u64::from(*max_timestamp))
.expect("infallible: vec writer");
}
if let Some(start_systime) = &self.start_systime {
w.put_uint(Tag::Context(7), u64::from(*start_systime))
.expect("infallible: vec writer");
}
if let Some(end_systime) = &self.end_systime {
w.put_uint(Tag::Context(8), u64::from(*end_systime))
.expect("infallible: vec writer");
}
if let Some(min_systime) = &self.min_systime {
w.put_uint(Tag::Context(9), u64::from(*min_systime))
.expect("infallible: vec writer");
}
if let Some(max_systime) = &self.max_systime {
w.put_uint(Tag::Context(10), u64::from(*max_systime))
.expect("infallible: vec writer");
}
}
#[must_use]
#[allow(clippy::expect_used)] pub fn encode(&self) -> Vec<u8> {
let mut buf = Vec::new();
let mut w = TlvWriter::new(&mut buf);
w.start_structure(Tag::Anonymous)
.expect("infallible: vec writer");
self.write_fields(&mut w);
w.end_container().expect("infallible: vec writer");
buf
}
}
pub fn decode_power_mode(tlv: &[u8]) -> Result<PowerModeEnum, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Uint(v),
..
}) => Ok(PowerModeEnum::from_raw(
u8::try_from(v).map_err(|_| ClusterError::InvalidLength("PowerMode"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "PowerMode",
}),
}
}
pub fn decode_number_of_measurement_types(tlv: &[u8]) -> Result<u8, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Uint(v),
..
}) => {
Ok(u8::try_from(v)
.map_err(|_| ClusterError::InvalidLength("NumberOfMeasurementTypes"))?)
}
_ => Err(ClusterError::UnexpectedType {
context: "NumberOfMeasurementTypes",
}),
}
}
pub fn decode_accuracy(tlv: &[u8]) -> Result<Vec<MeasurementAccuracyStruct>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Array,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "Accuracy",
})
}
}
let r = &mut r;
let mut out = Vec::new();
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {
out.push(MeasurementAccuracyStruct::decode_from(r)?);
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(out)
}
pub fn decode_ranges(tlv: &[u8]) -> Result<Vec<MeasurementRangeStruct>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::ContainerStart {
kind: ContainerKind::Array,
..
}) => {}
_ => return Err(ClusterError::UnexpectedType { context: "Ranges" }),
}
let r = &mut r;
let mut out = Vec::new();
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {
out.push(MeasurementRangeStruct::decode_from(r)?);
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(out)
}
pub fn decode_voltage(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("Voltage"))?,
)),
_ => Err(ClusterError::UnexpectedType { context: "Voltage" }),
}
}
pub fn decode_active_current(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("ActiveCurrent")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "ActiveCurrent",
}),
}
}
pub fn decode_reactive_current(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("ReactiveCurrent")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "ReactiveCurrent",
}),
}
}
pub fn decode_apparent_current(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("ApparentCurrent")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "ApparentCurrent",
}),
}
}
pub fn decode_active_power(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("ActivePower"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "ActivePower",
}),
}
}
pub fn decode_reactive_power(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("ReactivePower")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "ReactivePower",
}),
}
}
pub fn decode_apparent_power(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("ApparentPower")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "ApparentPower",
}),
}
}
pub fn decode_rms_voltage(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("RmsVoltage"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "RmsVoltage",
}),
}
}
pub fn decode_rms_current(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("RmsCurrent"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "RmsCurrent",
}),
}
}
pub fn decode_rms_power(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("RmsPower"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "RmsPower",
}),
}
}
pub fn decode_frequency(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("Frequency"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "Frequency",
}),
}
}
pub fn decode_harmonic_currents(
tlv: &[u8],
) -> Result<Nullable<Vec<HarmonicMeasurementStruct>>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => return Ok(Nullable::Null),
Some(Element::ContainerStart {
kind: ContainerKind::Array,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "HarmonicCurrents",
})
}
}
let r = &mut r;
let mut out = Vec::new();
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {
out.push(HarmonicMeasurementStruct::decode_from(r)?);
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Nullable::Value(out))
}
pub fn decode_harmonic_phases(
tlv: &[u8],
) -> Result<Nullable<Vec<HarmonicMeasurementStruct>>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => return Ok(Nullable::Null),
Some(Element::ContainerStart {
kind: ContainerKind::Array,
..
}) => {}
_ => {
return Err(ClusterError::UnexpectedType {
context: "HarmonicPhases",
})
}
}
let r = &mut r;
let mut out = Vec::new();
loop {
match r.next()? {
Some(Element::ContainerEnd) => break,
Some(Element::ContainerStart {
kind: ContainerKind::Structure,
..
}) => {
out.push(HarmonicMeasurementStruct::decode_from(r)?);
}
None => return Err(ClusterError::Tlv(matter_codec::Error::UnclosedContainer)),
Some(Element::ContainerStart { .. }) => r.skip_container()?,
Some(_) => {} }
}
Ok(Nullable::Value(out))
}
pub fn decode_power_factor(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => Ok(Nullable::Value(
i64::try_from(v).map_err(|_| ClusterError::InvalidLength("PowerFactor"))?,
)),
_ => Err(ClusterError::UnexpectedType {
context: "PowerFactor",
}),
}
}
pub fn decode_neutral_current(tlv: &[u8]) -> Result<Nullable<i64>, ClusterError> {
let mut r = TlvReader::new(tlv);
match r.next()? {
Some(Element::Scalar {
value: Value::Null, ..
}) => Ok(Nullable::Null),
Some(Element::Scalar {
value: Value::Int(v),
..
}) => {
Ok(Nullable::Value(i64::try_from(v).map_err(|_| {
ClusterError::InvalidLength("NeutralCurrent")
})?))
}
_ => Err(ClusterError::UnexpectedType {
context: "NeutralCurrent",
}),
}
}