robot_description_builder/cluster_objects/
kinematic_data_errors.rs

1use thiserror::Error;
2
3use std::{
4	collections::HashMap,
5	sync::{Arc, PoisonError},
6};
7
8use crate::{
9	joint::Joint,
10	link::Link,
11	material::data::MaterialData,
12	transmission::{BuildTransmissionError, Transmission},
13	utils::{ArcLock, ErroredRead, ErroredWrite, WeakLock},
14};
15
16use super::kinematic_data_tree::KinematicDataTree;
17
18pub(crate) type PoisonReadIndexError<K, V> = PoisonError<ErroredRead<ArcLock<HashMap<K, V>>>>;
19pub(crate) type PoisonWriteIndexError<K, V> = PoisonError<ErroredWrite<ArcLock<HashMap<K, V>>>>;
20
21// TODO: Improve Doc
22#[derive(Debug, Error)]
23pub enum AddMaterialError {
24	//TODO: IMPR DOC
25	/// Error that results from `PoisonError<RwLockReadGuard<'_, MaterialData>>` occurs when attempting to read a poisoned `Arc<RwLock<MaterialData>>`.
26	#[error("The lock of the new Material is poisoned and therefore could not be read")]
27	ReadMaterial(#[from] PoisonError<ErroredRead<ArcLock<MaterialData>>>),
28	//TODO: IMPR DOC
29	/// Error that results from `PoisonError<RwLockReadGuard<'_, HashMap<String, ArcLock<MaterialData>>>>` occurs when attempting to read a poisoned `HashMap<String, ArcLock<MaterialData>>`.
30	/* In the future the lock could be saved by overwriting with a newly generated index (Might lose some data), however waiting for
31	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
32	#[error("The lock of the Material Index is poisoned and therefore could not be read")]
33	ReadIndex(#[from] PoisonReadIndexError<String, ArcLock<MaterialData>>),
34	//TODO: IMPR DOC
35	/// Error that results from `PoisonError<RwLockWriteGuard<'_, HashMap<String, ArcLock<MaterialData>>>>` occurs when attempting to write to a poisoned `HashMap<String, ArcLock<MaterialData>>`.
36	/* In the future the lock could be saved by overwriting with a newly generated index (Might lose some data), however waiting for
37	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
38	#[error("The lock of the Material Index is poisoned and therefore could be written to")]
39	WriteIndex(#[from] PoisonWriteIndexError<String, ArcLock<MaterialData>>),
40	/// An Error, which occurse when a named `Material` is being registered and the name is already in use by another `Material` with a different `MaterialDescription`.
41	#[error("The Material name '{0}' is already in use by another Material with non-matching descriptions")]
42	Conflict(String),
43}
44
45impl PartialEq for AddMaterialError {
46	fn eq(&self, other: &Self) -> bool {
47		match (self, other) {
48			(Self::ReadMaterial(l0), Self::ReadMaterial(r0)) => l0.get_ref() == r0.get_ref(),
49			(Self::ReadIndex(l0), Self::ReadIndex(r0)) => l0.get_ref() == r0.get_ref(),
50			(Self::WriteIndex(l0), Self::WriteIndex(r0)) => l0.get_ref() == r0.get_ref(),
51			(Self::Conflict(l0), Self::Conflict(r0)) => l0 == r0,
52			_ => false,
53		}
54	}
55}
56
57#[derive(Debug, Error)]
58pub enum AddLinkError {
59	/// Error that results from `PoisonError<RwLockReadGuard<'_, Link>>` occurs when attempting to read a poisoned `Arc<RwLock<Link>>`.
60	#[error("The lock of the new Link is poisoned and therefore could not be read")]
61	ReadNewLink(#[from] PoisonError<ErroredRead<ArcLock<Link>>>),
62	/// Error that results from `PoisonError<RwLockWriteGuard<'_, Link>>` occurs when attempting to write to a poisoned `Arc<RwLock<Link>>`.
63	#[error("The lock of the new Link is poisoned and therefore could not be written to")]
64	WriteNewLink(#[from] PoisonError<ErroredWrite<ArcLock<Link>>>),
65	/// Error that results from `PoisonError<RwLockReaddGuard<'_, HashMap<String, Weak<RwLock<Link>>>>` occurs when attempting to read a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Link>>>>>`.
66	/* In the future the lock could be saved by overwriting with a newly generated index, however waiting for
67	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
68	#[error("The lock of the Link Index is poisoned and therefor could not be read")]
69	ReadIndex(#[from] PoisonReadIndexError<String, WeakLock<Link>>),
70	/// Error that results from `PoisonError<RwLockWriteGuard<'_, HashMap<String, Weak<RwLock<Link>>>>` occurs when attempting to write to a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Link>>>>>`.
71	/* In the future the lock could be saved by overwriting with a newly generated index, however waiting for
72	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
73	#[error("The lock of the Link Index is poisoned and therefor could not be written to")]
74	WriteIndex(#[from] PoisonWriteIndexError<String, WeakLock<Link>>),
75	#[error(
76		"The new Link could not be added since its name '{0}' is already in use by another Link"
77	)]
78	Conflict(String),
79	/// Error that results from `PoisonError<RwLockWriteGuard<'_, Weak<RwLock<Link>>>>` occurs when attempting to write to a poisoned `RwLock<Weak<RwLock<Link>>>>`. (Only used for `KinematicDataTree``.newest_link`).
80	/* In the future the lock could be saved by overwriting with a newly generated index, however waiting for
81	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
82	#[error("The lock of the `newest_link` on the KinematicDataTree is poisoned and therefore could not be accessed")]
83	AccessNewestLink(#[from] PoisonError<ErroredWrite<Arc<KinematicDataTree>>>),
84}
85
86impl PartialEq for AddLinkError {
87	fn eq(&self, other: &Self) -> bool {
88		match (self, other) {
89			(Self::ReadNewLink(l0), Self::ReadNewLink(r0)) => l0.get_ref() == r0.get_ref(),
90			(Self::ReadIndex(l0), Self::ReadIndex(r0)) => l0.get_ref() == r0.get_ref(),
91			(Self::WriteIndex(l0), Self::WriteIndex(r0)) => l0.get_ref() == r0.get_ref(),
92			(Self::Conflict(l0), Self::Conflict(r0)) => l0 == r0,
93			(Self::AccessNewestLink(l0), Self::AccessNewestLink(r0)) => {
94				l0.get_ref() == r0.get_ref()
95			}
96			_ => false,
97		}
98	}
99}
100
101// TODO: Improve Doc
102#[derive(Debug, Error)]
103pub enum AddJointError {
104	/// Error that results from `PoisonError<RwLockReadGuard<'_, Joint>>` occurs when attempting to read a poisoned `Arc<RwLock<Joint>>`.
105	#[error("The lock of the new Joint is poisoned and therefore could not be read")]
106	ReadNewJoint(#[from] PoisonError<ErroredRead<ArcLock<Joint>>>),
107	/// Error that results from `PoisonError<RwLockReaddGuard<'_, HashMap<String, Weak<RwLock<Joint>>>>` occurs when attempting to read a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Joint>>>>>`.
108	/* In the future the lock could be saved by overwriting with a newly generated index, however waiting for
109	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
110	#[error("The lock of the Joint Index is poisoned and therefore could not be read")]
111	ReadIndex(#[from] PoisonReadIndexError<String, WeakLock<Joint>>),
112	/// Error that results from `PoisonError<RwLockWriteGuard<'_, HashMap<String, Weak<RwLock<Joint>>>>` occurs when attempting to write to a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Joint>>>>>`.
113	/* In the future the lock could be saved by overwriting with a newly generated index, however waiting for
114	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
115	#[error("The lock of Joint Index is poisoned and therefore could not be written to")]
116	WriteIndex(#[from] PoisonWriteIndexError<String, WeakLock<Joint>>),
117	#[error(
118		"The new Joint could not be added since its name '{0}' is already in use by another Joint"
119	)]
120	Conflict(String),
121}
122
123impl PartialEq for AddJointError {
124	fn eq(&self, other: &Self) -> bool {
125		match (self, other) {
126			(Self::ReadNewJoint(l0), Self::ReadNewJoint(r0)) => l0.get_ref() == r0.get_ref(),
127			(Self::ReadIndex(l0), Self::ReadIndex(r0)) => l0.get_ref() == r0.get_ref(),
128			(Self::WriteIndex(l0), Self::WriteIndex(r0)) => l0.get_ref() == r0.get_ref(),
129			(Self::Conflict(l0), Self::Conflict(r0)) => l0 == r0,
130			_ => false,
131		}
132	}
133}
134
135#[derive(Debug, Error)]
136pub enum AddTransmissionError {
137	/// Error that results from `PoisonError<RwLockReaddGuard<'_, HashMap<String, Weak<RwLock<Transmission>>>>` occurs when attempting to read a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Transmission>>>>>`.
138	/* In the future this lock might be saveable but waiting for
139	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
140	#[error("Read TransmissionIndex Error: {0}")]
141	ReadIndex(#[from] PoisonReadIndexError<String, ArcLock<Transmission>>),
142	/// Error that results from `PoisonError<RwLockWriteGuard<'_, HashMap<String, Weak<RwLock<Transmission>>>>` occurs when attempting to write to a poisoned `Arc<RwLock<HashMap<String, Weak<RwLock<Transmission>>>>>`.
143	/* In the future this lock might be saveable but waiting for
144	"This is a nightly-only experimental API. (mutex_unpoison #96469)" */
145	#[error("Write TransmissionIndex Error: {0}")]
146	WriteIndex(#[from] PoisonWriteIndexError<String, ArcLock<Transmission>>),
147	#[error("Duplicate Transmission name '{0}'")]
148	Conflict(String),
149	#[error(transparent)]
150	BuildTransmission(#[from] BuildTransmissionError),
151}
152
153impl PartialEq for AddTransmissionError {
154	fn eq(&self, other: &Self) -> bool {
155		match (self, other) {
156			(Self::ReadIndex(l0), Self::ReadIndex(r0)) => l0.get_ref() == r0.get_ref(),
157			(Self::WriteIndex(l0), Self::WriteIndex(r0)) => l0.get_ref() == r0.get_ref(),
158			(Self::Conflict(l0), Self::Conflict(r0)) => l0 == r0,
159			(Self::BuildTransmission(l0), Self::BuildTransmission(r0)) => l0 == r0,
160			_ => false,
161		}
162	}
163}
164
165#[derive(Debug, PartialEq, Error)]
166pub enum AttachChainError {
167	#[error("An error occured when registering a Link: {0}")]
168	Link(#[from] AddLinkError),
169	#[error("An error occured when registering a Joint: {0}")]
170	Joint(#[from] AddJointError),
171	#[error("An error occured when registering a Material: {0}")]
172	Material(#[from] AddMaterialError),
173}
174
175impl From<PoisonError<ErroredWrite<Arc<KinematicDataTree>>>> for AttachChainError {
176	fn from(value: PoisonError<ErroredWrite<Arc<KinematicDataTree>>>) -> Self {
177		Self::Link(value.into())
178	}
179}