1
- from .base import BaseLoRa
2
- import spidev
3
- import RPi .GPIO
1
+ from .base import LoRaSpi , LoRaGpio , BaseLoRa
2
+ from typing import Optional
4
3
import time
5
4
6
- spi = spidev .SpiDev ()
7
- gpio = RPi .GPIO
8
- gpio .setmode (RPi .GPIO .BCM )
9
- gpio .setwarnings (False )
10
-
11
5
class SX126x (BaseLoRa ) :
12
6
"""Class for SX1261/62/68 and LLCC68 LoRa chipsets from Semtech"""
13
7
@@ -250,18 +244,10 @@ class SX126x(BaseLoRa) :
250
244
STATUS_CAD_DONE = 12
251
245
252
246
# SPI and GPIO pin setting
253
- _bus = 0
254
- _cs = 0
255
- _reset = 22
256
- _busy = 23
257
- _irq = - 1
258
- _txen = - 1
259
- _rxen = - 1
260
- _wake = - 1
261
247
_busyTimeout = 5000
262
- _spiSpeed = 7800000
263
- _txState = gpio .LOW
264
- _rxState = gpio .LOW
248
+ _irqTimeout = 10000
249
+ _txState = LoRaGpio .LOW
250
+ _rxState = LoRaGpio .LOW
265
251
266
252
# LoRa setting
267
253
_dio = 1
@@ -277,6 +263,7 @@ class SX126x(BaseLoRa) :
277
263
_invertIq = False
278
264
279
265
# Operation properties
266
+ _monitoring = None
280
267
_bufferIndex = 0
281
268
_payloadTxRx = 32
282
269
_statusWait = STATUS_DEFAULT
@@ -287,13 +274,20 @@ class SX126x(BaseLoRa) :
287
274
_onTransmit = None
288
275
_onReceive = None
289
276
277
+ def __init__ (self , spi : LoRaSpi , cs : LoRaGpio , reset : LoRaGpio , busy : LoRaGpio , irq : Optional [LoRaGpio ]= None , txen : Optional [LoRaGpio ]= None , rxen : Optional [LoRaGpio ]= None ):
278
+
279
+ self ._spi = spi
280
+ self ._cs = cs
281
+ self ._reset = reset
282
+ self ._busy = busy
283
+ self ._irq = irq
284
+ self ._txen = txen
285
+ self ._rxen = rxen
286
+
290
287
### COMMON OPERATIONAL METHODS ###
291
288
292
- def begin (self , bus : int = _bus , cs : int = _cs , reset : int = _reset , busy : int = _busy , irq : int = _irq , txen : int = _txen , rxen : int = _rxen , wake : int = _wake ) :
289
+ def begin (self ) -> bool :
293
290
294
- # set spi and gpio pins
295
- self .setSpi (bus , cs )
296
- self .setPins (reset , busy , irq , txen , rxen , wake )
297
291
# perform device reset
298
292
self .reset ()
299
293
@@ -308,15 +302,13 @@ def begin(self, bus: int = _bus, cs: int = _cs, reset: int = _reset, busy: int =
308
302
def end (self ) :
309
303
310
304
self .sleep (self .SLEEP_COLD_START )
311
- spi .close ()
312
- gpio .cleanup ()
313
305
314
306
def reset (self ) -> bool :
315
307
316
308
# put reset pin to low then wait busy pin to low
317
- gpio . output ( self ._reset , gpio .LOW )
309
+ self ._reset . output ( LoRaGpio .LOW )
318
310
time .sleep (0.001 )
319
- gpio . output ( self ._reset , gpio .HIGH )
311
+ self ._reset . output ( LoRaGpio .HIGH )
320
312
return not self .busyCheck ()
321
313
322
314
def sleep (self , option = SLEEP_WARM_START ) :
@@ -329,10 +321,8 @@ def sleep(self, option = SLEEP_WARM_START) :
329
321
def wake (self ) :
330
322
331
323
# wake device by set wake pin (cs pin) to low before spi transaction and put device in standby mode
332
- if (self ._wake != - 1 ) :
333
- gpio .setup (self ._wake , gpio .OUT )
334
- gpio .output (self ._wake , gpio .LOW )
335
- time .sleep (0.0005 )
324
+ self ._cs .output (LoRaGpio .LOW )
325
+ time .sleep (0.0005 )
336
326
self .setStandby (self .STANDBY_RC )
337
327
self ._fixResistanceAntenna ()
338
328
@@ -344,7 +334,7 @@ def busyCheck(self, timeout: int = _busyTimeout) :
344
334
345
335
# wait for busy pin to LOW or timeout reached
346
336
t = time .time ()
347
- while gpio . input ( self ._busy ) == gpio .HIGH :
337
+ while self ._busy . input ( ) == LoRaGpio .HIGH :
348
338
if (time .time () - t ) > (timeout / 1000 ) : return True
349
339
return False
350
340
@@ -358,31 +348,9 @@ def getMode(self) -> int :
358
348
359
349
### HARDWARE CONFIGURATION METHODS ###
360
350
361
- def setSpi (self , bus : int , cs : int , speed : int = _spiSpeed ) :
351
+ def setSpiSpeed (self , speed : int ) :
362
352
363
- self ._bus = bus
364
- self ._cs = cs
365
- self ._spiSpeed = speed
366
- # open spi line and set bus id, chip select, and spi speed
367
- spi .open (bus , cs )
368
- spi .max_speed_hz = speed
369
- spi .lsbfirst = False
370
- spi .mode = 0
371
-
372
- def setPins (self , reset : int , busy : int , irq : int = - 1 , txen : int = - 1 , rxen : int = - 1 , wake : int = - 1 ) :
373
-
374
- self ._reset = reset
375
- self ._busy = busy
376
- self ._irq = irq
377
- self ._txen = txen
378
- self ._rxen = rxen
379
- self ._wake = wake
380
- # set pins as input or output
381
- gpio .setup (reset , gpio .OUT )
382
- gpio .setup (busy , gpio .IN )
383
- if irq != - 1 : gpio .setup (irq , gpio .IN )
384
- if txen != - 1 : gpio .setup (txen , gpio .OUT )
385
- if rxen != - 1 : gpio .setup (rxen , gpio .OUT )
353
+ self ._spi .speed = speed
386
354
387
355
def setRfIrqPin (self , dioPinSelect : int ) :
388
356
@@ -642,11 +610,11 @@ def beginPacket(self) :
642
610
self .setBufferBaseAddress (self ._bufferIndex , (self ._bufferIndex + 0xFF ) % 0xFF )
643
611
644
612
# save current txen and rxen pin state and set txen pin to high and rxen pin to low
645
- if self ._txen != - 1 and self ._rxen != - 1 :
646
- self ._txState = gpio . input ( self ._txen )
647
- self ._rxState = gpio . input ( self ._rxen )
648
- gpio . output ( self ._txen , gpio .HIGH )
649
- gpio . output ( self ._rxen , gpio .LOW )
613
+ if self ._txen != None and self ._rxen != None :
614
+ self ._txState = self ._txen . input ( )
615
+ self ._rxState = self ._rxen . input ( )
616
+ self ._txen . output ( LoRaGpio .HIGH )
617
+ self ._rxen . output ( LoRaGpio .LOW )
650
618
self ._fixLoRaBw500 (self ._bw )
651
619
652
620
def endPacket (self , timeout : int = TX_SINGLE ) -> bool :
@@ -671,9 +639,7 @@ def endPacket(self, timeout: int = TX_SINGLE) -> bool :
671
639
self ._transmitTime = time .time ()
672
640
673
641
# set operation status to wait and attach TX interrupt handler
674
- if self ._irq != - 1 :
675
- gpio .remove_event_detect (self ._irq )
676
- gpio .add_event_detect (self ._irq , gpio .RISING , callback = self ._interruptTx , bouncetime = 10 )
642
+
677
643
return True
678
644
679
645
def write (self , data , length : int = 0 ) :
@@ -724,22 +690,17 @@ def request(self, timeout: int = RX_SINGLE) -> bool :
724
690
self ._statusWait = self .STATUS_RX_CONTINUOUS
725
691
726
692
# save current txen and rxen pin state and set txen pin to low and rxen pin to high
727
- if self ._txen != - 1 and self ._rxen != - 1 :
728
- self ._txState = gpio . input ( self ._txen )
729
- self ._rxState = gpio . input ( self ._rxen )
730
- gpio . output ( self ._txen , gpio .LOW )
731
- gpio . output ( self ._rxen , gpio .HIGH )
693
+ if self ._txen != None and self ._rxen != None :
694
+ self ._txState = self ._txen . input ( )
695
+ self ._rxState = self ._rxen . input ( )
696
+ self ._txen . output ( LoRaGpio .LOW )
697
+ self ._rxen . output ( LoRaGpio .HIGH )
732
698
733
699
# set device to receive mode with configured timeout, single, or continuous operation
734
700
self .setRx (rxTimeout )
735
701
736
702
# set operation status to wait and attach RX interrupt handler
737
- if self ._irq != - 1 :
738
- gpio .remove_event_detect (self ._irq )
739
- if timeout == self .RX_CONTINUOUS :
740
- gpio .add_event_detect (self ._irq , gpio .RISING , callback = self ._interruptRxContinuous , bouncetime = 10 )
741
- else :
742
- gpio .add_event_detect (self ._irq , gpio .RISING , callback = self ._interruptRx , bouncetime = 10 )
703
+
743
704
return True
744
705
745
706
def listen (self , rxPeriod : int , sleepPeriod : int ) -> bool :
@@ -760,19 +721,17 @@ def listen(self, rxPeriod: int, sleepPeriod: int) -> bool :
760
721
if sleepPeriod > 0x00FFFFFF : sleepPeriod = 0x00FFFFFF
761
722
762
723
# save current txen and rxen pin state and set txen pin to low and rxen pin to high
763
- if self ._txen != - 1 and self ._rxen != - 1 :
764
- self ._txState = gpio . input ( self ._txen )
765
- self ._rxState = gpio . input ( self ._rxen )
766
- gpio . output ( self ._txen , gpio .LOW )
767
- gpio . output ( self ._rxen , gpio .HIGH )
724
+ if self ._txen != None and self ._rxen != None :
725
+ self ._txState = self ._txen . input ( )
726
+ self ._rxState = self ._rxen . input ( )
727
+ self ._txen . output ( LoRaGpio .LOW )
728
+ self ._rxen . output ( LoRaGpio .HIGH )
768
729
769
730
# set device to receive mode with configured receive and sleep period
770
731
self .setRxDutyCycle (rxPeriod , sleepPeriod )
771
732
772
733
# set operation status to wait and attach RX interrupt handler
773
- if self ._irq != - 1 :
774
- gpio .remove_event_detect (self ._irq )
775
- gpio .add_event_detect (self ._irq , gpio .RISING , callback = self ._interruptRx , bouncetime = 10 )
734
+
776
735
return True
777
736
778
737
def available (self ) -> int :
@@ -832,7 +791,7 @@ def wait(self, timeout: int = 0) -> bool :
832
791
t = time .time ()
833
792
while irqStat == 0x0000 and self ._statusIrq == 0x0000 :
834
793
# only check IRQ status register for non interrupt operation
835
- if self ._irq == - 1 : irqStat = self .getIrqStatus ()
794
+ if self ._irq == None : irqStat = self .getIrqStatus ()
836
795
# return when timeout reached
837
796
if (time .time () - t ) > timeout and timeout > 0 : return False
838
797
@@ -842,15 +801,15 @@ def wait(self, timeout: int = 0) -> bool :
842
801
elif self ._statusWait == self .STATUS_TX_WAIT :
843
802
# for transmit, calculate transmit time and set back txen and rxen pin to previous state
844
803
self ._transmitTime = time .time () - self ._transmitTime
845
- if self ._txen != - 1 and self ._rxen != - 1 :
846
- gpio . output ( self ._txen , self ._txState )
847
- gpio . output ( self ._rxen , self ._rxState )
804
+ if self ._txen != None and self ._rxen != None :
805
+ self ._txen . output ( self ._txState )
806
+ self ._rxen . output ( self ._rxState )
848
807
elif self ._statusWait == self .STATUS_RX_WAIT :
849
808
# for receive, get received payload length and buffer index and set back txen and rxen pin to previous state
850
809
(self ._payloadTxRx , self ._bufferIndex ) = self .getRxBufferStatus ()
851
- if self ._txen != - 1 and self ._rxen != - 1 :
852
- gpio . output ( self ._txen , self ._txState )
853
- gpio . output ( self ._rxen , self ._rxState )
810
+ if self ._txen != None and self ._rxen != None :
811
+ self ._txen . output ( self ._txState )
812
+ self ._rxen . output ( self ._rxState )
854
813
self ._fixRxTimeout ()
855
814
elif self ._statusWait == self .STATUS_RX_CONTINUOUS :
856
815
# for receive continuous, get received payload length and buffer index and clear IRQ status
@@ -932,27 +891,27 @@ def _irqSetup(self, irqMask) :
932
891
else : dio1Mask = irqMask
933
892
self .setDioIrqParams (irqMask , dio1Mask , dio2Mask , dio3Mask )
934
893
935
- def _interruptTx (self , channel ) :
894
+ def _interruptTx (self ) :
936
895
937
896
# calculate transmit time
938
897
self ._transmitTime = time .time () - self ._transmitTime
939
898
# set back txen and rxen pin to previous state
940
- if self ._txen != - 1 and self ._rxen != - 1 :
941
- gpio . output ( self ._txen , self ._txState )
942
- gpio . output ( self ._rxen , self ._rxState )
899
+ if self ._txen != None and self ._rxen != None :
900
+ self ._txen . output ( self ._txState )
901
+ self ._rxen . output ( self ._rxState )
943
902
# store IRQ status
944
903
self ._statusIrq = self .getIrqStatus ()
945
904
946
905
# call onTransmit function
947
906
if callable (self ._onTransmit ) :
948
907
self ._onTransmit ()
949
908
950
- def _interruptRx (self , channel ) :
909
+ def _interruptRx (self ) :
951
910
952
911
# set back txen and rxen pin to previous state
953
- if self ._txen != - 1 and self ._rxen != - 1 :
954
- gpio . output ( self ._txen , self ._txState )
955
- gpio . output ( self ._rxen , self ._rxState )
912
+ if self ._txen != None and self ._rxen != None :
913
+ self ._txen . output ( self ._txState )
914
+ self ._rxen . output ( self ._rxState )
956
915
self ._fixRxTimeout ()
957
916
# store IRQ status
958
917
self ._statusIrq = self .getIrqStatus ()
@@ -963,7 +922,7 @@ def _interruptRx(self, channel) :
963
922
if callable (self ._onReceive ) :
964
923
self ._onReceive ()
965
924
966
- def _interruptRxContinuous (self , channel ) :
925
+ def _interruptRxContinuous (self ) :
967
926
968
927
# store IRQ status
969
928
self ._statusIrq = self .getIrqStatus ()
@@ -1274,12 +1233,16 @@ def _writeBytes(self, opCode: int, data: tuple, nBytes: int) :
1274
1233
if self .busyCheck () : return
1275
1234
buf = [opCode ]
1276
1235
for i in range (nBytes ) : buf .append (data [i ])
1277
- spi .xfer2 (buf )
1236
+ self ._cs .output (LoRaGpio .LOW )
1237
+ self ._spi .transfer (buf )
1238
+ self ._cs .output (LoRaGpio .HIGH )
1278
1239
1279
1240
def _readBytes (self , opCode : int , nBytes : int , address : tuple = (), nAddress : int = 0 ) -> tuple :
1280
1241
if self .busyCheck () : return ()
1281
1242
buf = [opCode ]
1282
1243
for i in range (nAddress ) : buf .append (address [i ])
1283
1244
for i in range (nBytes ) : buf .append (0x00 )
1284
- feedback = spi .xfer2 (buf )
1245
+ self ._cs .output (LoRaGpio .LOW )
1246
+ feedback = self ._spi .transfer (buf )
1247
+ self ._cs .output (LoRaGpio .HIGH )
1285
1248
return tuple (feedback [nAddress + 1 :])
0 commit comments