Skip to content

Implement IEEE 802.11s meshing. #4

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 9 commits into
base: main
Choose a base branch
from
Open

Implement IEEE 802.11s meshing. #4

wants to merge 9 commits into from

Conversation

Frostie314159
Copy link
Member

@Frostie314159 Frostie314159 commented Apr 17, 2025

This PR adds foa_mesh as an implementation for IEEE 802.11s compliant meshing. This is developed by @redfast00, I only opened the PR, so I don't want to take credit for his work.

/// Parameters that may change over the course of a session.
pub(crate) struct DynamicSessionParameters {
pub(crate) is_mesh_gate: Cell<bool>,
pub(crate) peers: [Cell<MPMFSMState>; 5],
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not totally familiar with 802.11s, but wouldn't it be more advantageous to use something like heapless::FnvIndexMap for this? It doesn't use dynamic allocations, and you could remove the Idle variant, which would greatly simplify all code using this. I think in this case, it would also make sense to wrap the list in an embassy_sync::NoopMutex<RefCell<...>>.

The reason, that the parts of FoA I wrote are so littered with Cell is, because I saw how many unreachable panics were generated by the compiler, since it failed to optimize out the ref count checks. Looking back, the worries were probably unfounded, and it makes sense to use mutexes in some places. For primitive types, like bool you can either use cells or atomics, none of which are extremely ergonomic.

&TxParameters {
rate: WiFiRate::PhyRate12M,
override_seq_num: true,
tx_error_behaviour: TxErrorBehaviour::Drop,
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IMO, it would make more sense here to use the default retry behavior, since it's an unicast management frame, and then handling any errors. For foa_sta I had to add a check, where it retransmitted the management frame, if the AP ACK'ed the frame, but then just didn't transmit a response. No idea, why it does that, but it's a possibility. If you're interested, that's implemented in do_bidirectional_connection_step.

Similarly to that function, you could also make a generic function to transmit MPO frames, with different bodies, since the header, as well as serialization and transmission logic is always the same.

}

pub fn generate_new_link_id(&self) -> u16 {
u16::try_from(self.rng.clone().next_u32() & 0xFFFF).unwrap()
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Although a collision is fairly unlikely (1 : 65536), I think it would be best to check if that link ID is already in use, since this seems horrible to debug and probably won't cause a big hit to performance.

Comment on lines +19 to +25
self.interface_control.set_filter_parameters(
RxFilterBank::ReceiverAddress,
*self.mac_address,
None,
);
self.interface_control
.set_filter_status(RxFilterBank::ReceiverAddress, true);
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it might be better to set the BSSID here anyway since it's more obvious what's actually going on here, even though the hardware technically does this automatically when none is provided. Alternatively, a comment would also work.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants