Hello,
I am working on the GNSS application provided in the sdk-nrf at [path: samples/cellular/gnss] and I'm using thing91: nrf9160 board. I have modified the GPS acquisition loop to meet my project requirements, specifically requiring GPS coordinates with an accuracy of up to 5 meters from the reference point.
During testing, I noticed an issue: while the application prints an accuracy of 5 meters after obtaining a GPS fix, the actual distance between the reference point and the acquired GPS coordinates (latitude and longitude), when checked on Google Maps, ranges from 13 meters to 98 meters. This discrepancy poses a significant problem for my use case.
Below is the code snippet we are using to fetch GPS coordinates.
#define STS_AGNSS_FIX_ACCURACY_THD_MTR (5.0f) #define STS_AGNSS_ACCURACY_RETRY_TIMEOUT_SEC (30U) #define STS_AGNSS_FIX_RETRY_TIMEOUT_SEC (90U) int sts_get_gnss_fix(double *latitude, double *longitude) { bool isGNSSFixAvial = false; uint16_t fixRetryCntAGNSS = 0U; uint16_t agpsSecCnt = 0U; #if defined(CONFIG_GNSS_SAMPLE_ACCURACY_CHECK) uint16_t accuracyRetryCntAGNSS = 0U; #endif /* CONFIG_GNSS_SAMPLE_ACCURACY_CHECK */ if (sts_work_queue_init() != 0) { LOG_ERR("Failed to initialize GNSS work queue"); return -1; } if (sts_gnss_init() != 0) { LOG_ERR("Failed to initialize GNSS"); return -1; } if (sts_gnss_start(0U, 1U) != 0) { LOG_ERR("Failed to start GNSS"); return -1; } for (;;) { (void)k_poll(events, 1, K_MSEC(500)); if (events[0].state == K_POLL_STATE_SEM_AVAILABLE && k_sem_take(events[0].sem, K_NO_WAIT) == 0) { /* Display RSRP, RSRQ, SNR values */ STS_Get_Signal_Values(); /* New PVT data available */ sts_print_satellite_stats(&sts_last_pvt); if (sts_last_pvt.flags & NRF_MODEM_GNSS_PVT_FLAG_DEADLINE_MISSED) { printf("GNSS operation blocked by LTE\n"); } if (sts_last_pvt.flags & NRF_MODEM_GNSS_PVT_FLAG_NOT_ENOUGH_WINDOW_TIME) { printf("Insufficient GNSS time windows\n"); } if (sts_last_pvt.flags & NRF_MODEM_GNSS_PVT_FLAG_SLEEP_BETWEEN_PVT) { printf("Sleep period(s) between PVT notifications\n"); } agpsSecCnt++; printf("-----------------------------------:%d\n", agpsSecCnt); if (sts_last_pvt.flags & NRF_MODEM_GNSS_PVT_FLAG_FIX_VALID) { sts_print_fix_data(&sts_last_pvt); #if defined(CONFIG_GNSS_SAMPLE_ACCURACY_CHECK) accuracyRetryCntAGNSS++; if ( ( sts_last_pvt.accuracy <= STS_AGNSS_FIX_ACCURACY_THD_MTR ) || ( accuracyRetryCntAGNSS == STS_AGNSS_ACCURACY_RETRY_TIMEOUT_SEC ) ) #endif /* CONFIG_GNSS_SAMPLE_ACCURACY_CHECK */ { *latitude = sts_last_pvt.latitude; *longitude = sts_last_pvt.longitude; isGNSSFixAvial = true; break; } } else { fixRetryCntAGNSS++; printf("Searching [%c]\n", sts_update_indicator[fixRetryCntAGNSS%4]); if ( fixRetryCntAGNSS == STS_AGNSS_FIX_RETRY_TIMEOUT_SEC ) { sts_print_fix_data(&sts_last_pvt); isGNSSFixAvial = false; break; } } events[0].state = K_POLL_STATE_NOT_READY; } } sts_gnss_stop_dInit(); if ( isGNSSFixAvial ) { return 0; } else { return -1; } } static void sts_gnss_event_handler(int event) { int retval; switch (event) { case NRF_MODEM_GNSS_EVT_PVT: retval = nrf_modem_gnss_read(&sts_last_pvt, sizeof(sts_last_pvt), NRF_MODEM_GNSS_DATA_PVT); if (retval == 0) { k_sem_give(&pvt_data_sem); } break; case NRF_MODEM_GNSS_EVT_AGNSS_REQ: #if !defined(CONFIG_GNSS_SAMPLE_ASSISTANCE_NONE) retval = nrf_modem_gnss_read(&sts_last_agnss, sizeof(sts_last_agnss), NRF_MODEM_GNSS_DATA_AGNSS_REQ); if (retval == 0) { sts_add_element_to_work_queue(); } #endif /* !CONFIG_GNSS_SAMPLE_ASSISTANCE_NONE */ break; default: break; } } static void sts_print_fix_data(struct nrf_modem_gnss_pvt_data_frame *pvt_data) { printf("Latitude: %.06f\n", pvt_data->latitude); printf("Longitude: %.06f\n", pvt_data->longitude); printf("Altitude: %.01f m\n", pvt_data->altitude); printf("Accuracy: %.01f m\n", pvt_data->accuracy); printf("Speed: %.01f m/s\n", pvt_data->speed); printf("Speed accuracy: %.01f m/s\n", pvt_data->speed_accuracy); printf("Heading: %.01f deg\n", pvt_data->heading); printf("Date: %04u-%02u-%02u\n", pvt_data->datetime.year, pvt_data->datetime.month, pvt_data->datetime.day); printf("Time (UTC): %02u:%02u:%02u.%03u\n", pvt_data->datetime.hour, pvt_data->datetime.minute, pvt_data->datetime.seconds, pvt_data->datetime.ms); printf("PDOP: %.01f\n", pvt_data->pdop); printf("HDOP: %.01f\n", pvt_data->hdop); printf("VDOP: %.01f\n", pvt_data->vdop); printf("TDOP: %.01f\n", pvt_data->tdop); }
Kindly please let me know how I can fix this issue.
Best Regards,
Mahima