mirror of
https://github.com/meshcore-dev/MeshCore.git
synced 2026-04-20 22:13:47 +00:00
JP LBT mode now activates automatically based on operating frequency: - CH25: 920.800MHz - CH26: 921.000MHz - CH27: 921.200MHz (ARIB STD-T108, 200kHz grid) Changes: - Add isJapanMode() to RadioLibWrapper using getFreqMHz() - Add getFreqMHz() to CustomSX1262Wrapper and CustomLR1110Wrapper - Remove #ifdef JP_STRICT throughout, replaced by isJapanMode() - Remove -D JP_STRICT build flag from platformio.ini - MAX_TEXT_LEN dynamically determined by CR at runtime via getMaxTextLen() No build flags required: JP compliance activates automatically when device is configured to Japan 3 frequencies.
97 lines
3 KiB
C++
97 lines
3 KiB
C++
#pragma once
|
|
|
|
#include <Mesh.h>
|
|
#include <RadioLib.h>
|
|
|
|
class RadioLibWrapper : public mesh::Radio {
|
|
protected:
|
|
PhysicalLayer* _radio;
|
|
mesh::MainBoard* _board;
|
|
uint32_t n_recv, n_sent, n_recv_errors, _tx_start_ms;
|
|
int16_t _noise_floor, _threshold;
|
|
uint8_t _busy_count; // consecutive busy detections for exponential backoff
|
|
uint16_t _num_floor_samples;
|
|
int32_t _floor_sample_sum;
|
|
|
|
void idle();
|
|
void startRecv();
|
|
float packetScoreInt(float snr, int sf, int packet_len);
|
|
virtual bool isReceivingPacket() =0;
|
|
virtual void doResetAGC();
|
|
|
|
public:
|
|
RadioLibWrapper(PhysicalLayer& radio, mesh::MainBoard& board) : _radio(&radio), _board(&board) { n_recv = n_sent = 0; }
|
|
|
|
void begin() override;
|
|
virtual void powerOff() { _radio->sleep(); }
|
|
int recvRaw(uint8_t* bytes, int sz) override;
|
|
uint32_t getEstAirtimeFor(int len_bytes) override;
|
|
bool startSendRaw(const uint8_t* bytes, int len) override;
|
|
bool isSendComplete() override;
|
|
void onSendFinished() override;
|
|
bool isInRecvMode() const override;
|
|
bool isChannelActive();
|
|
|
|
bool isReceiving() override {
|
|
if (isReceivingPacket()) return true;
|
|
|
|
return isChannelActive();
|
|
}
|
|
|
|
virtual float getCurrentRSSI() =0;
|
|
virtual uint8_t getCodingRate() const = 0;
|
|
virtual float getFreqMHz() const = 0;
|
|
|
|
bool isJapanMode() const {
|
|
float freq = getFreqMHz();
|
|
return (fabsf(freq - 920.800f) < 0.05f ||
|
|
fabsf(freq - 921.000f) < 0.05f ||
|
|
fabsf(freq - 921.200f) < 0.05f);
|
|
}
|
|
|
|
int getMaxTextLen() const {
|
|
if (!isJapanMode()) return 10 * 16; // default
|
|
uint8_t cr = getCodingRate();
|
|
if (cr <= 5) return 3 * 16; // 48 bytes ~16 JP chars
|
|
if (cr == 6) return 2 * 16; // 32 bytes ~10 JP chars
|
|
if (cr == 7) return 1 * 16 + 8; // 24 bytes ~8 JP chars
|
|
return 1 * 16; // 16 bytes ~5 JP chars
|
|
}
|
|
|
|
virtual int16_t performChannelScan();
|
|
|
|
int getNoiseFloor() const override { return _noise_floor; }
|
|
void triggerNoiseFloorCalibrate(int threshold) override;
|
|
void resetAGC() override;
|
|
|
|
void loop() override;
|
|
|
|
uint32_t getPacketsRecv() const { return n_recv; }
|
|
uint32_t getPacketsRecvErrors() const { return n_recv_errors; }
|
|
uint32_t getPacketsSent() const { return n_sent; }
|
|
void resetStats() { n_recv = n_sent = n_recv_errors = 0; }
|
|
|
|
virtual float getLastRSSI() const override;
|
|
virtual float getLastSNR() const override;
|
|
|
|
float packetScore(float snr, int packet_len) override { return packetScoreInt(snr, 10, packet_len); } // assume sf=10
|
|
|
|
virtual void setRxBoostedGainMode(bool) { }
|
|
virtual bool getRxBoostedGainMode() const { return false; }
|
|
};
|
|
|
|
/**
|
|
* \brief an RNG impl using the noise from the LoRa radio as entropy.
|
|
* NOTE: this is VERY SLOW! Use only for things like creating new LocalIdentity
|
|
*/
|
|
class RadioNoiseListener : public mesh::RNG {
|
|
PhysicalLayer* _radio;
|
|
public:
|
|
RadioNoiseListener(PhysicalLayer& radio): _radio(&radio) { }
|
|
|
|
void random(uint8_t* dest, size_t sz) override {
|
|
for (int i = 0; i < sz; i++) {
|
|
dest[i] = _radio->randomByte() ^ (::random(0, 256) & 0xFF);
|
|
}
|
|
}
|
|
};
|