Skip to content

Commit 78d0760

Browse files
authored
Merge pull request #163 from sparkfun/release_candidate
v2.2.18
2 parents 3a1d357 + 3570c77 commit 78d0760

File tree

6 files changed

+577
-16
lines changed

6 files changed

+577
-16
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,340 @@
1+
/*
2+
Configuring the GNSS to automatically send RXM SFRBX and RAWX reports over SPI and log them to file on SD card using full 4-bit SDIO
3+
By: Paul Clark
4+
SparkFun Electronics
5+
Date: October 20th, 2022
6+
License: MIT. See license file for more information but you can
7+
basically do whatever you want with this code.
8+
9+
This example shows how to configure the u-blox GNSS to send RXM SFRBX and RAWX reports automatically
10+
and log the data to SD card in UBX format.
11+
12+
This code is written for the OpenLog ESP32 (DEV-20594) - coming soon!
13+
14+
Hardware set-up:
15+
Close the DSEL jumper on the ZED-F9P breakout - to select SPI mode
16+
Connect:
17+
OpenLog ESP32 : ZED-F9P
18+
GND GND
19+
3V3_SW 3V3
20+
SCK (18) SCK
21+
PICO (23) PICO (MOSI)
22+
POCI (19) POCI (MISO)
23+
33 CS
24+
25+
** Please note: this example will only work on u-blox ADR or High Precision GNSS or Time Sync products **
26+
27+
Data is logged in u-blox UBX format.
28+
29+
Feel like supporting open source hardware?
30+
Buy a board from SparkFun!
31+
OpenLog ESP32: https://www.sparkfun.com/products/20594
32+
ZED-F9P RTK2: https://www.sparkfun.com/products/15136
33+
NEO-M8P RTK: https://www.sparkfun.com/products/15005
34+
*/
35+
36+
#define GNSS_CS 33 // Connect the ZED-F9P CS pin to OpenLog ESP32 pin 33
37+
#define EN_3V3_SW 32 // The 3.3V_SW regulator Enable pin is connected to D32
38+
#define STAT_LED 25 // The OpenLog ESP32 STAT LED is connected to pin 25
39+
#define IMU_CS 5 // The ISM330 IMU CS is connected to pin 5
40+
#define MAG_CS 27 // The MMC5983 Mag CS is connected to pin 27
41+
42+
#include "FS.h"
43+
#include "SD_MMC.h"
44+
File myFile;
45+
46+
#include <SPI.h>
47+
#define spiPort SPI
48+
49+
#include <SparkFun_u-blox_GNSS_Arduino_Library.h> //Click here to get the library: http://librarymanager/All#SparkFun_u-blox_GNSS
50+
SFE_UBLOX_GNSS myGNSS;
51+
52+
#define sdWriteSize 2048 // Write data to the SD card in blocks of n*512 bytes
53+
#define fileBufferSize 65530 // Allocate just under 64KBytes of RAM for UBX message storage
54+
#define navRate 20 // Set the Nav Rate (Frequency) to 20Hz
55+
//#define ubxOnly // Uncomment this line to log UBX (RAWX and SFRBX) only
56+
uint8_t *myBuffer; // Use myBuffer to hold the data while we write it to SD card
57+
58+
unsigned long lastPrint; // Record when the last Serial print took place
59+
60+
// Note: we'll keep a count of how many SFRBX and RAWX messages arrive - but the count will not be completely accurate.
61+
// If two or more SFRBX messages arrive together as a group and are processed by one call to checkUblox, the count will
62+
// only increase by one.
63+
64+
int numSFRBX = 0; // Keep count of how many SFRBX message groups have been received (see note above)
65+
int numRAWX = 0; // Keep count of how many RAWX message groups have been received (see note above)
66+
67+
// Callback: newSFRBX will be called when new RXM SFRBX data arrives
68+
// See u-blox_structs.h for the full definition of UBX_RXMSFRBX_data_t
69+
// _____ You can use any name you like for the callback. Use the same name when you call setAutoRXMSFRBXcallback
70+
// / _____ This _must_ be UBX_RXM_SFRBX_data_t
71+
// | / _____ You can use any name you like for the struct
72+
// | | /
73+
// | | |
74+
void newSFRBX(UBX_RXM_SFRBX_data_t *ubxDataStruct)
75+
{
76+
numSFRBX++; // Increment the count
77+
}
78+
79+
// Callback: newRAWX will be called when new RXM RAWX data arrives
80+
// See u-blox_structs.h for the full definition of UBX_RXMRAWX_data_t
81+
// _____ You can use any name you like for the callback. Use the same name when you call setAutoRXMRAWXcallback
82+
// / _____ This _must_ be UBX_RXM_RAWX_data_t
83+
// | / _____ You can use any name you like for the struct
84+
// | | /
85+
// | | |
86+
void newRAWX(UBX_RXM_RAWX_data_t *ubxDataStruct)
87+
{
88+
numRAWX++; // Increment the count
89+
}
90+
91+
void setup()
92+
{
93+
Serial.begin(115200);
94+
95+
pinMode(STAT_LED, OUTPUT); // Flash the STAT LED each time we write to the SD card
96+
digitalWrite(STAT_LED, LOW);
97+
98+
pinMode(GNSS_CS, OUTPUT);
99+
digitalWrite(GNSS_CS, HIGH);
100+
pinMode(IMU_CS, OUTPUT);
101+
digitalWrite(IMU_CS, HIGH);
102+
pinMode(MAG_CS, OUTPUT);
103+
digitalWrite(MAG_CS, HIGH);
104+
105+
spiPort.begin();
106+
107+
// Do a fake transaction to initialize the SPI pins
108+
spiPort.beginTransaction(SPISettings(4000000, MSBFIRST, SPI_MODE0));
109+
spiPort.transfer(0);
110+
spiPort.endTransaction();
111+
112+
pinMode(EN_3V3_SW, OUTPUT); // Enable power for the microSD card and GNSS
113+
digitalWrite(EN_3V3_SW, HIGH);
114+
115+
delay(3000); // Allow time for the GNSS and SD card to start up and for Tera Term to reconnect
116+
Serial.println(F("SparkFun OpenLog ESP32 GNSS Logging : SPI and SDIO"));
117+
118+
// -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
119+
// Initialize the GNSS
120+
121+
Serial.println(F("Initializing the GNSS..."));
122+
123+
//myGNSS.enableDebugging(); // Uncomment this line to see helpful debug messages on Serial
124+
125+
myGNSS.setFileBufferSize(fileBufferSize); // setFileBufferSize must be called _before_ .begin
126+
127+
// Connect to the u-blox module using SPI port, csPin and speed setting
128+
// ublox devices generally work up to 5MHz. We'll use 4MHz for this example:
129+
bool begun = false;
130+
do
131+
{
132+
begun = myGNSS.begin(spiPort, GNSS_CS, 4000000);
133+
if (!begun)
134+
{
135+
Serial.println(F("u-blox GNSS not detected on SPI bus."));
136+
delay(1000);
137+
}
138+
}
139+
while (!begun);
140+
141+
// -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
142+
// Wait for a 3D fix. Get the date and time for the log file
143+
144+
//myGNSS.factoryDefault(); delay(5000); // Uncomment this line to reset the module back to its factory defaults
145+
146+
#ifdef ubxOnly
147+
myGNSS.setSPIOutput(COM_TYPE_UBX); //Set the SPI port to output only UBX
148+
#else
149+
myGNSS.setSPIOutput(COM_TYPE_UBX | COM_TYPE_NMEA); //Set the SPI port to output both UBX and NMEA messages
150+
#endif
151+
152+
//myGNSS.saveConfigSelective(VAL_CFG_SUBSEC_IOPORT); //Optional: save (only) the communications port settings to flash and BBR
153+
154+
Serial.print(F("Waiting for a 3D fix"));
155+
156+
uint8_t fix = 0;
157+
158+
do
159+
{
160+
fix = myGNSS.getFixType();
161+
delay(1000);
162+
Serial.print(F("."));
163+
}
164+
while ( fix != 3 ); // Wait for a 3D fix
165+
166+
Serial.println();
167+
168+
uint16_t y = myGNSS.getYear();
169+
uint8_t M = myGNSS.getMonth();
170+
uint8_t d = myGNSS.getDay();
171+
uint8_t h = myGNSS.getHour();
172+
uint8_t m = myGNSS.getMinute();
173+
uint8_t s = myGNSS.getSecond();
174+
175+
char szBuffer[40] = {'\0'};
176+
snprintf(szBuffer, sizeof(szBuffer), "/%04d%02d%02d%02d%02d%02d.ubx", y, M, d, h, m, s);
177+
178+
Serial.println(F("GNSS initialized."));
179+
180+
// -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
181+
// Initialize the SD card. Open the log file
182+
183+
Serial.println(F("Initializing SD card..."));
184+
185+
// Begin the SD card
186+
if(!SD_MMC.begin())
187+
{
188+
Serial.println(F("Card mount failed. Freezing..."));
189+
while(1);
190+
}
191+
192+
// Open the log file for writing
193+
Serial.printf("Log file is: %s\r\n", szBuffer);
194+
myFile = SD_MMC.open((const char *)szBuffer, FILE_WRITE);
195+
if(!myFile)
196+
{
197+
Serial.println(F("Failed to open log file for writing. Freezing..."));
198+
while(1);
199+
}
200+
201+
Serial.println(F("SD card initialized."));
202+
203+
// -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
204+
// Wait for a key press
205+
206+
while (Serial.available()) // Make sure the Serial buffer is empty
207+
{
208+
Serial.read();
209+
}
210+
211+
Serial.println(F("Press any key to start logging."));
212+
213+
while (!Serial.available()) // Wait for the user to press a key
214+
{
215+
; // Do nothing
216+
}
217+
218+
delay(100); // Wait, just in case multiple characters were sent
219+
220+
while (Serial.available()) // Empty the Serial buffer
221+
{
222+
Serial.read();
223+
}
224+
225+
// -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
226+
// Enable RAWX and SFRBX
227+
228+
myGNSS.setAutoRXMSFRBXcallbackPtr(&newSFRBX); // Enable automatic RXM SFRBX messages with callback to newSFRBX
229+
230+
myGNSS.logRXMSFRBX(); // Enable RXM SFRBX data logging
231+
232+
myGNSS.setAutoRXMRAWXcallbackPtr(&newRAWX); // Enable automatic RXM RAWX messages with callback to newRAWX
233+
234+
myGNSS.logRXMRAWX(); // Enable RXM RAWX data logging
235+
236+
myBuffer = new uint8_t[sdWriteSize]; // Create our own buffer to hold the data while we write it to SD card
237+
238+
#ifndef ubxOnly
239+
myGNSS.enableNMEAMessage(UBX_NMEA_GGA, COM_PORT_SPI, navRate); // Ensure the GxGGA (Global positioning system fix data) message is enabled. Send every second.
240+
myGNSS.enableNMEAMessage(UBX_NMEA_GSA, COM_PORT_SPI, navRate); // Ensure the GxGSA (GNSS DOP and Active satellites) message is enabled. Send every second.
241+
myGNSS.enableNMEAMessage(UBX_NMEA_GSV, COM_PORT_SPI, navRate); // Ensure the GxGSV (GNSS satellites in view) message is enabled. Send every second.
242+
myGNSS.enableNMEAMessage(UBX_NMEA_GST, COM_PORT_SPI, navRate); // Ensure the GxGST (Position error statistics) message is enabled. Send every second.
243+
myGNSS.enableNMEAMessage(UBX_NMEA_RMC, COM_PORT_SPI, navRate); // Ensure the GxRMC (Recommended minimum: position, velocity and time) message is enabled. Send every second.
244+
myGNSS.setNMEALoggingMask(SFE_UBLOX_FILTER_NMEA_GGA | SFE_UBLOX_FILTER_NMEA_GSA | SFE_UBLOX_FILTER_NMEA_GSV | SFE_UBLOX_FILTER_NMEA_GST | SFE_UBLOX_FILTER_NMEA_RMC); // Log only these NMEA messages
245+
#endif
246+
247+
myGNSS.setNavigationFrequency(navRate); // Set navigation rate
248+
249+
Serial.println(F("Press any key to stop logging."));
250+
251+
lastPrint = millis(); // Initialize lastPrint
252+
}
253+
254+
void loop()
255+
{
256+
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
257+
258+
myGNSS.checkUblox(); // Check for the arrival of new data and process it.
259+
myGNSS.checkCallbacks(); // Check if any callbacks are waiting to be processed.
260+
261+
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
262+
263+
while (myGNSS.fileBufferAvailable() >= sdWriteSize) // Check to see if we have at least sdWriteSize waiting in the buffer
264+
{
265+
digitalWrite(STAT_LED, HIGH); // Flash the STAT LED each time we write to the SD card
266+
267+
myGNSS.extractFileBufferData(myBuffer, sdWriteSize); // Extract exactly sdWriteSize bytes from the UBX file buffer and put them into myBuffer
268+
269+
myFile.write(myBuffer, sdWriteSize); // Write exactly sdWriteSize bytes from myBuffer to the ubxDataFile on the SD card
270+
271+
// In case the SD writing is slow or there is a lot of data to write, keep checking for the arrival of new data
272+
myGNSS.checkUblox(); // Check for the arrival of new data and process it.
273+
myGNSS.checkCallbacks(); // Check if any callbacks are waiting to be processed.
274+
275+
digitalWrite(STAT_LED, LOW); // Turn the STAT LED off again
276+
}
277+
278+
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
279+
280+
if (millis() > (lastPrint + 1000)) // Print the message count once per second
281+
{
282+
uint16_t maxBufferBytes = myGNSS.getMaxFileBufferAvail(); // Get how full the file buffer has been (not how full it is now)
283+
float bufferHigh = 100.0 * (float)maxBufferBytes / (float)fileBufferSize;
284+
285+
Serial.print(F("Message groups received: SFRBX: ")); // Print how many message groups have been received (see note above)
286+
Serial.print(numSFRBX);
287+
Serial.print(F(" RAWX: "));
288+
Serial.print(numRAWX);
289+
Serial.print(F(" \tBuffer high tide: "));
290+
Serial.print(bufferHigh, 1); // It is a fun thing to watch how full the buffer gets
291+
if (bufferHigh > 90.)
292+
Serial.println(F("%!!"));
293+
else if (bufferHigh > 80.)
294+
Serial.println(F("%!"));
295+
else
296+
Serial.println(F("%"));
297+
298+
lastPrint = millis(); // Update lastPrint
299+
}
300+
301+
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
302+
303+
if (Serial.available()) // Check if the user wants to stop logging
304+
{
305+
uint16_t remainingBytes = myGNSS.fileBufferAvailable(); // Check if there are any bytes remaining in the file buffer
306+
307+
while (remainingBytes > 0) // While there is still data in the file buffer
308+
{
309+
digitalWrite(STAT_LED, HIGH); // Flash the STAT LED while we write to the SD card
310+
311+
uint16_t bytesToWrite = remainingBytes; // Write the remaining bytes to SD card sdWriteSize bytes at a time
312+
if (bytesToWrite > sdWriteSize)
313+
{
314+
bytesToWrite = sdWriteSize;
315+
}
316+
317+
myGNSS.extractFileBufferData(myBuffer, bytesToWrite); // Extract bytesToWrite bytes from the UBX file buffer and put them into myBuffer
318+
319+
myFile.write(myBuffer, bytesToWrite); // Write bytesToWrite bytes from myBuffer to the ubxDataFile on the SD card
320+
321+
remainingBytes -= bytesToWrite; // Decrement remainingBytes
322+
}
323+
324+
digitalWrite(STAT_LED, LOW); // Turn the STAT LED off
325+
326+
myFile.close(); // Close the data file
327+
328+
myGNSS.setNavigationFrequency(1); // Set navigation rate to 1Hz
329+
330+
myGNSS.disableMessage(UBX_CLASS_RXM, UBX_RXM_RAWX, COM_PORT_SPI);
331+
myGNSS.disableMessage(UBX_CLASS_RXM, UBX_RXM_SFRBX, COM_PORT_SPI);
332+
333+
myGNSS.setSPIOutput(COM_TYPE_UBX | COM_TYPE_NMEA); // Re-enable NMEA
334+
335+
Serial.println(F("Logging stopped. Freezing..."));
336+
while(1); // Do nothing more
337+
}
338+
339+
// =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
340+
}

Diff for: keywords.txt

+5
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@ NMEA_ZDA_data_t KEYWORD1
7979
#######################################
8080

8181
setPacketCfgPayloadSize KEYWORD2
82+
getPacketCfgSpaceRemaining KEYWORD2
8283
begin KEYWORD2
8384
end KEYWORD2
8485
setI2CpollingWait KEYWORD2
@@ -232,6 +233,7 @@ setVal8 KEYWORD2
232233
setVal16 KEYWORD2
233234
setVal32 KEYWORD2
234235
setVal64 KEYWORD2
236+
newCfgValset KEYWORD2
235237
newCfgValset8 KEYWORD2
236238
newCfgValset16 KEYWORD2
237239
newCfgValset32 KEYWORD2
@@ -244,6 +246,9 @@ sendCfgValset8 KEYWORD2
244246
sendCfgValset16 KEYWORD2
245247
sendCfgValset32 KEYWORD2
246248
sendCfgValset64 KEYWORD2
249+
sendCfgValset KEYWORD2
250+
getCfgValsetLen KEYWORD2
251+
getCfgValsetSpaceRemaining KEYWORD2
247252

248253
getNAVPOSECEF KEYWORD2
249254
setAutoNAVPOSECEF KEYWORD2

Diff for: library.properties

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
name=SparkFun u-blox GNSS Arduino Library
2-
version=2.2.17
2+
version=2.2.18
33
author=SparkFun Electronics <[email protected]>
44
maintainer=SparkFun Electronics <sparkfun.com>
55
sentence=Library for I2C, Serial and SPI Communication with u-blox GNSS modules<br/><br/>

0 commit comments

Comments
 (0)