Skip to content

Commit 247b894

Browse files
committed
JP LBT: suppress txdelay to jitter-scale at SF12/BW125
1 parent 6b3c7a9 commit 247b894

5 files changed

Lines changed: 47 additions & 3 deletions

File tree

examples/simple_repeater/MyMesh.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -541,10 +541,22 @@ int MyMesh::calcRxDelay(float score, uint32_t air_time) const {
541541
}
542542

543543
uint32_t MyMesh::getRetransmitDelay(const mesh::Packet *packet) {
544+
if (_radio->isAS923_1_JP()) {
545+
// JP LBT: suppress txdelay to jitter-scale to avoid adding unnecessary
546+
// latency on top of LBT backoff. A window equal to jitter_max gives
547+
// ~33% collision reduction vs zero, scales naturally with airtime as
548+
// CR changes, and keeps average added delay to ~56ms at SF12/BW125.
549+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
550+
return getRNG()->nextInt(0, jitter_max + 1);
551+
}
544552
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.tx_delay_factor);
545553
return getRNG()->nextInt(0, 5*t + 1);
546554
}
547555
uint32_t MyMesh::getDirectRetransmitDelay(const mesh::Packet *packet) {
556+
if (_radio->isAS923_1_JP()) {
557+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
558+
return getRNG()->nextInt(0, jitter_max + 1);
559+
}
548560
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.direct_tx_delay_factor);
549561
return getRNG()->nextInt(0, 5*t + 1);
550562
}

examples/simple_room_server/MyMesh.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -272,10 +272,22 @@ const char *MyMesh::getLogDateTime() {
272272
}
273273

274274
uint32_t MyMesh::getRetransmitDelay(const mesh::Packet *packet) {
275+
if (_radio->isAS923_1_JP()) {
276+
// JP LBT: suppress txdelay to jitter-scale to avoid adding unnecessary
277+
// latency on top of LBT backoff. A window equal to jitter_max gives
278+
// ~33% collision reduction vs zero, scales naturally with airtime as
279+
// CR changes, and keeps average added delay to ~56ms at SF12/BW125.
280+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
281+
return getRNG()->nextInt(0, jitter_max + 1);
282+
}
275283
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.tx_delay_factor);
276284
return getRNG()->nextInt(0, 5*t + 1);
277285
}
278286
uint32_t MyMesh::getDirectRetransmitDelay(const mesh::Packet *packet) {
287+
if (_radio->isAS923_1_JP()) {
288+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
289+
return getRNG()->nextInt(0, jitter_max + 1);
290+
}
279291
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.direct_tx_delay_factor);
280292
return getRNG()->nextInt(0, 5*t + 1);
281293
}

examples/simple_sensor/SensorMesh.cpp

Lines changed: 14 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -313,12 +313,24 @@ int SensorMesh::calcRxDelay(float score, uint32_t air_time) const {
313313
}
314314

315315
uint32_t SensorMesh::getRetransmitDelay(const mesh::Packet* packet) {
316+
if (_radio->isAS923_1_JP()) {
317+
// JP LBT: suppress txdelay to jitter-scale to avoid adding unnecessary
318+
// latency on top of LBT backoff. A window equal to jitter_max gives
319+
// ~33% collision reduction vs zero, scales naturally with airtime as
320+
// CR changes, and keeps average added delay to ~56ms at SF12/BW125.
321+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
322+
return getRNG()->nextInt(0, jitter_max + 1);
323+
}
316324
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.tx_delay_factor);
317-
return getRNG()->nextInt(0, 6)*t;
325+
return getRNG()->nextInt(0, 5*t + 1);
318326
}
319327
uint32_t SensorMesh::getDirectRetransmitDelay(const mesh::Packet* packet) {
328+
if (_radio->isAS923_1_JP()) {
329+
uint32_t jitter_max = _radio->getEstAirtimeFor(MAX_TRANS_UNIT) / RadioLibWrapper::JP_LBT_JITTER_DIVISOR;
330+
return getRNG()->nextInt(0, jitter_max + 1);
331+
}
320332
uint32_t t = (_radio->getEstAirtimeFor(packet->getPathByteLen() + packet->payload_len + 2) * _prefs.direct_tx_delay_factor);
321-
return getRNG()->nextInt(0, 6)*t;
333+
return getRNG()->nextInt(0, 5*t + 1);
322334
}
323335
int SensorMesh::getInterferenceThreshold() const {
324336
return _prefs.interference_threshold;

src/helpers/radiolib/RadioLibWrappers.cpp

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -209,8 +209,14 @@ bool RadioLibWrapper::isChannelActive() {
209209
}
210210
YIELD_TASK();
211211
}
212+
// Channel free: reset busy counter and add airtime-scaled jitter.
213+
// JP_LBT_JITTER_DIVISOR controls jitter upper bound:
214+
// /8 -> SF12/BW125 ~975ms, SF7/BW62.5 ~50ms
215+
// /16 -> SF12/BW125 ~490ms, SF7/BW62.5 ~25ms
216+
// /32 -> SF12/BW125 ~245ms, SF7/BW62.5 ~12ms (default)
212217
_busy_count = 0;
213-
uint32_t jitter_until = millis() + random(0, 500);
218+
uint32_t airtime_ms = getEstAirtimeFor(MAX_TRANS_UNIT);
219+
uint32_t jitter_until = millis() + random(0, airtime_ms / JP_LBT_JITTER_DIVISOR);
214220
while (millis() < jitter_until) {
215221
YIELD_TASK();
216222
}

src/helpers/radiolib/RadioLibWrappers.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,8 @@ class RadioLibWrapper : public mesh::Radio {
5151
virtual uint8_t getCodingRate() const { return 8; } // default CR4/8, override in subclass
5252
virtual float getFreqMHz() const { return 0.0f; } // default unknown, override in subclass
5353

54+
static constexpr uint8_t JP_LBT_JITTER_DIVISOR = 32;
55+
5456
bool isAS923_1_JP() const override {
5557
float freq = getFreqMHz();
5658
return (fabsf(freq - 920.800f) < 0.05f ||

0 commit comments

Comments
 (0)