-
Notifications
You must be signed in to change notification settings - Fork 53
Mesh Synchronization Implementation Notes
Mesh Synchronization is specified in the IEEE 802.11 Standard. For our implementation, we've used IEEE Draft P802.11-REVmbTM/D12, November 2011.
There have been changes required to nl80211, cfg80211 and mac80211. But the bulk of the mesh synchronization takes place in net/mac80211/mesh_sync.c. This should be your starting point if you intend to review and/or extend this code.
The 802.11s specification defines an extensible mesh synchronization framework. To achieve this extensibility, the framework has been implemented using the common operations table pattern frequently used in the kernel.
The table is an array of struct ieee80211_mesh_sync_ops which provides definitions for the following functions (operations):
struct ieee80211_mesh_sync_ops {
void (*rx_bcn_presp)(...);
void (*adjust_tbtt)(...);
void (*add_vendor_ie)(...);
};The functions will be called by the open80211s protocol at different times as required to track timing offset and correct drift.
- rx_bcn_presp() - this is called every time a mesh beacon is received.
- adjust_tbtt() - this is called immediately before a beacon is about to be transmitted.
- add_vendor_ie() - this is called every time a beacon or a peer link management frame is about to be transmitted.
Per-peer offset tracking takes place inside mesh_sync_offset_rx_bcn_presp(). The function is passed an struct ieee80211_rx_status that contains a filed (rx_status->mactime) with the local tsf value recorded at the reception of the first symbol of the beacon. If the beacon comes from a known station (either an established peer or a peer candidate), the t_offset for that station (sta) is recorded in ```sta->t_offset``.
Jitter mitigation is essential for the correct adjustment of clock drifts, but the 802.11 specification does not define any jitter mitigation method. Instead, there is only an implicit reference to it. See Section 13.13.2.2.3:
When the previous TClockDrift values have been stable for a neighbor mesh STA, the mesh STA may substitute the previous TClockDrift value for the TClockDrift value in the measurement procedure and process the step d), at the time of a TBTT of the neighbor STA, without receiving a Beacon frame.
(The italics above are not on the original text)
To compensate for jitter, subsequent offset measurements are averaged using the following formula:
[ avg_t_offset_{n+1} = {T_{offset} + 7 * avg_t_offset_{n} \over 8} ]
When you review the code you will surely be tempted to re-order some statements to optimize the offset calculations: think twice before doing so. In particular, you have to consider that any access to the sta pointer must take place within the rcu_read_lock/unlock section, and also one cannot call any functions that might sleep within that section. That includes the evident spin_lock() calls but also the calls to the driver to get or set the TSF counter (drv_get/set_tsf()).
Once the t_offset for a particular peer is known, the flag WLAN_STA_TOFFSET_KNOWN is set on the station so that the can be reported to userspace (e.g. iw).