embassy-rs / lora-phy Goto Github PK
View Code? Open in Web Editor NEWREPO ARCHIVED - moved to https://github.com/lora-rs/lora-rs -- LoRa implementation based on embedded-hal-async
License: Apache License 2.0
REPO ARCHIVED - moved to https://github.com/lora-rs/lora-rs -- LoRa implementation based on embedded-hal-async
License: Apache License 2.0
└─ /home/r/.cargo/registry/src/index.crates.io-6f17d22bba15001f/lora-phy-2.1.2/src/sx1261_2/mod.rs:440
0.361870 ERROR panicked at /home/r/.cargo/registry/src/index.crates.io-6f17d22bba15001f/lora-phy-2.1.2/src/sx1261_2/mod.rs:72:36:
index out of bounds: the len is 9 but the index is 9
Code snippet and code crashed in LoRa::new()
;
``` let iv = GenericSx126xInterfaceVariant::new(nss, reset, dio1, busy, None, None).unwrap();
let mut lora = {
match LoRa::new(
SX1261_2::new(BoardType::RpPicoWaveshareSx1262, lora_spi, iv),
false,
&mut delay,
)
.await
{
Ok(l) => l,
Err(err) => {
info!("Radio error = {}", err);
return;
}
}
};
But it doesn't crash if I set enable_public_network
true.
A trace is given below of stm32wl example lora_lorawan.rs, which is expected to fail here because there is no LoRaWAN gateway with which to communicate. However, the trace does show the setup for chip initialization and transmit/receive operations.
There does not appear to be anything remarkable in the trace, but one thing to verify against The Things Network is that it responds with IQ inverted packets to the join request. The trace does not include pin manipulations (for example, for RF switch settings). It traces write/read operations.
`
---- LoRa chip initialization start ----
0.001617 INFO write: 0x[c0, 0] GetStatus - awake Sx1262
0.001861 INFO write: 0x[80, 0] SetStandby
0.002105 INFO write: 0x[8a, 1] SetPacketType LoRa
0.002380 INFO write: 0x[d, 7, 40, 34, 44] WriteRegister LoRaSyncword LORA_MAC_PUBLIC_SYNCWORD
0.002685 INFO write: 0x[97, 1, 0, 2, 80] SetTCXOMode Ctrl1V7, board wakeup timeout
0.002990 INFO write: 0x[96, 1] SetRegulatorMode UseDCDC
0.003234 INFO write: 0x[8f, 0, 0] SetBufferBaseAddress 0 0
0.003540 INFO write: 0x[1d, 8, d8, 0] ReadRegister TxClampCfg
0.003784 INFO read 1: 0x[de]
0.004058 INFO write: 0x[d, 8, d8, de] WriteRegister TxClampCfg
0.004364 INFO write: 0x[95, 4, 7, 0, 1] SetPAConfig pa_duty_cycle, hp_max, device_sel, pa_lut
0.004669 INFO write: 0x[8e, 0, 4] SetTxParams power, ramp_time (set low during chip initialization)
0.004943 INFO write: 0x[8, ff, ff, ff, ff, 0, 0, 0, 0] CfgDIOIrq all
0.005432 INFO write: 0x[1d, 2, 9f, 0] ReadRegister RetentionList (add RxGain and TxModulation to retention list)
0.005676 INFO read 9: 0x[0, 1c, 4c, d4, 87, c2, bc, 3b, 85]
0.006134 INFO write: 0x[d, 2, 9f] 0x[1, 8, ac, d4, 87, c2, bc, 3b, 85] WriteRegister RetentionList
0.006774 INFO write: 0x[1d, 2, 9f, 0] ReadRegister RetentionList
0.006988 INFO read 9: 0x[1, 8, ac, d4, 87, c2, bc, 3b, 85]
0.007446 INFO write: 0x[d, 2, 9f] 0x[2, 8, ac, 8, 89, c2, bc, 3b, 85] WriteRegister
---- LoRa chip initialization end ----
0.060699 INFO Joining LoRaWAN network
0.062683 INFO write: 0x[8b, c, 4, 1, 1] SetModulationParams spreading_factor, bandwidth_val, coding_rate_val, low_data_rate_optimize
0.063018 INFO write: 0x[1d, 8, 89, 0] ReadRegister TxModulation
0.063232 INFO read 1: 0x[25]
0.063507 INFO write: 0x[d, 8, 89, 25] WriteRegister TxModulation
0.063842 INFO write: 0x[1d, 8, d8, 0] ReadRegister TxClampCfg
0.064086 INFO read 1: 0x[fe]
0.064361 INFO write: 0x[d, 8, d8, fe] WriteRegister TxClampCfg
0.064666 INFO write: 0x[95, 2, 2, 0, 1] SetPAConfig pa_duty_cycle, hp_max, device_sel, pa_lut
0.064971 INFO write: 0x[8e, 16, 2] SetTxParams power, ramp_time
0.065277 INFO write: 0x[8c, 0, 8, 0, 17, 1, 0] SetPacketParams preamble_length (8 here), implicit_header, payload_length, crc_on, iq_inverted
0.078369 INFO write: 0x[98, d7, db] CalibrateImage - values depend on frequency: see calibrate_image()
0.078735 INFO write: 0x[86, 36, 41, 99, 9a] SetRFFrequency - see set_channel() for value
0.079162 INFO write: 0x[e, 0] 0x[join request buffer elided] WriteBuffer with join request
0.079742 INFO write: 0x[8, 2, 1, 2, 1, 0, 0, 0, 0] CfgDIOIrq TxDone and RxTxTimeout
0.091461 INFO write: 0x[83, ff, ff, ff] SetTx no timeout
0.091766 INFO process_irq loop entered
1.573455 INFO write: 0x[12] GetIrqStatus
1.573638 INFO read 2 status 0xac: 0x[0, 1] TxDone
1.573974 INFO write: 0x[2, 0, 1] ClrIrqStatus
1.574188 INFO process_irq satisfied: irq_flags = 1
6.571472 INFO write: 0x[80, 0] SetStandby
6.571807 INFO write: 0x[8b, c, 4, 1, 1] SetModulationParams SetModulationParams spreading_factor, bandwidth_val, coding_rate_val, low_data_rate_optimize
6.572143 INFO write: 0x[1d, 8, 89, 0] ReadRegister TxModulation
6.572387 INFO read 1: 0x[24]
6.572662 INFO write: 0x[d, 8, 89, 24] WriteRegister TxModulation
6.572998 INFO write: 0x[8c, 0, 8, 0, 0, 1, 1] SetPacketParams preamble_length (8 here), implicit_header, payload_length, crc_on, iq_inverted (IQ INVERTED SET)
6.573425 INFO write: 0x[86, 36, 41, 99, 9a] SetRFFrequency - see set_channel() for value
6.573760 INFO write: 0x[8, ff, ff, ff, ff, 0, 0, 0, 0] CfgDIOIrq all
6.574127 INFO write: 0x[9f, 0] SetStopRxTimerOnPreamble false
6.574371 INFO write: 0x[a0, 0] SetLoRaSymbTimeout 0 since rx continuous used
6.574676 INFO write: 0x[1d, 7, 36, 0] ReadRegister IQPolarity
6.574920 INFO read 1: 0x[9]
6.575195 INFO write: 0x[d, 7, 36, 9] WriteRegister IQPolarity
6.575500 INFO write: 0x[d, 8, ac, 94] WriteRegister RxGain - see do_rx() for value
6.587219 INFO write: 0x[82, ff, ff, ff] SetRx rx continuous without timeout
6.587463 INFO process_irq loop entered
6.587707 INFO write: 0x[12] GetIrqStatus unproductive interrupt
6.587921 INFO read 2 status 0xd2: 0x[0, 0]
6.588226 INFO write: 0x[2, 0, 0] ClrIrqStatus
6.588439 INFO process_irq satisfied: irq_flags = 0
6.588592 INFO process_irq loop entered
7.571563 INFO write: 0x[80, 0] SetStandby - this must have happened due to a timeout in rust-lorawan, since lora is still in the irq loop, try again as above
7.571929 INFO write: 0x[8b, c, 4, 1, 1] SetModulationParams
7.572265 INFO write: 0x[1d, 8, 89, 0] ReadRegister TxModulation
7.572509 INFO read 1: 0x[24]
7.572784 INFO write: 0x[d, 8, 89, 24] WriteRegister TxModulation
7.573120 INFO write: 0x[8c, 0, 8, 0, 0, 1, 1] SetPacketParams
7.573516 INFO write: 0x[86, 36, 58, 66, 66] SetRFFrequency
7.573883 INFO write: 0x[8, ff, ff, ff, ff, 0, 0, 0, 0] CfgDIOIrq
7.574249 INFO write: 0x[9f, 0] SetStopRxTimerOnPreamble
7.574493 INFO write: 0x[a0, 0] SetLoRaSymbTimeout
7.574768 INFO write: 0x[1d, 7, 36, 0] ReadRegister IQPolarity
7.575012 INFO read 1: 0x[9]
7.575286 INFO write: 0x[d, 7, 36, 9] WriteRegister IQPolarity
7.575592 INFO write: 0x[d, 8, ac, 94] WriteRegister RxGain
7.587310 INFO write: 0x[82, ff, ff, ff] SetRx
7.587554 INFO process_irq loop entered
8.574554 INFO Radio error = RxTimeout - rust-lorawan apparently gives up after 2 attempts
`
The TCXO control voltage is hard coded in set_oscillator to be 1.7V, but it's normally configurable because different radios use different voltages.
It would be nice to have it controllable.
I'm happy to make a PR if you tell me how you want it to work :)
Hi:
Have you ever considered de possibility to including support for serial LoRa devices such as E32-433T20DT. Y do understand there is already a crate for that. But to be honest i does not play nice with embassy, has full fledged async support and the implementation is missing many features I'll like it to have. If you wish I could contribute. I do understand that this is something out of the scope of what you are achieving right now with the SPI interfaces.
Still any interest ?
Provide a "custom" board type and chip type so that the user can provide a custom RadioKind for a custom LoRa board or extend an existing one. This is partially resolved in PR #16 as a minor update.
However, complete freedom to use a LoRa chip unknown to lora-phy will require a new major release, since the implementations of modulation and packet parameter creation contain logic specific to the radio kind, but is not currently implemented within the RadioKind trait. An update to the RadioKind trait will necessitate a new major release.
Evaluate changes for embedded-hal-async 0.2.0-alpha.1.
Tips:
When running this example, there is a soft lock. It can be reproduced by sending another message while the match is waiting, the rx
function get stuck, and cannot receive any more messages until the micro controller is reset.
Copy line 89 - 98 and paste after line 98 in the lora_p2p_send.rs
file.
Compile and load on the respective pico devices, and after the first message, any messages sent after are lost, and the receive loop does not continue.
(HOST) INFO flashing program (14 pages / 56.00 KiB)
(HOST) INFO success!
(HOST) WARN insufficient DWARF info; compile your program with `debug = 2` to enable location info
(HOST) WARN `defmt::timestamp!` implementation was found, but timestamp is not part of the log format;
────────────────────────────────────────────────────────────────────────────────
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[c0, 0]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[9d, 1]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[80, 0]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8a, 1]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 7, 40, 14, 24]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[97, 1, 0, 2, 80]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[96, 1]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8f, 0, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1d, 8, d8, 0]
└─ <mod path> @ <file>:0
TRACE read 1: 0x[c8]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 8, d8, de]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[95, 4, 7, 0, 1]
└─ <mod path> @ <file>:0
DEBUG tx power = 0
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8e, 0, 4]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8, ff, ff, ff, ff, 0, 0, 0, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1d, 2, 9f, 0]
└─ <mod path> @ <file>:0
TRACE read 9: 0x[0, 44, 11, ff, a3, b0, ed, 18, 7]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 2, 9f] 0x[1, 8, ac, ff, a3, b0, ed, 18, 7]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1d, 2, 9f, 0]
└─ <mod path> @ <file>:0
TRACE read 9: 0x[1, 8, ac, ff, a3, b0, ed, 18, 7]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 2, 9f] 0x[2, 8, ac, 8, 89, b0, ed, 18, 7]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
DEBUG sf = 10, bw = 5, cr = 4
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8b, a, 5, 4, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1d, 8, 89, 0]
└─ <mod path> @ <file>:0
TRACE read 1: 0x[5]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 8, 89, 5]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8c, 0, 4, 0, 64, 1, 0]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[98, e1, e9]
└─ <mod path> @ <file>:0
DEBUG channel = 903900000
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[86, 38, 7e, 66, 66]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[8, ff, ff, ff, ff, 0, 0, 0, 0]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[9f, 0]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[a0, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1d, 7, 36, 0]
└─ <mod path> @ <file>:0
TRACE read 1: 0x[d]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 7, 36, d]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[d, 8, ac, 94]
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[82, ff, ff, ff]
└─ <mod path> @ <file>:0
DEBUG Loop intera
└─ <mod path> @ <file>:0
DEBUG process_irq loop entered
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE EdgeHigh for pin 20 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[12]
└─ <mod path> @ <file>:0
TRACE read 2 status 0xd2: 0x[0, 4]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[2, 0, 4]
└─ <mod path> @ <file>:0
DEBUG process_irq satisfied: irq_flags = 0x4 in radio mode Receive
└─ <mod path> @ <file>:0
DEBUG PreambleDetected in radio mode Receive
└─ <mod path> @ <file>:0
DEBUG process_irq loop entered
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE EdgeHigh for pin 20 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[12]
└─ <mod path> @ <file>:0
TRACE read 2 status 0xd2: 0x[0, 10]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[2, 0, 10]
└─ <mod path> @ <file>:0
DEBUG process_irq satisfied: irq_flags = 0x10 in radio mode Receive
└─ <mod path> @ <file>:0
DEBUG HeaderValid in radio mode Receive
└─ <mod path> @ <file>:0
DEBUG process_irq loop entered
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
TRACE EdgeHigh for pin 20 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[12]
└─ <mod path> @ <file>:0
TRACE read 2 status 0xd4: 0x[0, 2]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[2, 0, 2]
└─ <mod path> @ <file>:0
DEBUG process_irq satisfied: irq_flags = 0x2 in radio mode Receive
└─ <mod path> @ <file>:0
DEBUG RxDone in radio mode Receive
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[13]
└─ <mod path> @ <file>:0
TRACE read 2 status 0xd4: 0x[3, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[1e, 0, 0]
└─ <mod path> @ <file>:0
TRACE read 3: 0x[1, 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
└─ <mod path> @ <file>:0
TRACE LevelLow for pin 2 was cleared, return Poll::Ready
└─ <mod path> @ <file>:0
TRACE write: 0x[14]
└─ <mod path> @ <file>:0
TRACE read 3 status 0xd4: 0x[b8, 21, ba]
└─ <mod path> @ <file>:0
INFO rx successful
└─ <mod path> @ <file>:0
DEBUG Loop intera
└─ <mod path> @ <file>:0
DEBUG process_irq loop entered
└─ <mod path> @ <file>:0
TRACE InputFuture::poll return Poll::Pending
└─ <mod path> @ <file>:0
Ensure a read status error for an IRQ event does not obscure useful information returned by the read. In particular, check that a Tx timeout is not obscured by a read status timeout if the Tx timeout information is actually available from the read. Lacking that, specify the actual OpError rather than just reporting OpError with a numeric parameter.
For LoRa chips which support it, Implement deep sleep for maximum power savings.
Issue #30 has identified a use case where it would be beneficial for the SPI interface to the LoRa chip to share the SPI bus.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.