Rust::com Derive macro for CommData#156
Conversation
719a3c7 to
7524795
Compare
7524795 to
14a7f51
Compare
pawelrutkaq
left a comment
There was a problem hiding this comment.
LGTM, one issues found
14a7f51 to
57e641a
Compare
57e641a to
ba2b668
Compare
c5fd1f6 to
23e00d4
Compare
| /// | ||
| /// This macro **only** validates the optional `#[comm_data(id = "…")]` attribute. It does | ||
| /// **not** check `#[repr(C)]`, field relocatability, or enum layout — those invariants are | ||
| /// already enforced by `#[derive(Reloc)]`, which must be placed before this macro. |
There was a problem hiding this comment.
I think this is not needed since compiler will tell you that anyway
| /// ``` | ||
| /// ``` | ||
| #[proc_macro_derive(CommData, attributes(comm_data))] | ||
| pub fn derive_comm_data(input: TokenStream) -> TokenStream { |
There was a problem hiding this comment.
I think this opens something like:
#[derive(Debug, Reloc, CommData)]
#[repr(C)]
pub struct Tire {
#[comm_data(id = "Tire")]
pub pressure: f32,
}
And I dont see whether we forbit this anywhere as compilation error ?
There was a problem hiding this comment.
Agreed, this is gap in current macro implementation, when #[comm_data(id = "Tire")] is placed on a field, it lives in the field's attribute, which the macro never inspects. So the macro falls back to the auto-generated ID (module_path::Tire), silently discarding the user's annotation. No error, no warning.
we will add validation check to iterate over all fields and emit a compile error if any field carries a comm_data attribute.
| /// they can use the `#[comm_data(id = "CustomID")]` attribute on the struct definition. | ||
| /// The custom ID must be unique across all communication data types to avoid conflicts in the system. | ||
| /// If no custom ID is provided, the struct name will be used as the default ID with module path as prefix to ensure uniqueness. | ||
| pub trait CommData: Reloc + Send + Debug + 'static { |
There was a problem hiding this comment.
Now I think Reloc shall be Reloc: Send + 'static because Reloc is responsible for "allowing a type to be safely shared between processes" which means it can be Send and it 'static.
The CommData is only extension over with custom ID thus CommData: Reloc
There was a problem hiding this comment.
The suggested change does not affect users at the API level, users will continue to use the macro in exactly the same way: #[derive(Reloc, CommData)].
The difference is purely conceptual and relates to how constraints are owned and expressed.
-
Current approach:
CommData: Reloc + Send + Debug + 'static
All requirements are explicitly declared on CommData. The full contract is visible in one place, making it easy to understand at a glance. -
suggested approach:
Reloc: Send + 'static, followed byCommData: Reloc + Debug
Some requirements are moved into the trait hierarchy. As a result, CommData’s full set of bounds becomes implicit through Reloc, rather than being stated directly.
There was a problem hiding this comment.
Maybe even
Reloc: Send + Unpin + 'static and CommData: Reloc (NOT Debug, though, or why would that be strictly necessary..?)
There was a problem hiding this comment.
Debug is required because we want to support printing the value of T and enforce the bound through CommData alone. Therefore, keeping the Debug bound within CommData is fine in my opinion, otherwise, we would have to introduce an unnecessary dual bound - T: CommData + Debug.
There was a problem hiding this comment.
I think Debug shall be bound to API itself and not here, even though you need to state it in many places later (agree with @darkwisebear ). Is Unpin here something really necessary? Thie pin history is future workound in Rust as i remeber and not sure if here we really need to mention it ?
There was a problem hiding this comment.
Unpin means that a type can be moved within the same address space by means of a simple memcpy. CommData means that a type can be moved between different address spaces. So while it's not strictly needed by the API, imo it's a strict subset of CommData, so for consistency reasons, it should be included.
There was a problem hiding this comment.
@darkwisebear , @pawelrutkaq ,
Added the code changes as per above discussion.
There was a problem hiding this comment.
have a feeling that this is just overspecification, but since Unpint is auto impl trait, I think it does not matter.
Anyway, user needs to know that it has !Unpin type (by ie placing PhantomPin) otherwise his type will be Unpin .
23e00d4 to
8fcb3a7
Compare
* Implemented derive macro for CommData trait impl
* CommData should explicitly derive Reloc. This makes the dependency clear in the code.
* Moved trait bound from CommData to Reloc trait * Added field check on comm_data attribute
* Removed Debug trait bound from CommData trait
8fcb3a7 to
1dae308
Compare
pawelrutkaq
left a comment
There was a problem hiding this comment.
Fine for me. However I would do next PR with ScoreDebug trait as this is needed in Score to log.
We need to talk about |
We can, however, keep in mind we discussed it around Q3.2025 and at that point we said that if the logging team requires full type information, it has to be developed and it's nothing you can do. |
#155