Zmiana sposobu obsługi gpsa - do poprawek

aprs_test
Łukasz Nidecki 2016-12-28 00:03:08 +01:00
rodzic fef7a130ad
commit 21dcf0d64f
11 zmienionych plików z 548 dodań i 147 usunięć

48
delay.c 100644
Wyświetl plik

@ -0,0 +1,48 @@
/*
*
* Copyright (C) Patryk Jaworski <regalis@regalis.com.pl>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#include <stm32f10x.h>
#include "delay.h"
static inline void systick_stop() {
SysTick->CTRL &= ~(SysTick_CTRL_ENABLE_Msk);
}
static inline void systick_start() {
SysTick->CTRL |= SysTick_CTRL_ENABLE_Msk;
}
void delay_init() {
SysTick->CTRL &= ~(SysTick_CTRL_CLKSOURCE_Msk); // AHB / 8 = 10.5MHz
SysTick->LOAD = 1; // Tick every 1.047us
}
void _delay_us(uint32_t us) {
systick_start();
while (us != 0) {
while ((SysTick->CTRL & SysTick_CTRL_COUNTFLAG_Msk) == 0) {}
--us;
}
systick_stop();
}
inline void _delay_ms(uint32_t ms) {
_delay_us(ms * 1000);
}

29
delay.h 100644
Wyświetl plik

@ -0,0 +1,29 @@
/*
*
* Copyright (C) Patryk Jaworski <regalis@regalis.com.pl>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*
*/
#ifndef __DELAY_H_
#define __DELAY_H_
/** Initialize delay core - configure SysTick timer */
void delay_init();
void _delay_us(uint32_t us);
void _delay_ms(uint32_t ms);
#endif

28
fun.c
Wyświetl plik

@ -5,6 +5,8 @@
const char ascii[] = "0123456789ABCDEF";
int srednia_u[5] = {0, 0, 0, 0, 0};
int HexCharToInt(char ch) {
if (ch < 48 || (ch > 57 && ch < 65) || ch > 70) return 0;
return (ch < 58) ? ch - 48 : ch - 55;
@ -18,32 +20,6 @@ void print(char *s) {
}
}
void sendtogps(uint8_t *s, unsigned char cun) {
unsigned char CK_A = 0;
unsigned char CK_B = 0;
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
USART_SendData(USART1, *(s++));
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
USART_SendData(USART1, *(s++));
cun--;
cun--;
while (cun-- != 0) {
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
CK_A += *(s);
CK_B += CK_A;
USART_SendData(USART1, *(s++));
}
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
USART_SendData(USART1, CK_A);
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
USART_SendData(USART1, CK_B);
}
void send_hex(unsigned char data) {
while (USART_GetFlagStatus(USART3, USART_FLAG_TC) == RESET) {
}

2
fun.h
Wyświetl plik

@ -1,8 +1,8 @@
int HexCharToInt(char ch);
void print( char* s);
void sendtogps(uint8_t* s, unsigned char cun);
void send_hex(unsigned char data);
unsigned char czytaj_GPS(unsigned char pos,unsigned char len, char *source, char * destination);
uint16_t gps_CRC16_checksum (char *string);
int srednia (int dana);

65
init.c
Wyświetl plik

@ -16,9 +16,42 @@ ADC_InitTypeDef ADC_InitStructure;
DMA_InitTypeDef DMA_InitStructure;
#define ADC1_DR_Address ((uint32_t)0x4001244C)
void init_usart_gps(const uint32_t speed) {
NVIC_DisableIRQ(USART1_IRQn);
USART_ITConfig(USART1, USART_IT_RXNE, DISABLE);
USART_Cmd(USART1, DISABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);// | RCC_APB2Periph_AFIO, ENABLE);
USART_InitStructure.USART_BaudRate = speed; //0x9c4;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_Init(USART1, &USART_InitStructure);
USART_Cmd(USART1, ENABLE);
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);
NVIC_EnableIRQ(USART1_IRQn);
}
void init_usart_debug() {
NVIC_DisableIRQ(USART3_IRQn);
USART_Cmd(USART3, DISABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3, ENABLE);// | RCC_APB2Periph_AFIO, ENABLE);
USART_InitStructure.USART_BaudRate = 19200; //0x9c4;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_Init(USART3, &USART_InitStructure);
USART_Cmd(USART3, ENABLE);
}
void NVIC_Conf()
{
#ifdef VECT_TAB_RAM
@ -92,34 +125,20 @@ void init_port()
GPIO_Conf.GPIO_Pin = GPIO_Pin_10;
GPIO_Conf.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_Init(GPIOA, &GPIO_Conf);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);// | RCC_APB2Periph_AFIO, ENABLE);
USART_InitStructure.USART_BaudRate = 9600; //0x9c4;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_Init(USART1, &USART_InitStructure);
USART_Cmd(USART1, ENABLE);
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);
NVIC_EnableIRQ(USART1_IRQn);
GPIO_Conf.GPIO_Pin = GPIO_Pin_10;
init_usart_gps(9600);
GPIO_Conf.GPIO_Pin = GPIO_Pin_10;
GPIO_Conf.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_Conf.GPIO_Speed = GPIO_Speed_10MHz;
GPIO_Init(GPIOB, &GPIO_Conf);
GPIO_Conf.GPIO_Pin = GPIO_Pin_11;
GPIO_Conf.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_Init(GPIOB, &GPIO_Conf);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART3, ENABLE);// | RCC_APB2Periph_AFIO, ENABLE);
USART_InitStructure.USART_BaudRate = 19200; //0x9c4;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
USART_Init(USART3, &USART_InitStructure);
USART_Cmd(USART3, ENABLE);
RCC_AHBPeriphClockCmd ( RCC_AHBPeriph_DMA1 , ENABLE ) ;
init_usart_debug();
RCC_AHBPeriphClockCmd ( RCC_AHBPeriph_DMA1 , ENABLE ) ;
DMA_DeInit(DMA1_Channel1);
DMA_InitStructure.DMA_BufferSize = 2;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;

1
init.h
Wyświetl plik

@ -3,3 +3,4 @@ void NVIC_Conf();
void RCC_Conf();
void init_port();
void init_timer(const int rtty_speed);
void init_usart_gps(const uint32_t speed);

161
main.c
Wyświetl plik

@ -17,9 +17,11 @@
#include "init.h"
#include "config.h"
#include "radio.h"
#include "ublox.h"
#include "delay.h"
///////////////////////////// test mode /////////////
unsigned char test = 0; // 0 - normal, 1 - short frame only cunter, height, flag
const unsigned char test = 0; // 0 - normal, 1 - short frame only cunter, height, flag
char callsign[15] = {CALLSIGN};
#define gps_RMC_dlugosc 5
@ -61,12 +63,10 @@ char szerokosc_kier = 0;// 'S';s
char wysokosc[6] = {"0"};
char predkosc[6] = {"0"};
char kierunek[6] = {"0"};
int8_t temperatura;
char FixOk = 0;
int napiecie;
unsigned int czest;
float fdlugosc = 0;
float fszerokosc = 0;
float deg = 0;
float fbuf = 0;
char use_sat[3] = {'0'};
@ -79,7 +79,6 @@ char init_trx[] = "\n\rPowering up TX\n\r";
char powitanie[] = "greetings from earth";
unsigned char pun = 0;
unsigned int cun = 10;
char temp;
unsigned char dev = 0;
unsigned char tx_on = 0;
unsigned int tx_on_delay;
@ -111,47 +110,15 @@ unsigned char bOFF = 0;
unsigned char bCheckKay = 0;
unsigned char GPSConf = 0;
void processGPS();
/**
* GPS data processing
*/
void USART1_IRQHandler(void) {
if ((USART1->SR & USART_FLAG_RXNE) != (u16) RESET) {
GPS_temp = USART_ReceiveData(USART1);
USART_SendData(USART3, GPS_temp);
if (GPS_temp == '*') {
crc_GPS_start = 0;
crc_GPS_cun = 0;
crc_GPS_rec = 0;
}
if (crc_GPS_start) {
crc_GPS ^= GPS_temp;
} else {
if (GPS_rec) {
if (crc_GPS_cun < 3 && crc_GPS_cun > 0) {
crc_GPS_rec *= 16;
crc_GPS_rec += HexCharToInt(GPS_temp);
}
crc_GPS_cun++;
}
}
if (GPS_temp == GPS_START) {
wsk_GPS_buf = GPS_buf;
GPS_rec = 1;
crc_GPS = 0;
crc_GPS_start = 1;
}
if (GPS_rec) {
*(wsk_GPS_buf++) = GPS_temp;
}
if (GPS_temp == GPS_STOP) {
GPS_rec = 0;
*(wsk_GPS_buf) = 0x00;
if (crc_GPS_rec == crc_GPS) {
new_GPS_msg = 1;
GPS_rec = 0;
}
}
ublox_handle_incoming_byte((uint8_t) USART_ReceiveData(USART1));
}
}
@ -166,15 +133,15 @@ void TIM2_IRQHandler(void) {
GPIO_SetBits(GPIOB, RED);
if (*(++rtty_buf) == 0) {
tx_on = 0;
tx_on_delay = tx_delay;//2500;
tx_on_delay = 1;//tx_delay;//2500;
tx_enable = 0;
radio_disable_tx();
}
} else if (send_rtty_status == rttyOne) {
temp = radio_rw_register(0x73, 0x02, 1);
radio_rw_register(0x73, 0x02, 1);
GPIO_SetBits(GPIOB, RED);
} else if (send_rtty_status == rttyZero) {
temp = radio_rw_register(0x73, 0x00, 1);
radio_rw_register(0x73, 0x00, 1);
GPIO_ResetBits(GPIOB, RED);
}
}
@ -207,77 +174,74 @@ int main(void) {
RCC_Conf();
NVIC_Conf();
init_port();
init_timer(RTTY_SPEED);
delay_init();
ublox_init();
wsk_GPS_buf = GPS_buf;
int8_t temperatura;
GPIO_SetBits(GPIOB, RED);
USART_SendData(USART3, 0xc);
print(menu);
temp = radio_rw_register(0x02, 0xff, 0);
radio_rw_register(0x02, 0xff, 0);
//send_hex(temp);
temp = radio_rw_register(0x03, 0xff, 0);
temp = radio_rw_register(0x04, 0xff, 0);
radio_rw_register(0x03, 0xff, 0);
radio_rw_register(0x04, 0xff, 0);
radio_soft_reset();
print(init_trx);
// programowanie czestotliwosci nadawania
radio_set_tx_frequency();
// Programowanie mocy nadajnika
temp = radio_rw_register(0x6D, 00 | (Smoc & 0x0007), 1);
radio_rw_register(0x6D, 00 | (Smoc & 0x0007), 1);
temp = radio_rw_register(0x71, 0x00, 1);
temp = radio_rw_register(0x87, 0x08, 0);
temp = radio_rw_register(0x02, 0xff, 0);
temp = radio_rw_register(0x75, 0xff, 0);
temp = radio_rw_register(0x76, 0xff, 0);
temp = radio_rw_register(0x77, 0xff, 0);
temp = radio_rw_register(0x12, 0x20, 1);
temp = radio_rw_register(0x13, 0x00, 1);
temp = radio_rw_register(0x12, 0x00, 1);
temp = radio_rw_register(0x0f, 0x80, 1);
radio_rw_register(0x71, 0x00, 1);
radio_rw_register(0x87, 0x08, 0);
radio_rw_register(0x02, 0xff, 0);
radio_rw_register(0x75, 0xff, 0);
radio_rw_register(0x76, 0xff, 0);
radio_rw_register(0x77, 0xff, 0);
radio_rw_register(0x12, 0x20, 1);
radio_rw_register(0x13, 0x00, 1);
radio_rw_register(0x12, 0x00, 1);
radio_rw_register(0x0f, 0x80, 1);
rtty_buf = buf_rtty;
tx_on = 0;
tx_enable = 1;
//tx_enable =0;
Button = ADCVal[1];
while (1) {
if (status[0] == 'A') {
flaga |= 0x80;
} else {
flaga &= ~0x80;
}
while (1) {
if (tx_on == 0 && tx_enable) {
start_bits = RTTY_PRE_START_BITS;
temp = radio_rw_register(0x11, 0xff, 0); //odczyt ADC
temperatura = (int8_t) (-64 + (temp * 5 / 10) - 16);
temp = radio_rw_register(0x0f, 0x80, 1);
temperatura = radio_read_temperature();
napiecie = srednia(ADCVal[0] * 600 / 4096);
fdlugosc = atoff(dlugosc);
deg = (int) (fdlugosc / 100);
fbuf = fdlugosc - (deg * 100);
fdlugosc = deg + fbuf / 60;
if (dlugosc_kier == 'W') {
fdlugosc *= -1;
}
fszerokosc = atoff(szerokosc);
deg = (int) (fszerokosc / 100);
fbuf = fszerokosc - (deg * 100);
fszerokosc = deg + fbuf / 60;
if (szerokosc_kier == 'S') {
fszerokosc *= -1;
GPSEntry gpsData;
ublox_get_last_data(&gpsData);
if (gpsData.fix >= 3) {
flaga |= 0x80;
} else {
flaga &= ~0x80;
}
if (test) {
sprintf(buf_rtty, "$$$$$$$%d,%d,%02x", send_cun, atoi(wysokosc), flaga);
} else {
sprintf(buf_rtty, "$$$$$$$%s,%d,%s,%.5f,%.5f,%d,%d,%s,%d,%d,%d,%02x", callsign, send_cun, czas, fszerokosc,
fdlugosc, atoi(wysokosc), atoi(predkosc), kierunek, temperatura, napiecie, atoi(use_sat), flaga);
uint8_t lat_d = (uint8_t) abs(gpsData.lat_raw / 10000000);
uint32_t lat_fl = (uint32_t) abs(abs(gpsData.lat_raw) - lat_d * 10000000) / 100;
uint8_t lon_d = (uint8_t) abs(gpsData.lon_raw / 10000000);
uint32_t lon_fl = (uint32_t) abs(abs(gpsData.lon_raw) - lon_d * 10000000) / 100;
sprintf(buf_rtty, "$$$$$$$%s,%d,%02u%02u%02u,%s%d.%05ld,%s%d.%05ld,%ld,%d,%s,%d,%d,%d,%d,%02x", callsign, send_cun,
gpsData.hours, gpsData.minutes, gpsData.seconds,
gpsData.lat_raw < 0 ? "-" : "", lat_d, lat_fl,
gpsData.lon_raw < 0 ? "-" : "", lon_d, lon_fl,
(gpsData.alt_raw / 1000), atoi(predkosc), kierunek, temperatura, napiecie, gpsData.fix, gpsData.sats_raw, flaga);
}
CRC_rtty = 0xffff; //napiecie flaga
CRC_rtty = gps_CRC16_checksum(buf_rtty + 7);
@ -289,13 +253,18 @@ int main(void) {
send_cun++;
}
if (new_GPS_msg) {
//processGPS();
}
}
void processGPS() {
if (new_GPS_msg) {
//print(GPS_buf);
new_GPS_msg = 0;
if (strncmp(GPS_buf, "$GPRMC", 6) == 0) {
if (czytaj_GPS(gps_RMC_czas, gps_RMC_czas_len, GPS_buf, czas) == 0) {
strcpy(czas, "000000");
}
// if (czytaj_GPS(gps_RMC_czas, gps_RMC_czas_len, GPS_buf, czas) == 0) {
// strcpy(czas, "000000");
// }
if (czytaj_GPS(gps_RMC_kierunek, gps_RMC_kierunek_len, GPS_buf, kierunek) == 0) {
strcpy(kierunek, "0");
@ -341,27 +310,25 @@ int main(void) {
if (strncmp(GPS_buf, "$GPZDA", 6) == 0) {
switch (GPSConf) {
case 0:
sendtogps(confGPSNAV, sizeof(confGPSNAV) / sizeof(uint8_t));
send_ublox_packet((uBloxPacket *) confGPSNAV);
break;
case 1:
sendtogps(GPS_GSV_OFF, sizeof(GPS_GSV_OFF) / sizeof(uint8_t));
send_ublox_packet((uBloxPacket *) GPS_GSV_OFF);
break;
case 2:
sendtogps(GPS_GSA_OFF, sizeof(GPS_GSA_OFF) / sizeof(uint8_t));
send_ublox_packet((uBloxPacket *) GPS_GSA_OFF);
break;
case 3:
sendtogps(GPS_GLL_OFF, sizeof(GPS_GLL_OFF) / sizeof(uint8_t));
send_ublox_packet((uBloxPacket *) GPS_GLL_OFF);
break;
case 4:
sendtogps(GPS_ZDA_OFF, sizeof(GPS_ZDA_OFF) / sizeof(uint8_t));
send_ublox_packet((uBloxPacket *) GPS_ZDA_OFF);
break;
default:break;
}
GPSConf++;
}
}
}
}
#pragma clang diagnostic pop

Wyświetl plik

@ -41,3 +41,11 @@ void radio_soft_reset() {
void radio_enable_tx() {
radio_rw_register(0x07, 0x48, 1);
}
int8_t radio_read_temperature() {
uint8_t temp;
temp = radio_rw_register(0x11, 0xff, 0); //odczyt ADC
int8_t temperatura = (int8_t) (-64 + (temp * 5 / 10) - 16);
radio_rw_register(0x0f, 0x80, 1);
return temperatura;
}

Wyświetl plik

@ -20,5 +20,6 @@ void radio_set_tx_frequency();
void radio_disable_tx();
void radio_soft_reset();
void radio_enable_tx();
int8_t radio_read_temperature();
#endif //STM32_RTTY_RADIO_H

167
ublox.c 100644
Wyświetl plik

@ -0,0 +1,167 @@
//
// Created by Admin on 2016-12-27.
//
#include <stm32f10x_usart.h>
#include <string.h>
#include "ublox.h"
#include "delay.h"
#include "init.h"
GPSEntry currentGPSData;
volatile uint8_t active = 0;
void _sendSerialByte(uint8_t message) {
while (USART_GetFlagStatus(USART1, USART_FLAG_TC) == RESET) {
}
USART_SendData(USART1, message);
}
void send_ublox(uint8_t msgClass, uint8_t msgId, uint8_t *payload, uint16_t payloadSize) {
uBloxChecksum chksum = ublox_calc_checksum(msgClass, msgId, payload, payloadSize);
_sendSerialByte(0xB5);
_sendSerialByte(0x62);
_sendSerialByte(msgClass);
_sendSerialByte(msgId);
_sendSerialByte((uint8_t) (payloadSize & 0xff));
_sendSerialByte((uint8_t) (payloadSize >> 8));
uint16_t i;
for (i = 0; i < payloadSize; ++i) {
_sendSerialByte(payload[i]);
}
_sendSerialByte(chksum.ck_a);
_sendSerialByte(chksum.ck_b);
}
void send_ublox_packet(uBloxPacket * packet){
send_ublox(packet->header.messageClass, packet->header.messageId, (uint8_t*)&packet->data, packet->header.payloadSize);
}
uBloxChecksum ublox_calc_checksum(const uint8_t msgClass, const uint8_t msgId, const uint8_t *message, uint16_t size) {
uBloxChecksum ck = {0, 0};
uint8_t i;
ck.ck_a += msgClass;
ck.ck_b += ck.ck_a;
ck.ck_a += msgId;
ck.ck_b += ck.ck_a;
ck.ck_a += size & 0xff;
ck.ck_b += ck.ck_a;
ck.ck_a += size >> 8;
ck.ck_b += ck.ck_a;
for (i =0;i<size;i++){
ck.ck_a += message[i];
ck.ck_b += ck.ck_a;
}
return ck;
}
void ublox_get_last_data(GPSEntry * gpsEntry){
__disable_irq();
memcpy(gpsEntry, &currentGPSData, sizeof(GPSEntry));
__enable_irq();
}
void ublox_init(){
uBloxPacket msfcgprt = {.header = {0xb5, 0x62, .messageClass=0x06, .messageId=0x00, .payloadSize=sizeof(uBloxCFGPRTPayload)},
.data.cfgprt = {.portID=1, .reserved1=0, .txReady=0, .mode=0b00100011000000, .baudRate=9600,
.inProtoMask=1, .outProtoMask=1, .flags=0, .reserved2={0,0}}};
send_ublox_packet(&msfcgprt);
_delay_ms(10);
// init_usart_gps(57600);
// _delay_ms(10);
uBloxPacket msgcfgmsg = {.header = {0xb5, 0x62, .messageClass=0x06, .messageId=0x01, .payloadSize=sizeof(uBloxCFGMSGPayload)},
.data.cfgmsg = {.msgClass=0x01, .msgID=0x02, .rate=1}};
send_ublox_packet(&msgcfgmsg);
_delay_ms(10);
msgcfgmsg.data.cfgmsg.msgID = 0x6;
send_ublox_packet(&msgcfgmsg);
_delay_ms(10);
msgcfgmsg.data.cfgmsg.msgID = 0x21;
send_ublox_packet(&msgcfgmsg);
_delay_ms(10);
uBloxPacket msgcfgnav5 = {.header = {0xb5, 0x62, .messageClass=0x06, .messageId=0x24, .payloadSize=sizeof(uBloxCFGNAV5Payload)},
.data.cfgnav5={.mask=0b00000001111111111, .dynModel=8, .fixMode=3, .fixedAlt=0, .fixedAltVar=10000, .minElev=2, .drLimit=0, .pDop=0xfa, .tDop=0xfa,
.pAcc=100, .tAcc=300, .staticHoldThresh=0, .dgnssTimeout=0, .cnoThreshNumSVs=0, .cnoThresh=0, .reserved1={0,0}, .staticHoldMaxDist=0,
.utcStandard=0, .reserved2={0,0,0,0,0}}};
send_ublox_packet(&msgcfgnav5);
_delay_ms(10);
}
void ublox_handle_incoming_byte(uint8_t data){
static uint8_t sync = 0;
static uint8_t buffer_pos = 0;
volatile static uBloxPacket incoming_packet;
if (!sync){
if (!buffer_pos && data == 0xB5){
buffer_pos = 1;
incoming_packet.header.sc1 = data;
} else if (buffer_pos == 1 && data == 0x62){
sync = 1;
buffer_pos = 2;
incoming_packet.header.sc2 = data;
} else {
buffer_pos = 0;
}
} else {
((uint8_t *)&incoming_packet)[buffer_pos] = data;
if ((buffer_pos >= sizeof(uBloxHeader)-1) && (buffer_pos-1 == (incoming_packet.header.payloadSize + sizeof(uBloxHeader) + sizeof(uBloxChecksum)))){
ublox_handle_packet((uBloxPacket *) &incoming_packet);
buffer_pos = 0;
sync = 0;
} else {
buffer_pos++;
if (buffer_pos == 255) {
buffer_pos = 0;
sync = 0;
}
}
}
}
void ublox_handle_packet(uBloxPacket *pkt) {
uBloxChecksum cksum = ublox_calc_checksum(pkt->header.messageClass, pkt->header.messageId, (const uint8_t *) &pkt->data, pkt->header.payloadSize);
uBloxChecksum *checksum = (uBloxChecksum *)(((uint8_t*)&pkt->data) + pkt->header.payloadSize);
if (cksum.ck_a != checksum->ck_a || cksum.ck_b != checksum->ck_b) {
currentGPSData.fix = 0xf;
} else {
if (pkt->header.messageClass == 0x01 && pkt->header.messageId == 0x07){
currentGPSData.fix = pkt->data.navpvt.fixType;
currentGPSData.lat_raw = pkt->data.navpvt.lat;
currentGPSData.lon_raw = pkt->data.navpvt.lon;
currentGPSData.alt_raw = pkt->data.navpvt.hMSL;
currentGPSData.hours = pkt->data.navpvt.hour;
currentGPSData.minutes = pkt->data.navpvt.min;
currentGPSData.seconds = pkt->data.navpvt.sec;
currentGPSData.sats_raw = pkt->data.navpvt.numSV;
currentGPSData.speed_raw = pkt->data.navpvt.gSpeed;
} else if (pkt->header.messageClass == 0x01 && pkt->header.messageId == 0x02){
currentGPSData.lat_raw = pkt->data.navposllh.lat;
currentGPSData.lon_raw = pkt->data.navposllh.lon;
currentGPSData.alt_raw = pkt->data.navposllh.hMSL;
} else if (pkt->header.messageClass == 0x01 && pkt->header.messageId == 0x06){
currentGPSData.fix = pkt->data.navsol.gpsFix;
currentGPSData.sats_raw = pkt->data.navsol.numSV;
} else if (pkt->header.messageClass == 0x01 && pkt->header.messageId == 0x21){
currentGPSData.hours = pkt->data.navtimeutc.hour;
currentGPSData.minutes = pkt->data.navtimeutc.min;
currentGPSData.seconds = pkt->data.navtimeutc.sec;
} else if (pkt->header.messageClass == 0x05 && pkt->header.messageId == 0x01){
currentGPSData.fix += 1;
} else if (pkt->header.messageClass == 0x05 && pkt->header.messageId == 0x00){
currentGPSData.fix += 30;
}
}
}

185
ublox.h 100644
Wyświetl plik

@ -0,0 +1,185 @@
//
// Created by Admin on 2016-12-27.
//
#ifndef STM32_RTTY_UBLOX_H
#define STM32_RTTY_UBLOX_H
#include <stdint.h>
typedef struct {
int32_t lat_raw;
int32_t lon_raw;
int32_t alt_raw;
int32_t speed_raw;
uint8_t sats_raw;
uint8_t seconds;
uint8_t minutes;
uint8_t hours;
uint8_t fix;
} GPSEntry;
typedef struct __attribute__((packed)){
uint8_t sc1; // 0xB5
uint8_t sc2; // 0x62
uint8_t messageClass;
uint8_t messageId;
uint16_t payloadSize;
} uBloxHeader;
typedef struct {
uint8_t ck_a;
uint8_t ck_b;
} uBloxChecksum;
typedef struct {
uint32_t iTOW; //GPS time of week of the navigation epoch. [- ms]
uint16_t year; //Year (UTC) [- y]
uint8_t month; //Month, range 1..12 (UTC) [- month]
uint8_t day; //Day of month, range 1..31 (UTC) [- d]
uint8_t hour; //Hour of day, range 0..23 (UTC) [- h]
uint8_t min; //Minute of hour, range 0..59 (UTC) [- min]
uint8_t sec; //Seconds of minute, range 0..60 (UTC) [- s]
uint8_t valid; //Validity flags (see graphic below) [- -]
uint32_t tAcc; //Time accuracy estimate (UTC) [- ns]
int32_t nano; //Fraction of second, range -1e9 .. 1e9 (UTC) [- ns]
uint8_t fixType; //GNSSfix Type: [- -]
uint8_t flags; //Fix status flags (see graphic below) [- -]
uint8_t flags2; //Additional flags (see graphic below) [- -]
uint8_t numSV; //Number of satellites used in Nav Solution [- -]
int32_t lon; //Longitude [1e-7 deg]
int32_t lat; //Latitude [1e-7 deg]
int32_t height; //Height above ellipsoid [- mm]
int32_t hMSL; //Height above mean sea level [- mm]
uint32_t hAcc; //Horizontal accuracy estimate [- mm]
uint32_t vAcc; //Vertical accuracy estimate [- mm]
int32_t velN; //NED north velocity [- mm/s]
int32_t velE; //NED east velocity [- mm/s]
int32_t velD; //NED down velocity [- mm/s]
int32_t gSpeed; //Ground Speed (2-D) [- mm/s]
int32_t headMot; //Heading of motion (2-D) [1e-5 deg]
uint32_t sAcc; //Speed accuracy estimate [- mm/s]
uint32_t headAcc; //Heading accuracy estimate (both motion and vehicle) [1e-5 deg]
uint16_t pDOP; //Position DOP [0.01 -]
uint8_t reserved1[6]; //Reserved [- -]
int32_t headVeh; //Heading of vehicle (2-D) [1e-5 deg]
uint8_t reserved2[4]; //Reserved [- -]
} uBloxNAVPVTPayload;
typedef struct {
uint32_t iTOW; //GPS Millisecond Time of Week [- ms]
int32_t lon; //Longitude [1e-7 deg]
int32_t lat; //Latitude [1e-7 deg]
int32_t height; //Height above Ellipsoid [- mm]
int32_t hMSL; //Height above mean sea level [- mm]
uint32_t hAcc; //Horizontal Accuracy Estimate [- mm]
uint32_t vAcc; //Vertical Accuracy Estimate [- mm]
} uBloxNAVPOSLLHPayload;
typedef struct {
uint32_t iTOW; //GPS Millisecond Time of Week [- ms]
int32_t fTOW; //Fractional Nanoseconds remainder of rounded ms above, range -500000 .. 500000 [- ns]
int16_t week; //GPS week (GPS time) [- -]
uint8_t gpsFix; //GPSfix Type, range 0..5 0x00 = No Fix 0x01 = Dead Reckoning only 0x02 = 2D-Fix 0x03 = 3D-Fix 0x04 = GPS + dead reckoning combined 0x05 = Time only fix 0x06..0xff: reserved [- -]
uint8_t flags; //Fix Status Flags (see graphic below) [- -]
int32_t ecefX; //ECEF X coordinate [- cm]
int32_t ecefY; //ECEF Y coordinate [- cm]
int32_t ecefZ; //ECEF Z coordinate [- cm]
uint32_t pAcc; //3D Position Accuracy Estimate [- cm]
int32_t ecefVX; //ECEF X velocity [- cm/s]
int32_t ecefVY; //ECEF Y velocity [- cm/s]
int32_t ecefVZ; //ECEF Z velocity [- cm/s]
uint32_t sAcc; //Speed Accuracy Estimate [- cm/s]
uint16_t pDOP; //Position DOP [0.01 -]
uint8_t reserved1; //Reserved [- -]
uint8_t numSV; //Number of SVs used in Nav Solution [- -]
uint32_t reserved2; //Reserved [- -]
} uBloxNAVSOLPayload;
typedef struct {
uint32_t tAcc; //Time Accuracy Estimate [- ns]
int32_t nano; //Nanoseconds of second, range -1e9 .. 1e9 (UTC) [- ns]
uint16_t year; //Year, range 1999..2099 (UTC) [- y]
uint8_t month; //Month, range 1..12 (UTC) [- month]
uint8_t day; //Day of Month, range 1..31 (UTC) [- d]
uint8_t hour; //Hour of Day, range 0..23 (UTC) [- h]
uint8_t min; //Minute of Hour, range 0..59 (UTC) [- min]
uint8_t sec; //Seconds of Minute, range 0..59 (UTC) [- s]
uint8_t valid; //Validity Flags (see graphic below) [- -]
} uBloxNAVTIMEUTCPayload;
typedef struct {
uint8_t portID; //Port Identifier Number (see Serial [- -]
uint8_t reserved1; //Reserved [- -]
uint16_t txReady; //TX ready PIN configuration [- -]
uint32_t mode; //A bit mask describing the UART mode [- -]
uint32_t baudRate; //Baud rate in bits/second [- Bits/s]
uint16_t inProtoMask; //A mask describing which input protocols are active. [- -]
uint16_t outProtoMask; //A mask describing which output protocols are active. [- -]
uint16_t flags; //Flags bit mask (see graphic below) [- -]
uint8_t reserved2[2]; //Reserved [- -]
} uBloxCFGPRTPayload;
typedef struct {
uint8_t clsID; //Message Class [- -]
uint8_t msgID; //Message Identifier [- -]
uint8_t ck_a;
uint8_t ck_b;
} uBloxACKACKayload;
typedef struct {
uint8_t msgClass; //Message Class [- -]
uint8_t msgID; //Message Identifier [- -]
uint8_t rate; //Send rate on current Port [- -]
} uBloxCFGMSGPayload;
typedef struct {
uint16_t mask; //Parameters Bitmask. Only the masked parameters will be applied. [- -]
uint8_t dynModel; //Dynamic platform model: 0: portable 2: stationary 3: pedestrian 4: automotive 5: sea 6: airborne with <1g acceleration 7: airborne with <2g acceleration 8: airborne with <4g acceleration 9: wrist worn watch (not supported in protocol versions less than 18) [- -]
uint8_t fixMode; //Position Fixing Mode: 1: 2D only 2: 3D only 3: auto 2D/3D [- -]
int32_t fixedAlt; //Fixed altitude (mean sea level) for 2D fix mode. [0.01 m]
uint32_t fixedAltVar; //Fixed altitude variance for 2D mode. [0.0001 m^2]
int8_t minElev; //Minimum Elevation for a GNSS satellite to be used in NAV [- deg]
uint8_t drLimit; //Reserved [- s]
uint16_t pDop; //Position DOP Mask to use [0.1 -]
uint16_t tDop; //Time DOP Mask to use [0.1 -]
uint16_t pAcc; //Position Accuracy Mask [- m]
uint16_t tAcc; //Time Accuracy Mask [- m]
uint8_t staticHoldThresh; //Static hold threshold [- cm/s]
uint8_t dgnssTimeout; //DGNSS timeout [- s]
uint8_t cnoThreshNumSVs; //Number of satellites required to have C/N0 above cnoThresh for a fix to be attempted [- -]
uint8_t cnoThresh; //C/N0 threshold for deciding whether to attempt a fix [- dBHz]
uint8_t reserved1[2]; //Reserved [- -]
uint16_t staticHoldMaxDist; //Static hold distance threshold (before quitting static hold) [- m]
uint8_t utcStandard; //UTC standard to be used: 0: Automatic; receiver selects based on GNSS configuration (see GNSS time bases). 3: UTC as operated by the U.S. Naval Observatory (USNO); derived from GPS time 6: UTC as operated by the former Soviet Union; derived from GLONASS time 7: UTC as operated by the National Time Service Center, China; derived from BeiDou time (not supported in protocol versions less than 16). [- -]
uint8_t reserved2[5]; //Reserved [- -]
} uBloxCFGNAV5Payload;
typedef union {
uBloxNAVPVTPayload navpvt;
uBloxCFGPRTPayload cfgprt;
uBloxCFGMSGPayload cfgmsg;
uBloxCFGNAV5Payload cfgnav5;
uBloxNAVPOSLLHPayload navposllh;
uBloxNAVSOLPayload navsol;
uBloxNAVTIMEUTCPayload navtimeutc;
uBloxACKACKayload ackack;
} ubloxPacketData;
typedef struct __attribute__((packed)){
uBloxHeader header;
ubloxPacketData data;
} uBloxPacket;
void ublox_init();
void send_ublox(uint8_t msgClass, uint8_t msgId, uint8_t *payload, uint16_t payloadSize);
void send_ublox_packet(uBloxPacket * packet);
void ublox_get_last_data(GPSEntry * gpsEntry);
uBloxChecksum ublox_calc_checksum(const uint8_t msgClass, const uint8_t msgId, const uint8_t *message, uint16_t size);
void ublox_handle_incoming_byte(uint8_t data);
void ublox_handle_packet(uBloxPacket *pkt);
#endif //STM32_RTTY_UBLOX_H