浏览代码

Add handling of the salt

On start-up the sensor sends a Get_Salt-message to the base station. The
base station responds and sends the salt, which the sensor uses from
there on.
Bernd Gottschlag 5 年前
父节点
当前提交
4f83ec8bef

+ 120
- 29
weather-sensor/firmware/main.c 查看文件

36
 volatile uint8_t executionFlag;
36
 volatile uint8_t executionFlag;
37
 
37
 
38
 
38
 
39
-
40
-static PACKET reportPacket;
39
+static uint8_t messageBuffer[PACKET_LENGTH];
40
+static PACKET * packet = (PACKET*) messageBuffer;
41
 
41
 
42
 
42
 
43
 void Enter_Power_Save_Mode(void);
43
 void Enter_Power_Save_Mode(void);
44
 void Exit_Power_Save_Mode(void);
44
 void Exit_Power_Save_Mode(void);
45
 
45
 
46
 
46
 
47
-/* TODO Notes for power saving:
48
- * - Power-save-mode needed -> SM2...0 bits written to 011
49
- * - Entering by issuing the SLEEP instruction -> What call in C?
50
- *   - Before executing the SLEEP instruction, write bit SE of the SMCR to 1
51
- * - Let Timer/Counter2 run with the necessary period and enable an interrupt.
52
- *   -> The Global Interrupt Enable bit in SREG has to be set.
53
- * - asynchronous/synchronous clock source?
54
- * - When waking up
55
- *   - Set PRR bits for needed peripherals
56
- * - 
57
- */
47
+bool Send_Get_Salt_Message(PACKET * packet, uint64_t salt); //TODO: put into own file
48
+bool Read_Salt_Message(PACKET * packet, uint64_t * salt);
49
+
58
 void Set_Up_Power_Save_Mode(void);
50
 void Set_Up_Power_Save_Mode(void);
59
 void Enter_Power_Save_Mode(void);
51
 void Enter_Power_Save_Mode(void);
60
 
52
 
73
 {
65
 {
74
 	struct bme280_data sensorData;
66
 	struct bme280_data sensorData;
75
 	uint16_t crc;
67
 	uint16_t crc;
68
+	bool saltReceived = false;
76
 
69
 
77
 	/* Enable the debug LED */
70
 	/* Enable the debug LED */
78
 	LED_DDR |= (1 << LED_PIN);
71
 	LED_DDR |= (1 << LED_PIN);
96
 	Set_Up_Power_Save_Mode();
89
 	Set_Up_Power_Save_Mode();
97
 
90
 
98
 	/* Initialize the salt */
91
 	/* Initialize the salt */
99
-	salt = 0xFFFFFFFFFFFFFF00ull;
92
+	salt = 0x0ull;
100
 	salt |= ownId;
93
 	salt |= ownId;
101
 
94
 
95
+
96
+	/* TODO: Request a salt from the base station:
97
+	 * - loop as long as no reply from the base station was received:
98
+	 *   - send the packet that requests the salt
99
+	 *   - if no ack is received for the packet go direclty to sleep for 100 ms
100
+	 *   - if no salt is received within 100 ms send the message again
101
+	 *   - keep the LED on for the duration to allow the user to see that the device is ready for operation.
102
+	 */
103
+	LED_PORT |= (1 << LED_PIN);
104
+	do
105
+	{
106
+		if (Send_Get_Salt_Message(packet, salt) == true)
107
+		{
108
+			memset(messageBuffer, 0x0F, 32);
109
+			if (NRF24L01_Receive_Message(messageBuffer, 100 /*ms*/) == true)
110
+			{
111
+				_delay_ms(10);
112
+				saltReceived = Read_Salt_Message(packet, &salt);
113
+			}
114
+		}
115
+		else
116
+		{
117
+			/* TODO: enter power save mode instead to make the battery life longer */
118
+			_delay_ms(100);
119
+		}
120
+	} while (saltReceived == false);
121
+	LED_PORT &= ~(1 << LED_PIN);
122
+
123
+	salt &= 0xFFFFFFFFFFFFFF00ull;
124
+	salt |= ownId;
125
+
126
+
102
 	/* Delay the change of the operating frequency by the function Enter_Power_Save_Mode for the
127
 	/* Delay the change of the operating frequency by the function Enter_Power_Save_Mode for the
103
 	 * first function pass. If it is changed before the ISP can flash the MCU the clocks of the ISP
128
 	 * first function pass. If it is changed before the ISP can flash the MCU the clocks of the ISP
104
 	 * and MCU are mismatched and the flashing will fail.
129
 	 * and MCU are mismatched and the flashing will fail.
120
 			BME280_Get_Measurement(&sensorData);
145
 			BME280_Get_Measurement(&sensorData);
121
 
146
 
122
 
147
 
123
-			memset((uint8_t*)&reportPacket, 0, sizeof(reportPacket)); //Reinitialize the buffer with zeros
148
+			/* TODO: put the following into a Send_Report function */
149
+			memset((uint8_t*)packet, 0, PACKET_LENGTH); //Reinitialize the buffer with zeros
124
 
150
 
125
 			salt &= ~(1ull<<63);
151
 			salt &= ~(1ull<<63);
126
-			reportPacket.salt = salt;
127
-			reportPacket.payload.values.packetIdentifier.elementCount = 3;
128
-			reportPacket.payload.values.packetIdentifier.packetType = PACKET_TYPE_REPORT;
152
+			packet->salt = salt;
153
+			packet->payload.reportData.packetIdentifier.elementCount = 3;
154
+			packet->payload.reportData.packetIdentifier.packetType = PACKET_TYPE_REPORT;
129
 
155
 
130
 			/* Fill in the payload */
156
 			/* Fill in the payload */
131
-			reportPacket.payload.values.valueTypeTemperature = VALUE_TYPE_TEMPERATURE;
132
-			reportPacket.payload.values.temperature = sensorData.temperature/10;
133
-			reportPacket.payload.values.valueTypePressure = VALUE_TYPE_PRESSURE;
134
-			reportPacket.payload.values.pressure = sensorData.pressure;
135
-			reportPacket.payload.values.valueTypeHumidity = VALUE_TYPE_HUMIDITY;
136
-			reportPacket.payload.values.humidity = sensorData.humidity * 100/1024;
157
+			packet->payload.reportData.valueTypeTemperature = VALUE_TYPE_TEMPERATURE;
158
+			packet->payload.reportData.temperature = sensorData.temperature/10;
159
+			packet->payload.reportData.valueTypePressure = VALUE_TYPE_PRESSURE;
160
+			packet->payload.reportData.pressure = sensorData.pressure;
161
+			packet->payload.reportData.valueTypeHumidity = VALUE_TYPE_HUMIDITY;
162
+			packet->payload.reportData.humidity = sensorData.humidity * 100/1024;
137
 
163
 
138
 			/* Calculate the CRC */
164
 			/* Calculate the CRC */
139
-			crc = Calculate_Crc(reportPacket.payload.buffer, PACKET_BUFFER_LENGTH);
140
-			reportPacket.crc = crc;
165
+			crc = Calculate_Crc(packet->payload.buffer, PACKET_PAYLOAD_BUFFER_LENGTH);
166
+			packet->crc = crc;
141
 
167
 
142
 			/* Encrypt the packet */
168
 			/* Encrypt the packet */
143
 			/* TODO: 
169
 			/* TODO: 
144
 			 * - increment the salt for every packet
170
 			 * - increment the salt for every packet
145
 			 * - Receive salt from the base station
171
 			 * - Receive salt from the base station
146
 			 */
172
 			 */
147
-			Encrypt((uint32_t*) &reportPacket.payload.buffer,
148
-			        PACKET_BUFFER_LENGTH + sizeof(crc),
173
+			Encrypt((uint32_t*) packet->payload.buffer,
174
+			        PACKET_PAYLOAD_BUFFER_LENGTH + sizeof(crc),
149
 			        salt, (uint32_t*) encryptionKey);
175
 			        salt, (uint32_t*) encryptionKey);
150
 
176
 
151
-			NRF24L01_Send_Message((uint8_t*)&reportPacket, sizeof(reportPacket));
177
+			NRF24L01_Send_Message((uint8_t*)packet, PACKET_LENGTH);
152
 
178
 
179
+			/* Increment salt */
180
+			salt += (1 << 8);
181
+
182
+			LED_PORT |= (1 << LED_PIN);
153
 			_delay_ms(100); /* TODO: only for debugging, remove this later! */
183
 			_delay_ms(100); /* TODO: only for debugging, remove this later! */
154
 			LED_PORT &= ~(1 << LED_PIN);
184
 			LED_PORT &= ~(1 << LED_PIN);
155
 
185
 
225
 	PRR &= ~(1<<PRSPI); // Enable SPI
255
 	PRR &= ~(1<<PRSPI); // Enable SPI
226
 	Initialize_SPI(); // reinitalize SPI
256
 	Initialize_SPI(); // reinitalize SPI
227
 }
257
 }
258
+
259
+bool Send_Get_Salt_Message(PACKET * packet, uint64_t salt) //TODO: put into own file
260
+{
261
+	bool success = false;
262
+	uint16_t crc;
263
+
264
+	memset((uint8_t*)packet, 0, PACKET_LENGTH); //Reinitialize the buffer with zeros
265
+
266
+	salt &= ~(1ull<<63); /* Set the most significant bit to 0 to indicate a packet from the device to the base station */
267
+
268
+	packet->salt = salt;
269
+	packet->payload.reportData.packetIdentifier.elementCount = 0;
270
+	packet->payload.reportData.packetIdentifier.packetType = PACKET_TYPE_GET_SALT;
271
+
272
+	/* Calculate the CRC */
273
+	crc = Calculate_Crc(packet->payload.buffer, PACKET_PAYLOAD_BUFFER_LENGTH);
274
+	packet->crc = crc;
275
+
276
+	Encrypt((uint32_t*) packet->payload.buffer,
277
+	        PACKET_PAYLOAD_BUFFER_LENGTH + sizeof(crc),
278
+	        salt,
279
+	        (uint32_t*) encryptionKey);
280
+
281
+	success = NRF24L01_Send_Message((uint8_t*)packet, PACKET_LENGTH);
282
+
283
+
284
+	return success;
285
+}
286
+
287
+bool Read_Salt_Message(PACKET * packet, uint64_t * salt)
288
+{
289
+	uint16_t crcRemainder = 0xFFFF;
290
+	uint64_t baseStationSalt = 0x0;
291
+
292
+
293
+	/* TODO: check that the packet originated from the base station by checking the id */
294
+
295
+	baseStationSalt = packet->salt;
296
+	Decrypt((uint32_t*)packet->payload.buffer,
297
+	        PACKET_PAYLOAD_BUFFER_LENGTH + sizeof(packet->crc),
298
+	        baseStationSalt,
299
+	        (uint32_t*) encryptionKey);
300
+
301
+	crcRemainder = Calculate_Crc(packet->payload.buffer,
302
+	                             PACKET_PAYLOAD_BUFFER_LENGTH + sizeof(packet->crc));
303
+	if (crcRemainder != 0)
304
+	{
305
+		return false;
306
+	}
307
+
308
+	if ((packet->payload.saltData.packetIdentifier.packetType != PACKET_TYPE_SALT) ||
309
+	    (packet->payload.saltData.packetIdentifier.elementCount != 0))
310
+	{
311
+		return false;
312
+	}
313
+
314
+	memcpy((uint8_t*)salt, packet->payload.saltData.salt, 7);
315
+	*salt = (*salt) << 8;
316
+
317
+	return true;
318
+}

+ 150
- 70
weather-sensor/firmware/nrf24l01.c 查看文件

17
 extern volatile bool nrfInterruptRaised;
17
 extern volatile bool nrfInterruptRaised;
18
 
18
 
19
 void Print_Register_Contents(uint8_t address);
19
 void Print_Register_Contents(uint8_t address);
20
+
21
+
20
 void Send_TX_Flush_Command(void);
22
 void Send_TX_Flush_Command(void);
23
+void Send_RX_Flush_Command(void);
21
 
24
 
22
-static void Write_Two_Bytes(uint8_t byte1, uint8_t byte2);
25
+static uint8_t Write_One_Byte(uint8_t byte1);
26
+static uint8_t Write_Two_Bytes(uint8_t byte1, uint8_t byte2);
23
 static void Write_Byte_And_Buffer(uint8_t byte, uint8_t * buffer, uint8_t length);
27
 static void Write_Byte_And_Buffer(uint8_t byte, uint8_t * buffer, uint8_t length);
24
 
28
 
25
 /* Startup and initial configuration of the NRF24L01 */
29
 /* Startup and initial configuration of the NRF24L01 */
72
 	DYNPD_REGISTER dyndpRegisterContents = {.byte = 0x0};
76
 	DYNPD_REGISTER dyndpRegisterContents = {.byte = 0x0};
73
 
77
 
74
 	uint8_t txAddress[5] = {0xB3, 0xB3, 0xB3, 0xB3, 0x00};
78
 	uint8_t txAddress[5] = {0xB3, 0xB3, 0xB3, 0xB3, 0x00};
75
-	uint8_t rx0Address[5] = {0xB3, 0xB3, 0xB3, 0xB3, 0x00};
76
-	/* 
77
-	 * - Length of CRC (CRCO in CONFIG)
78
-	 * - Enable auto acknowledgment (EN_AA)
79
-	 *   -> Register already set correctly after reset
80
-	 * - Enable data pipes (EN_RXADDR)?
81
-	 *   -> Two pipes are already enabled on reset
82
-	 * - Set up address width (SETUP_AW)
83
-	 *   -> 3 bytes
84
-	 * - Automatic Retransmission (SETUP_RETR)
85
-	 *   -> ARD = 0b0000
86
-	 *   -> 3 retransmits -> ARC = 0b0011
87
-	 *   -> Register already set correctly after reset
88
-	 * - RF Channel (RF_CH)
89
-	 *   -> RF_CH = 0b1010000
90
-	 * - RF Setup (RF_SETUP)
91
-	 *   -> first use reset values, can be fine tuned later
92
-	 * - Enable dynamic payload length (DYNPD) -> command activate + 0x73, then set bits in FEATURE?
93
-	 */
94
-
95
-	/* Set the address width to 3 bytes */
96
-	//Write_NRF_Register(0x03, 0x1);
79
+	uint8_t rx1Address[5] = {0xB3, 0xB3, 0xB3, 0xB3, 0x00};
97
 
80
 
98
 	/* Set the frequency to 1450 MHz */
81
 	/* Set the frequency to 1450 MHz */
99
 	Write_NRF_Register(RF_CH_ADDRESS, 0x32);
82
 	Write_NRF_Register(RF_CH_ADDRESS, 0x32);
116
 	Write_NRF_Register(DYNPD_ADDRESS, dyndpRegisterContents.byte);
99
 	Write_NRF_Register(DYNPD_ADDRESS, dyndpRegisterContents.byte);
117
 
100
 
118
 	/* Set up the auto retries */
101
 	/* Set up the auto retries */
119
-
120
-	/* */
121
 	setupRetrRegisterContents.bits.ARC = 0x3;
102
 	setupRetrRegisterContents.bits.ARC = 0x3;
122
 	setupRetrRegisterContents.bits.ARD = 0xF;
103
 	setupRetrRegisterContents.bits.ARD = 0xF;
123
 	Write_NRF_Register(SETUP_RETR_ADDRESS, setupRetrRegisterContents.byte);
104
 	Write_NRF_Register(SETUP_RETR_ADDRESS, setupRetrRegisterContents.byte);
125
 	/* Set the TX address */
106
 	/* Set the TX address */
126
 	Set_TX_Address(txAddress, MAX_ADDRESS_LENGTH);
107
 	Set_TX_Address(txAddress, MAX_ADDRESS_LENGTH);
127
 
108
 
128
-	/* Set the RX_P0 address to the one of the base station to receive acks */
129
-	Set_RX_P0_Address(rx0Address, MAX_ADDRESS_LENGTH);
109
+	/* Set the address of the RX pipe 0 to the one of the base station to receive acks */
110
+	Set_RX_P0_Address(txAddress, MAX_ADDRESS_LENGTH);
111
+
112
+	/* Set the address of the RX pipe 1 to the own address to receive messages */
113
+	rx1Address[4] = moduleId; // The last byte of the address corresponds to the Id set by the pin programming
114
+	Set_RX_P1_Address(rx1Address, MAX_ADDRESS_LENGTH);
115
+
116
+	/* Enable the rx addresses for pipe 0 and pipe 1*/
117
+	enableRxAddressesRegisterContents.bits.ERX_P0 = 1;
118
+	enableRxAddressesRegisterContents.bits.ERX_P1 = 1;
119
+	Write_NRF_Register(EN_RXADDR_ADDRESS, enableRxAddressesRegisterContents.byte);
120
+
121
+	/* Set the payload witth for pipe 1 */
122
+	rxPwPnRegisterContents.bits.RX_PW_Pn = 32;
123
+	Write_NRF_Register(RX_PW_P1_ADDRESS, rxPwPnRegisterContents.byte);
124
+
125
+	rxPwPnRegisterContents.bits.RX_PW_Pn = 0;
126
+	Write_NRF_Register(RX_PW_P0_ADDRESS, rxPwPnRegisterContents.byte); // auto-ack pipe
127
+	Write_NRF_Register(RX_PW_P2_ADDRESS, rxPwPnRegisterContents.byte); // not used
128
+	Write_NRF_Register(RX_PW_P3_ADDRESS, rxPwPnRegisterContents.byte); // not used
129
+	Write_NRF_Register(RX_PW_P4_ADDRESS, rxPwPnRegisterContents.byte); // not used
130
+	Write_NRF_Register(RX_PW_P5_ADDRESS, rxPwPnRegisterContents.byte); // not used
131
+
132
+	/* Enable auto acknowledge for pipe 1 */
133
+	enAaRegister.bits.ENAA_P0 = 1;
134
+	enAaRegister.bits.ENAA_P1 = 1;
135
+	enAaRegister.bits.ENAA_P2 = 1;
136
+	enAaRegister.bits.ENAA_P3 = 1;
137
+	enAaRegister.bits.ENAA_P4 = 1;
138
+	enAaRegister.bits.ENAA_P5 = 1;
139
+	Write_NRF_Register(EN_AA_ADDRESS, enAaRegister.byte);
140
+
141
+	/* Flush FIFOs */
142
+	Send_TX_Flush_Command();
143
+	Send_RX_Flush_Command();
130
 
144
 
131
 
145
 
132
 	PCMSK2 |= (1<<PCINT21); // Set the external interrupt for PD5
146
 	PCMSK2 |= (1<<PCINT21); // Set the external interrupt for PD5
133
 }
147
 }
134
 
148
 
135
-void NRF24L01_Send_Message(uint8_t *buffer, uint8_t length)
149
+bool NRF24L01_Send_Message(uint8_t *buffer, uint8_t length)
136
 {
150
 {
151
+	bool success = false;
137
 	STATUS_REGISTER statusRegisterContents = {.byte = 0x0};
152
 	STATUS_REGISTER statusRegisterContents = {.byte = 0x0};
138
 	
153
 	
139
 	if ((length > 32) || (length == 0))
154
 	if ((length > 32) || (length == 0))
140
 	{
155
 	{
141
-		return;
156
+		return success;
142
 	}
157
 	}
143
 
158
 
144
 	PCICR |= (1<<PCIE2); // Enable the interrupt for the IRQ signal
159
 	PCICR |= (1<<PCIE2); // Enable the interrupt for the IRQ signal
155
 	 * induced by the SPI:
170
 	 * induced by the SPI:
156
 	 * https://forum.mysensors.org/topic/10452/nrf24l01-communication-failure-root-cause-and-solution
171
 	 * https://forum.mysensors.org/topic/10452/nrf24l01-communication-failure-root-cause-and-solution
157
 	 */
172
 	 */
158
-	LED_PORT |= (1 << LED_PIN);
159
 
173
 
160
 	statusRegisterContents.byte = Read_NRF_Status_Register();
174
 	statusRegisterContents.byte = Read_NRF_Status_Register();
161
 
175
 
164
 	{
178
 	{
165
 		Send_TX_Flush_Command(); /* Remove the packet from the TX FIFO as it is not done automatically */
179
 		Send_TX_Flush_Command(); /* Remove the packet from the TX FIFO as it is not done automatically */
166
 	}
180
 	}
181
+	else
182
+	{
183
+		success = true;
184
+	}
167
 	
185
 	
168
 
186
 
169
 	/* Reset the interrupts */
187
 	/* Reset the interrupts */
176
 	nrfInterruptRaised = false;
194
 	nrfInterruptRaised = false;
177
 
195
 
178
 
196
 
179
-	return;
197
+	return success;
180
 }
198
 }
181
 
199
 
182
-uint8_t Read_NRF_Status_Register(void)
200
+bool NRF24L01_Receive_Message(uint8_t *buffer, uint8_t duration)
183
 {
201
 {
184
-	uint8_t registerContents;
202
+	uint8_t messageReceived = false;
203
+	CONFIG_REGISTER configRegisterContents = {.byte = 0x0};
204
+	STATUS_REGISTER statusRegisterContents = {.byte = 0x0};
205
+	FIFO_STATUS_REGISTER fifoStatusRegisterContents = {.byte = 0x0};
185
 
206
 
186
-	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
187
-	registerContents = SPI_Transfer_Byte(0x00);
188
-	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
189
-	return registerContents;
190
-}
207
+	PCICR |= (1<<PCIE2); // Enable the interrupt for the IRQ signal
191
 
208
 
209
+	// Enable the receive mode
210
+	configRegisterContents.byte = Read_NRF_Register(CONFIG_ADDRESS);
211
+	configRegisterContents.bits.PRIM_RX = 0x1;
212
+	Write_NRF_Register(CONFIG_ADDRESS, configRegisterContents.byte);
192
 
213
 
193
-/* TODO: rewrite the read register function if it is needed (remove the read operations for the 5-byte registers)*/
194
-#if 0
195
-uint8_t Read_NRF_Register(uint8_t address, uint8_t * registerContents)
196
-{
197
-	/* TODO: simplify this function, as the registers with more than one byte are accessed with other functions */
198
-	uint8_t numberOfBytes = 0;
199
 
214
 
200
-	if ((address == 0x0A) ||
201
-	    (address == 0x0B) ||
202
-	    (address == 0x10))
215
+	NRF_CE_PORT |= (1 << NRF_CE_PIN);
216
+
217
+	_delay_ms(10);
218
+	while ((nrfInterruptRaised == false) && (duration > 0))
203
 	{
219
 	{
204
-		numberOfBytes = 5;
205
-	}
206
-	else
220
+		_delay_ms(1);
221
+		duration --;
222
+	};
223
+
224
+	if (nrfInterruptRaised == true) // check if a message was received
207
 	{
225
 	{
208
-		numberOfBytes = 1;
226
+		/* A message was received */
227
+
228
+		statusRegisterContents.byte = Read_NRF_Status_Register();
229
+
230
+		fifoStatusRegisterContents.byte = Read_NRF_Register(FIFO_STATUS_ADDRESS);
231
+		if (fifoStatusRegisterContents.bits.RX_EMPTY != 1)
232
+		{
233
+			messageReceived = true;
234
+		}
235
+
236
+		nrfInterruptRaised = false;
209
 	}
237
 	}
210
 
238
 
211
-	/* First write the address */
212
-	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
239
+	// Set the NRF to standby
240
+	NRF_CE_PORT &= ~(1 << NRF_CE_PIN);
213
 
241
 
242
+	configRegisterContents.byte = Read_NRF_Register(CONFIG_ADDRESS);
243
+	configRegisterContents.bits.PRIM_RX = 0x0;
244
+	Write_NRF_Register(CONFIG_ADDRESS, configRegisterContents.byte);
214
 
245
 
215
-	SPI_Transfer_Byte(address);
246
+	PCICR &= ~(1<<PCIE2); // Disable the interrupt for the IRQ signal
216
 
247
 
217
-	/* Read the register bytes */
218
-	for (uint8_t i = 0; i < numberOfBytes; i++)
248
+	if (messageReceived == true)
219
 	{
249
 	{
220
-		/* Write dummy data to shift in the register content */
221
-		registerContents[i] = SPI_Transfer_Byte(0x0);
250
+		Read_Message_From_RX_FIFO(PACKET_LENGTH, buffer); /* TODO: only possible after CE = 0? */
222
 	}
251
 	}
223
 
252
 
224
-	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
253
+	/* Reset the interrupts */
254
+	statusRegisterContents.bits.TX_DS = 1;
255
+	statusRegisterContents.bits.MAX_RT = 1;
256
+	statusRegisterContents.bits.RX_DR = 1;
257
+	Write_NRF_Register(STATUS_ADDRESS, statusRegisterContents.byte);
225
 
258
 
226
-	return numberOfBytes;
259
+	return messageReceived;
227
 }
260
 }
228
 
261
 
229
-#endif
262
+uint8_t Read_NRF_Status_Register(void)
263
+{
264
+	uint8_t registerContents;
265
+
266
+	registerContents = Write_One_Byte(0x0);
267
+	return registerContents;
268
+}
269
+
270
+
271
+uint8_t Read_NRF_Register(uint8_t address)
272
+{
273
+	uint8_t registerContents;
274
+
275
+	registerContents = Write_Two_Bytes(address, 0x0);
276
+
277
+	return registerContents;
278
+}
230
 
279
 
231
 void Write_NRF_Register(uint8_t address, uint8_t registerContents)
280
 void Write_NRF_Register(uint8_t address, uint8_t registerContents)
232
 {
281
 {
238
 	Write_Two_Bytes(0x50, 0x73);
287
 	Write_Two_Bytes(0x50, 0x73);
239
 }
288
 }
240
 
289
 
241
-static void Write_Two_Bytes(uint8_t byte1, uint8_t byte2)
290
+void Send_TX_Flush_Command(void)
291
+{
292
+	Write_One_Byte(FLUSH_TX_COMMAND);
293
+}
294
+
295
+void Send_RX_Flush_Command(void)
296
+{
297
+	Write_One_Byte(FLUSH_RX_COMMAND);
298
+}
299
+
300
+static uint8_t Write_One_Byte(uint8_t byte1)
242
 {
301
 {
302
+	uint8_t registerContents = 0;
243
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
303
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
244
 
304
 
245
-	SPI_Transfer_Byte(byte1);
246
-	SPI_Transfer_Byte(byte2);
305
+	registerContents = SPI_Transfer_Byte(byte1);
247
 
306
 
248
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
307
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
308
+	return registerContents;
249
 }
309
 }
250
 
310
 
251
-void Send_TX_Flush_Command(void)
311
+static uint8_t Write_Two_Bytes(uint8_t byte1, uint8_t byte2)
252
 {
312
 {
253
-	/* First write the write command with the address */
313
+	uint8_t registerContents = 0;
254
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
314
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
255
 
315
 
256
-	SPI_Transfer_Byte(0xE1);
316
+	SPI_Transfer_Byte(byte1);
317
+	registerContents = SPI_Transfer_Byte(byte2);
257
 
318
 
258
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
319
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
320
+	return registerContents;
259
 }
321
 }
260
 
322
 
261
 
323
 
262
 
324
 
263
 void Write_Message_To_TX_FIFO(uint8_t length, uint8_t * buffer)
325
 void Write_Message_To_TX_FIFO(uint8_t length, uint8_t * buffer)
264
 {
326
 {
265
-	Write_Byte_And_Buffer(0xA0, buffer, length);
327
+	Write_Byte_And_Buffer(W_TX_PAYLOAD_COMMAND, buffer, length);
328
+}
329
+
330
+void Read_Message_From_RX_FIFO(uint8_t length, uint8_t * buffer)
331
+{
332
+	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
333
+
334
+	SPI_Transfer_Byte(R_RX_PAYLOAD_COMMAND);
335
+
336
+	/* Write the data byte */
337
+	for (uint8_t i = 0; i < length; i ++)
338
+	{
339
+		buffer[i] = SPI_Transfer_Byte(0x0);
340
+	}
341
+
342
+	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
266
 }
343
 }
267
 
344
 
268
 void Set_TX_Address(uint8_t * txAddress, uint8_t length)
345
 void Set_TX_Address(uint8_t * txAddress, uint8_t length)
275
 	Write_Byte_And_Buffer(RX_ADDR_P0_ADDRESS | 0x20, rxAddress, length);
352
 	Write_Byte_And_Buffer(RX_ADDR_P0_ADDRESS | 0x20, rxAddress, length);
276
 }
353
 }
277
 
354
 
355
+void Set_RX_P1_Address(uint8_t * rxAddress, uint8_t length)
356
+{
357
+	Write_Byte_And_Buffer(RX_ADDR_P1_ADDRESS | 0x20, rxAddress, length);
358
+}
359
+
278
 static void Write_Byte_And_Buffer(uint8_t byte, uint8_t * buffer, uint8_t length)
360
 static void Write_Byte_And_Buffer(uint8_t byte, uint8_t * buffer, uint8_t length)
279
 {
361
 {
280
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
362
 	SPI_Start_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
289
 
371
 
290
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
372
 	SPI_Stop_Transmission(&NRF_CSN_PORT, NRF_CSN_PIN);
291
 }
373
 }
292
-
293
-//TODO: only write the used bytes into the address registers & add generic write functions

+ 27
- 10
weather-sensor/firmware/nrf24l01.h 查看文件

1
 #ifndef NRF24L01_H
1
 #ifndef NRF24L01_H
2
 #define NRF24L01_H
2
 #define NRF24L01_H
3
 
3
 
4
-#define PACKET_BUFFER_LENGTH 22
4
+#define PACKET_LENGTH 32
5
+
6
+#define PACKET_PAYLOAD_BUFFER_LENGTH 22
5
 
7
 
6
 /* AVR I/O pin definionts */
8
 /* AVR I/O pin definionts */
7
 #define NRF_CE_DDR   DDRD
9
 #define NRF_CE_DDR   DDRD
22
 void Set_NRF24L01_Pins(void);
24
 void Set_NRF24L01_Pins(void);
23
 void Configure_Transmission(uint8_t moduleId);
25
 void Configure_Transmission(uint8_t moduleId);
24
 uint8_t Read_NRF_Status_Register(void);
26
 uint8_t Read_NRF_Status_Register(void);
25
-uint8_t Read_NRF_Register(uint8_t address, uint8_t * registerContents);
27
+uint8_t Read_NRF_Register(uint8_t address);
26
 void Write_NRF_Register(uint8_t address, uint8_t registerContents);
28
 void Write_NRF_Register(uint8_t address, uint8_t registerContents);
27
 void Send_Activate_Command(void);
29
 void Send_Activate_Command(void);
28
-
29
-void NRF24L01_Send_Message(uint8_t *buffer, uint8_t length);
30
+bool NRF24L01_Send_Message(uint8_t *buffer, uint8_t length);
31
+bool NRF24L01_Receive_Message(uint8_t *buffer, uint8_t duration);
30
 void Write_Message_To_TX_FIFO(uint8_t length, uint8_t * buffer);
32
 void Write_Message_To_TX_FIFO(uint8_t length, uint8_t * buffer);
33
+void Read_Message_From_RX_FIFO(uint8_t length, uint8_t * buffer);
31
 void Set_TX_Address(uint8_t * txAddress, uint8_t length);
34
 void Set_TX_Address(uint8_t * txAddress, uint8_t length);
32
 void Set_RX_P0_Address(uint8_t * rxAddress, uint8_t length);
35
 void Set_RX_P0_Address(uint8_t * rxAddress, uint8_t length);
36
+void Set_RX_P1_Address(uint8_t * rxAddress, uint8_t length);
33
 
37
 
34
 typedef enum
38
 typedef enum
35
 {
39
 {
36
-	PACKET_TYPE_SALT = 0,
37
-	PACKET_TYPE_REPORT = 1,
38
-	PACKET_TYPE_GET_VALUES = 2,
39
-	PACKET_TYPE_VALUES = 3,
40
+	PACKET_TYPE_GET_SALT = 0,
41
+	PACKET_TYPE_SALT = 1,
42
+	PACKET_TYPE_REPORT = 2,
43
+	PACKET_TYPE_GET_VALUES = 3,
44
+	PACKET_TYPE_VALUES = 4,
40
 } PACKET_TYPE;
45
 } PACKET_TYPE;
41
 
46
 
42
 typedef enum
47
 typedef enum
66
 			uint8_t valueTypeHumidity;
71
 			uint8_t valueTypeHumidity;
67
 			uint16_t humidity;
72
 			uint16_t humidity;
68
 			uint8_t unused[10];
73
 			uint8_t unused[10];
69
-		} values;
70
-		uint8_t buffer[PACKET_BUFFER_LENGTH];
74
+		} reportData;
75
+
76
+		struct {
77
+			BITFIELD_PACKET_COUNT_ELEMENT packetIdentifier;
78
+			uint8_t salt[7];
79
+			uint8_t unused[14];
80
+		} saltData;
81
+
82
+		struct {
83
+			BITFIELD_PACKET_COUNT_ELEMENT packetIdentifier;
84
+			uint8_t unused[21];
85
+		} getSaltData;
86
+
87
+		uint8_t buffer[PACKET_PAYLOAD_BUFFER_LENGTH];
71
 	}payload;
88
 	}payload;
72
 	uint16_t crc;
89
 	uint16_t crc;
73
 } PACKET;
90
 } PACKET;

+ 6
- 0
weather-sensor/firmware/nrf24l01_definitions.h 查看文件

31
 #define DYNPD_ADDRESS 0x1C
31
 #define DYNPD_ADDRESS 0x1C
32
 #define FEATURE_ADDRESS 0x1D
32
 #define FEATURE_ADDRESS 0x1D
33
 
33
 
34
+/* Commands */
35
+#define FLUSH_TX_COMMAND 0xE1
36
+#define FLUSH_RX_COMMAND 0xE2
37
+#define W_TX_PAYLOAD_COMMAND 0xA0
38
+#define R_RX_PAYLOAD_COMMAND 0x61
39
+
34
 /* Register bits definitions */
40
 /* Register bits definitions */
35
 /* CONFIG*/
41
 /* CONFIG*/
36
 typedef union
42
 typedef union

正在加载...
取消
保存