1+ /* Heltec Automation LoRaWAN communication example
2+ *
3+ * Function:
4+ * 1. Upload node data to the server using the standard LoRaWAN protocol.
5+ *
6+ * Description:
7+ * 1. Communicate using LoRaWAN protocol.
8+ *
9+ * HelTec AutoMation, Chengdu, China
10+ * 成都惠利特自动化科技有限公司
11+ * www.heltec.org
12+ *
13+ * */
14+
15+ #include " LoRaWan_APP.h"
16+ int sensorData = 0 ;
17+ uint8_t confirmedNbTrials = 8 ;
18+ const int hallSensorPin = 21 ; // Connect the GPIO pin of the Hall sensor
19+ volatile int counter = 0 ; // Counter, used to record the number of changes in high and low levels
20+ volatile unsigned long lastInterruptTime = 0 ; // Record the last trigger time
21+ const unsigned long debounceTime = 50 ; // Anti shake delay time (milliseconds)
22+ const unsigned long measurementInterval = 30000 ; // Measurement time interval (30 seconds)
23+
24+ unsigned long startTime = 0 ; // Timing start time
25+ /* OTAA para*/
26+ uint8_t devEui[] = { 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xE8 };
27+ uint8_t appEui[] = { 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 };
28+ uint8_t appKey[] = { 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 , 0x88 };
29+
30+ /* ABP para*/
31+ uint8_t nwkSKey[] = { 0x15 , 0xb1 , 0xd0 , 0xef , 0xa4 , 0x63 , 0xdf , 0xbe , 0x3d , 0x11 , 0x18 , 0x1e , 0x1e , 0xc7 , 0xda ,0x85 };
32+ uint8_t appSKey[] = { 0xd7 , 0x2c , 0x78 , 0x75 , 0x8c , 0xdc , 0xca , 0xbf , 0x55 , 0xee , 0x4a , 0x77 , 0x8d , 0x16 , 0xef ,0x67 };
33+ uint32_t devAddr = ( uint32_t )0x007e6ae1 ;
34+
35+ /* LoraWan channelsmask, default channels 0-7*/
36+ uint16_t userChannelsMask[6 ]={ 0x00FF ,0x0000 ,0x0000 ,0x0000 ,0x0000 ,0x0000 };
37+
38+ /* LoraWan region, select in arduino IDE tools*/
39+ LoRaMacRegion_t loraWanRegion = ACTIVE_REGION;
40+
41+ /* LoraWan Class, Class A and Class C are supported*/
42+ DeviceClass_t loraWanClass = CLASS_A;
43+
44+ /* the application data transmission duty cycle. value in [ms].*/
45+ uint32_t appTxDutyCycle = 15000 ;
46+
47+ /* OTAA or ABP*/
48+ bool overTheAirActivation = true ;
49+
50+ /* ADR enable*/
51+ bool loraWanAdr = true ;
52+
53+ /* Indicates if the node is sending confirmed or unconfirmed messages */
54+ bool isTxConfirmed = true ;
55+
56+ /* Application port */
57+ uint8_t appPort = 2 ;
58+ /* !
59+ * Number of trials to transmit the frame, if the LoRaMAC layer did not
60+ * receive an acknowledgment. The MAC performs a datarate adaptation,
61+ * according to the LoRaWAN Specification V1.0.2, chapter 18.4, according
62+ * to the following table:
63+ *
64+ * Transmission nb | Data Rate
65+ * ----------------|-----------
66+ * 1 (first) | DR
67+ * 2 | DR
68+ * 3 | max(DR-1,0)
69+ * 4 | max(DR-1,0)
70+ * 5 | max(DR-2,0)
71+ * 6 | max(DR-2,0)
72+ * 7 | max(DR-3,0)
73+ * 8 | max(DR-3,0)
74+ *
75+ * Note, that if NbTrials is set to 1 or 2, the MAC will not decrease
76+ * the datarate, in case the LoRaMAC layer did not receive an acknowledgment
77+ */
78+
79+ void IRAM_ATTR handleInterrupt () {
80+ unsigned long currentTime = millis ();
81+
82+
83+ if (currentTime - lastInterruptTime > debounceTime) {
84+ counter++;
85+ lastInterruptTime = currentTime;
86+ }
87+ }
88+
89+ /* Prepares the payload of the frame */
90+
91+ static void prepareTxFrame (uint8_t port) {
92+ if (millis () - startTime >= measurementInterval) {
93+ Serial.printf (" Switching frequency: %d\n " , counter);
94+
95+ // Encapsulate Hall sensor data counter
96+ appDataSize = 0 ;
97+ unsigned char *puc;
98+ appData[appDataSize++] = 0x00 ; // parent ID
99+ appData[appDataSize++] = 0x00 ; // parent ID
100+ appData[appDataSize++] = 0x05 ; // sensor length
101+ appData[appDataSize++] = 0x00 ;
102+
103+ puc = (unsigned char *)(&counter);
104+ appData[appDataSize++] = puc[3 ];
105+ appData[appDataSize++] = puc[2 ];
106+ appData[appDataSize++] = puc[1 ];
107+ appData[appDataSize++] = puc[0 ];
108+
109+ Serial.print (" Sending data: " );
110+ for (int i = 0 ; i < appDataSize; i++) {
111+ Serial.print (appData[i], HEX);
112+ Serial.print (" " );
113+ }
114+ Serial.println ();
115+
116+ // Ensure that the total size does not exceed the maximum limit
117+ if (appDataSize > LORAWAN_APP_DATA_MAX_SIZE) {
118+ appDataSize = LORAWAN_APP_DATA_MAX_SIZE;
119+ }
120+ counter = 0 ;
121+ startTime = millis ();
122+ }
123+ }
124+
125+ void setup () {
126+ Serial.begin (115200 );
127+ while (!Serial) {
128+ delay (10 );
129+ }
130+ Mcu.begin (HELTEC_BOARD,SLOW_CLK_TPYE);
131+ pinMode (hallSensorPin, INPUT);
132+ attachInterrupt (digitalPinToInterrupt (hallSensorPin), handleInterrupt, RISING);
133+ startTime = millis ();
134+ }
135+
136+ void loop ()
137+ {
138+ switch ( deviceState )
139+ {
140+ case DEVICE_STATE_INIT:
141+ {
142+ #if (LORAWAN_DEVEUI_AUTO)
143+ LoRaWAN.generateDeveuiByChipID ();
144+ #endif
145+ LoRaWAN.init (loraWanClass,loraWanRegion);
146+ // both set join DR and DR when ADR off
147+ LoRaWAN.setDefaultDR (3 );
148+ break ;
149+ }
150+ case DEVICE_STATE_JOIN:
151+ {
152+ LoRaWAN.join ();
153+ break ;
154+ }
155+ case DEVICE_STATE_SEND:
156+ {
157+ prepareTxFrame (appPort);
158+ LoRaWAN.send ();
159+ deviceState = DEVICE_STATE_CYCLE;
160+ break ;
161+ }
162+ case DEVICE_STATE_CYCLE:
163+ {
164+ // Schedule next packet transmission
165+ txDutyCycleTime = appTxDutyCycle + randr ( -APP_TX_DUTYCYCLE_RND, APP_TX_DUTYCYCLE_RND );
166+ LoRaWAN.cycle (txDutyCycleTime);
167+ deviceState = DEVICE_STATE_SLEEP;
168+ break ;
169+ }
170+ case DEVICE_STATE_SLEEP:
171+ {
172+ LoRaWAN.sleep (loraWanClass);
173+ break ;
174+ }
175+ default :
176+ {
177+ deviceState = DEVICE_STATE_INIT;
178+ break ;
179+ }
180+ }
181+ }
0 commit comments