Skip to content

v2.0.12 #57

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Aug 10, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion library.properties
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
name=SparkFun u-blox GNSS Arduino Library
version=2.0.11
version=2.0.12
author=SparkFun Electronics <[email protected]>
maintainer=SparkFun Electronics <sparkfun.com>
sentence=Library for I2C and Serial Communication with u-blox GNSS modules<br/><br/>
Expand Down
90 changes: 68 additions & 22 deletions src/SparkFun_u-blox_GNSS_Arduino_Library.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -715,11 +715,28 @@ boolean SFE_UBLOX_GNSS::checkUbloxI2C(ubxPacket *incomingUBX, uint8_t requestedC
uint16_t bytesAvailable = 0;
_i2cPort->beginTransmission(_gpsI2Caddress);
_i2cPort->write(0xFD); //0xFD (MSB) and 0xFE (LSB) are the registers that contain number of bytes available
if (_i2cPort->endTransmission(false) != 0) //Send a restart command. Do not release bus.
uint8_t i2cError = _i2cPort->endTransmission(false); //Send a restart command. Do not release bus.
if (i2cError != 0)
{
if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
{
_debugSerial->print(F("checkUbloxI2C: I2C error: endTransmission returned "));
_debugSerial->println(i2cError);
}
return (false); //Sensor did not ACK
}

_i2cPort->requestFrom((uint8_t)_gpsI2Caddress, (uint8_t)2);
if (_i2cPort->available())
uint8_t bytesReturned = _i2cPort->requestFrom((uint8_t)_gpsI2Caddress, (uint8_t)2);
if (bytesReturned != 2)
{
if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
{
_debugSerial->print(F("checkUbloxI2C: I2C error: requestFrom 0xFD returned "));
_debugSerial->println(bytesReturned);
}
return (false); //Sensor did not return 2 bytes
}
//if (_i2cPort->available())
{
uint8_t msb = _i2cPort->read();
uint8_t lsb = _i2cPort->read();
Expand All @@ -728,7 +745,8 @@ boolean SFE_UBLOX_GNSS::checkUbloxI2C(ubxPacket *incomingUBX, uint8_t requestedC
//I believe this is a u-blox bug. Device should never present an 0xFF.
if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
{
_debugSerial->println(F("checkUbloxI2C: u-blox bug, length lsb is 0xFF"));
_debugSerial->print(F("checkUbloxI2C: u-blox bug? Length lsb is 0xFF. i2cPollingWait is "));
_debugSerial->println(i2cPollingWait);
}
if (debugPin >= 0)
{
Expand All @@ -739,6 +757,23 @@ boolean SFE_UBLOX_GNSS::checkUbloxI2C(ubxPacket *incomingUBX, uint8_t requestedC
lastCheck = millis(); //Put off checking to avoid I2C bus traffic
return (false);
}
// if (msb == 0xFF)
// {
// //I believe this is a u-blox bug. Device should never present an 0xFF.
// if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
// {
// _debugSerial->print(F("checkUbloxI2C: u-blox bug? Length msb is 0xFF. i2cPollingWait is "));
// _debugSerial->println(i2cPollingWait);
// }
// if (debugPin >= 0)
// {
// digitalWrite((uint8_t)debugPin, LOW);
// delay(10);
// digitalWrite((uint8_t)debugPin, HIGH);
// }
// lastCheck = millis(); //Put off checking to avoid I2C bus traffic
// return (false);
// }
bytesAvailable = (uint16_t)msb << 8 | lsb;
}

Expand All @@ -762,17 +797,17 @@ boolean SFE_UBLOX_GNSS::checkUbloxI2C(ubxPacket *incomingUBX, uint8_t requestedC
//Clear the MSbit
bytesAvailable &= ~((uint16_t)1 << 15);

if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
{
_debugSerial->print(F("checkUbloxI2C: Bytes available error: "));
_debugSerial->println(bytesAvailable);
if (debugPin >= 0)
{
digitalWrite((uint8_t)debugPin, LOW);
delay(10);
digitalWrite((uint8_t)debugPin, HIGH);
}
}
// if ((_printDebug == true) || (_printLimitedDebug == true)) // This is important. Print this if doing limited debugging
// {
// _debugSerial->print(F("checkUbloxI2C: Bytes available error: "));
// _debugSerial->println(bytesAvailable);
// if (debugPin >= 0)
// {
// digitalWrite((uint8_t)debugPin, LOW);
// delay(10);
// digitalWrite((uint8_t)debugPin, HIGH);
// }
// }
}

#ifndef SFE_UBLOX_REDUCED_PROG_MEM
Expand Down Expand Up @@ -9615,10 +9650,13 @@ uint32_t SFE_UBLOX_GNSS::getProcessNMEAMask()
//Max is 40Hz(?!)
boolean SFE_UBLOX_GNSS::setNavigationFrequency(uint8_t navFreq, uint16_t maxWait)
{
//if(updateRate > 40) updateRate = 40; //Not needed: module will correct out of bounds values
if (navFreq > 40)
navFreq = 40; // Limit navFreq to 40Hz so i2cPollingWait is set correctly

//Adjust the I2C polling timeout based on update rate
i2cPollingWait = 1000 / (((int)navFreq) * 4); //This is the number of ms to wait between checks for new I2C data
//Do this even if the sendCommand fails
i2cPollingWaitNAV = 1000 / (((int)navFreq) * 4); //This is the number of ms to wait between checks for new I2C data
i2cPollingWait = i2cPollingWaitNAV < i2cPollingWaitHNR ? i2cPollingWaitNAV : i2cPollingWaitHNR; // Set i2cPollingWait to the lower of NAV and HNR

//Query the module
packetCfg.cls = UBX_CLASS_CFG;
Expand Down Expand Up @@ -9664,8 +9702,12 @@ uint8_t SFE_UBLOX_GNSS::getNavigationFrequency(uint16_t maxWait)
//Set the elapsed time between GNSS measurements in milliseconds, which defines the rate
boolean SFE_UBLOX_GNSS::setMeasurementRate(uint16_t rate, uint16_t maxWait)
{
if (rate < 25) // "Measurement rate should be greater than or equal to 25 ms."
rate = 25;

//Adjust the I2C polling timeout based on update rate
i2cPollingWait = rate / 4; //This is the number of ms to wait between checks for new I2C data
i2cPollingWaitNAV = rate / 4; //This is the number of ms to wait between checks for new I2C data
i2cPollingWait = i2cPollingWaitNAV < i2cPollingWaitHNR ? i2cPollingWaitNAV : i2cPollingWaitHNR; // Set i2cPollingWait to the lower of NAV and HNR

//Query the module
packetCfg.cls = UBX_CLASS_CFG;
Expand Down Expand Up @@ -10950,6 +10992,14 @@ boolean SFE_UBLOX_GNSS::getSensorFusionStatus(UBX_ESF_STATUS_sensorStatus_t *sen
// Returns true if the setHNRNavigationRate is successful
boolean SFE_UBLOX_GNSS::setHNRNavigationRate(uint8_t rate, uint16_t maxWait)
{
if (rate > 40)
rate = 40; // Limit rate to 40Hz so i2cPollingWait is set correctly

//Adjust the I2C polling timeout based on update rate
//Do this even if the sendCommand is not ACK'd
i2cPollingWaitHNR = 1000 / (((int)rate) * 4); //This is the number of ms to wait between checks for new I2C data
i2cPollingWait = i2cPollingWaitNAV < i2cPollingWaitHNR ? i2cPollingWaitNAV : i2cPollingWaitHNR; // Set i2cPollingWait to the lower of NAV and HNR

packetCfg.cls = UBX_CLASS_CFG;
packetCfg.id = UBX_CFG_HNR;
packetCfg.len = 0;
Expand All @@ -10965,10 +11015,6 @@ boolean SFE_UBLOX_GNSS::setHNRNavigationRate(uint8_t rate, uint16_t maxWait)
//Update the navigation rate
sfe_ublox_status_e result = sendCommand(&packetCfg, maxWait); // We are only expecting an ACK

//Adjust the I2C polling timeout based on update rate
if (result == SFE_UBLOX_STATUS_DATA_SENT)
i2cPollingWait = 1000 / (((int)rate) * 4); //This is the number of ms to wait between checks for new I2C data

return (result == SFE_UBLOX_STATUS_DATA_SENT);
}

Expand Down
2 changes: 2 additions & 0 deletions src/SparkFun_u-blox_GNSS_Arduino_Library.h
Original file line number Diff line number Diff line change
Expand Up @@ -1351,6 +1351,8 @@ class SFE_UBLOX_GNSS
//If we are expecting an update every X Hz then we should check every quarter that amount of time
//Otherwise we may block ourselves from seeing new data
uint8_t i2cPollingWait = 100; //Default to 100ms. Adjusted when user calls setNavigationFrequency() or setHNRNavigationRate() or setMeasurementRate()
uint8_t i2cPollingWaitNAV = 100; //We need to record the desired polling rate for standard nav messages
uint8_t i2cPollingWaitHNR = 100; //and for HNR too so we can set i2cPollingWait to the lower of the two

//The SPI polling wait is a little different. checkUbloxSpi will delay for this amount before returning if
//there is no data waiting to be read. This prevents waitForACKResponse from pounding the SPI bus too hard.
Expand Down