STM32 GPS+BD ATGM332D定位

Posted 为了维护世界和平_

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了STM32 GPS+BD ATGM332D定位相关的知识,希望对你有一定的参考价值。

ATGM332D简介

高性能、低功耗 GPS、北斗双模定位模块

特性

特性说明
基本功能三维位置定位(经纬度、海拔),测速,授时
导航系统GPS、北斗 BDS(双模)
支持辅助GNSS
位置定位精度2.5 米(圆概率误差 CEP50)
测速精度<0.1m/s
航向角精度0.5 度
授时精度<30ns
射频通道数目支持全星座北斗 BDS、GPS 同时接收
定位时间冷启动:≤32s ; 热启动:≤1s
冷启动捕获灵敏度-148dBm
热启动捕获灵敏度-156dBm
重捕获灵敏度-160dBm
跟踪灵敏度-162dBm
导航信息最高更新速率1Hz(默认),最大 10Hz
串口预留有 TTL 电平标准的串口,支持与使用 3.3/5V 电平标
准的系统通讯支持传输速率:4800、9600、115200bps,默认为 9600bps
协议NMEA0183
输出的经纬度坐标系WGS-84 坐标系
最大高度18000m
最大速度515m/s
最大加速度4g
电源通过模块引出的电源引脚 3.3~5V 供电
工作温度-40 到+85 摄氏度
保存温度-40 到+125 摄氏度
功耗连续运行<25mA (@3.3V

引脚接入

名称说明
VCC电源线,正常电压范围为:3.3~5V
GND地线
TXD串口数据发送信号线,使用 TTL 电平
RXD串口数据接收信号线,使用 TTL 电平
PPS时间脉冲信号线,模块接收到 GPS 时间信息后,输出可调节的脉冲信号,默认为 1Hz,脉冲上升沿与 UTC 时间对齐

GPS模块 STM32
TXD <------->PA3
RXD<-------> PA2

串口通信

UART->DMA中断
gpio配置

#define GPS_USART                             USART2
#define GPS_USART_CLK                         RCC_APB1Periph_USART2
#define GPS_RCC_PeriphClockCmd_Fun          RCC_APB1PeriphClockCmd

#define GPS_USART_RX_GPIO_PORT                GPIOA
#define GPS_USART_RX_GPIO_CLK                 RCC_APB2Periph_GPIOA
#define GPS_USART_RX_PIN                      GPIO_Pin_3

#define GPS_USART_TX_GPIO_PORT                GPIOA
#define GPS_USART_TX_GPIO_CLK                 RCC_APB2Periph_GPIOA
#define GPS_USART_TX_PIN                      GPIO_Pin_2

#define GPS_DMA                      DMA1
#define GPS_DMA_CLK                  RCC_AHBPeriph_DMA1
#define GPS_DMA_CHANNEL              DMA1_Channel6
#define GPS_DMA_IRQn                 DMA1_Channel6_IRQn         //中断源

static void GPS_USART_Config(void)

	GPIO_InitTypeDef GPIO_InitStructure;
	USART_InitTypeDef USART_InitStructure;
	
	/* config USART clock */
	RCC_APB2PeriphClockCmd(GPS_USART_RX_GPIO_CLK|GPS_USART_TX_GPIO_CLK, ENABLE);
	GPS_RCC_PeriphClockCmd_Fun(GPS_USART_CLK, ENABLE);
	/* USART GPIO config */
   /* Configure USART Tx  as alternate function push-pull */
    GPIO_InitStructure.GPIO_Pin = GPS_USART_TX_PIN;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPS_USART_TX_GPIO_PORT, &GPIO_InitStructure);   
    /* Configure USART Rx as input floating */
    GPIO_InitStructure.GPIO_Pin = GPS_USART_RX_PIN;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
    GPIO_Init(GPS_USART_TX_GPIO_PORT, &GPIO_InitStructure);
	/* USART2 mode config */
	USART_InitStructure.USART_BaudRate = GPS_USART_BAUDRATE;//波特率 
	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_Rx | USART_Mode_Tx;

	USART_Init(GPS_USART, &USART_InitStructure); 
	USART_Cmd(GPS_USART, ENABLE);	


gps dma配置

static void GPS_DMA_Config(void)

   		DMA_InitTypeDef DMA_InitStructure;
		RCC_AHBPeriphClockCmd(GPS_DMA_CLK, ENABLE);//DMA时钟
		DMA_InitStructure.DMA_PeripheralBaseAddr = GPS_DATA_ADDR;//DMA源,串口数据寄存器地址	   
		DMA_InitStructure.DMA_MemoryBaseAddr = (u32)gps_rbuff;//收到数据地址
		DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;//内存到外设	
		DMA_InitStructure.DMA_BufferSize = GPS_RBUFF_SIZE;//传输大小   
		DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable; //外设地址不增
		DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;	//内存地址递增
		DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;//外设数据单位
		DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;	 //内存数据单位
		DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;	//不断循环 
		DMA_InitStructure.DMA_Priority = DMA_Priority_Medium;  //优先级 中
		DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;//禁止内存到内存	   
		DMA_Init(GPS_DMA_CHANNEL, &DMA_InitStructure); 	   //配置DMA通道
        GPS_Interrupt_Config();
        DMA_ITConfig(GPS_DMA_CHANNEL,DMA_IT_HT|DMA_IT_TC,ENABLE);  //DMA发送完产生中断
		/*使能DMA*/
		DMA_Cmd (GPS_DMA_CHANNEL,ENABLE);		
		USART_DMACmd(GPS_USART, USART_DMAReq_Rx, ENABLE);//配置串口向DMA发出TX请求


NMEA 协议解析

NMEA 是美国国家海洋电子协会(National Marine Electronics Association )为海用电子设备制定的标准格式,目前已经成为了 GPS 导航设备统一的 RTCM 标准协议。已成为所有的定位接收机中最通用的数据输出格式。

NMEA-0183 是一套定义接收机输出的标准信息,有几种不同的格式,每种都是独立相关的 ASCII 格式,使用逗号隔开数据,数据流长度从 30-100 字符不等,通常以每秒间隔选择输出,最常用的格式为"GGA",它包含了定位时间,纬度,经度,高度,定位所用的卫星数,DOP 值,差分状态和校正时段等,其他的有速度,跟踪,日期等。

语句协议解析
语句协议

该协议采用 ASCII 码。 帧格式形如: a a c c c , d d d , d d d , … , d d d ∗ h h < C R > < L F > < 1 > “ aaccc,ddd,ddd,…,ddd*hh<CR><LF> <1> “ aaccc,ddd,ddd,,dddhh<CR><LF><1>”——帧命令起始位
<2> aaccc——地址域,前两位为识别符,后三位为语句名
<3> ddd…ddd——数据
<4> “”——校验和前缀
<5> hh——校验和(check sum),$与
之间所有字符 ASCII 码的校验和(各字节做异或运
算,得到校验和后,再转换 16 进制格式的 ASCII 字符。)
<6> ——CR(Carriage Return) + LF(Line Feed)帧结束,回车和换

1、GGA 全球定位数据

$GNGGA,<1>,<2>,<3>,<4>,<5>,<6>,<7>,<8>,<9>,<10>,<11>,<12>,<13>,<14>*<15>
$GNGGA,012842.000,2253.7220,N,11350.7025,E,1,11,1.5,44.8,M,0.0,M,*44
<1> UTC 时间,格式为 hhmmss.sss
<2> 纬度,格式为 ddmm.mmmm(前导位数不足则补 0)
<3> 纬度半球,N 或 S(北纬或南纬)
<4> 经度,格式为 dddmm.mmmm(前导位数不足则补 0)
<5> 经度半球,E 或 W(东经或西经)
<6> 定位质量指示,0=定位无效,1=标准定位,2=差分定位,6=估算
<7> 使用卫星数量,从 00 到 12(前导位数不足则补 0)
<8> 水平精确度,0.5 到 99.9
<9> 天线离海平面的高度,-9999.9 到 9999.9 米
<10> 高度单位,M 表示单位米
<11> 大地椭球面相对海平面的高度(-999.9 到 9999.9)
<12> 高度单位,M 表示单位米
<13> 差分 GPS 数据期限(RTCM SC-104),最后设立 RTCM 传送的秒数量
<14> 差分参考基站标号,从 0000 到 1023(前导位数不足则补 0)
<15> 校验和。

2、RMC 推荐最小数据

$ GNRMC,<1>,<2>,<3>,<4>,<5>,<6>,<7>,<8>,<9>,<10>,<11>,<12>,<13><14>
$GNRMC,012841.000,A,2253.7220,N,11350.7025,E,0.00,0.00,140117,A
7B
<1> UTC(Coordinated Universal Time)时间,hhmmss(时分秒)格式
<2> 定位状态,A=有效定位,V=无效定位
<3> Latitude,纬度 ddmm.mmmm(度分)格式(前导位数不足则补 0)
<4> 纬度半球 N(北半球)或 S(南半球)
<5> Longitude,经度 dddmm.mmmm(度分)格式(前导位数不足则补 0
<6> 经度半球 E(东经)或 W(西经)
<7> 地面速率(000.0~999.9 节,Knot,前导位数不足则补 0)
<8> 地面航向(000.0~359.9 度,以真北为参考基准,前导位数不足则补 0)
<9> UTC 日期,ddmmyy(日月年)格式
<10> Magnetic Variation,磁偏角(000.0~180.0 度,前导位数不足则补 0)
<11> Declination,磁偏角方向,E(东)或 W(西)
<12> Mode Indicator,模式指示(仅 NMEA0183 3.00 版本输出,A=自主定位,D=差分,
E=估算,N=数据无效)
<13> NavStatus,导航状态标示符( V 表示系统不输出导航状态信息)
<14> 校验和

3、VTG 地面速度信息(Course over ground and Ground speed)。

$ GNVTG,<1>,<2>,<3>,<4>,<5>,<6>,<7>,<8>,<9><10>
$GNVTG,0.00,T,M,0.00,N,0.00,K,A
23
<1> 以真北为参考基准的地面航向
<2> T,表示“真”
<3> 以磁北为参考基准的地面航向
<4> M,表示“磁场”
<5> 地面速率
<6> N,表示“节”
<7> 地面速率
<8> K,表示“千米/小时”
<9> 模式指示(A=自主定位,D=差分,E=估算,N=数据无效)
<10> 校验和

4、GLL 定位地理信息(Latitude and longitude, with time of position fix and status)

$ GNGLL,<1>,<2>,<3>,<4>,<5>,<6>,<7><8>
$GNGLL,2253.7220,N,11350.7025,E,012842.000,A,A
4D
<1> 纬度 ddmm.mmmmm(度分)
<2> 纬度半球 N(北半球)或 S(南半球)
<3> 经度 dddmm.mmmmm(度分)
<4> 经度半球 E(东经)或 W(西经)
<5> UTC 时间:hhmmss(时分秒)
<6> 定位状态,A=有效定位,V=无效定位
<7> 模式指示(A=自主定位,D=差分,E=估算,N=数据无效)
<8> 校验和

5、ZDA 当前时间信息:(Time and Date)

格式:$ GNZDA,<1>,<2>,<3>,<4>,<5>,<6><7>
例子:$GNZDA,012841.000,14,01,2017,00,00
46
<1> UTC 时间:hhmmss(时分秒,格林威治时间)
<2> 日
<3> 月
<4> 年

6、GSA GPS 精度指针及使用卫星 (GNSS DOP and Active Satellites)。

X X G S A , S m o d e , F S , S V I D , P D O P , H D O P , V D O P ∗ C S < C R > < L F > 例 子 : XXGSA,Smode,FS,SVID,PDOP,HDOP,VDOP*CS<CR><LF> 例子: XXGSA,Smode,FS,SVID,PDOP,HDOP,VDOPCS<CR><LF>GPGSA,A,3,05,13,02,30,15,24,2.2,1.5,1.635
$BDGSA,A,3,01,03,04,08,12,2.2,1.5,1.6
2D
<1> 模式 1:定位型式 1 = 未定位,2 = 二维定位,3 = 三维定位
<2> FS:定位状态标志
<3> ,SVID:用于定位的卫星编号,该字段共显示 12 颗可用卫星编号,多于 12 颗时只输
出前 12 颗, 不足 12 颗时不足的区域补空
<4> PDOP 综合位置精度因子(0.5 - 99.9)
<5> HDOP 水平精度因子(0.5 - 99.9)
<6> VDOP 垂直精度因子(0.5 - 99.9)
<7> systemId:NMEA 所定义的 GNSS 系统 ID 号
<8> 校验和

7、GSV 可视卫星状态输出语句 (GNSS Satellites in View)

$XXGSV,NumMsg,MsgNo,NumSv,SVID,ele,az,cn0 CS
$GPGSV,3,1,09,02,42,118,49,05,38,041,47,06,05,128,39,13,74,039,41
77
$GPGSV,3,2,09,15,68,244,28,20,45,325,21,24,15,180,28,29,47,278,23*72
<1> 总的 GSV 语句电文数
<2> 当前 GSV 语句号
<3> 可视卫星总数,00 至 12
<4> 卫星编号,SVID,ele,az,cn0,01 至 32
<5> 信噪比(C/No),00 至 99dB;无表示未接收到讯号
<6> 校验和。
注:每条语句最多包括四颗卫星的信息,每颗卫星的信息有四个数据项,即:卫星编
号、卫星仰角、卫星方位角、信噪比。

解码库 源码地址

直接使用该解码库,,它使用纯 C 语言编写,支持 windows、winCE 、
UNIX 平台,支持解析 GPGGA,GPGSA,GPGSV,GPRMC,GPVTG 这五种语句
关键代码

nmeaINFO info;          //GPS解码后得到的数据
nmeaPARSER parser;      //解码时使用的数据结构

//gps_rbuff 为串口DMA中断收到的数据
nmea_parse(&parser, (const char*)&gps_rbuff[0], HALF_GPS_RBUFF_SIZE, &info);

串口输出

nmealib在linux下使用

下载源码->编译->运行

root@ubuntu:/home/wy/nmealib# ls
build  CHANGELOG.TXT  doc  include  lib  LICENSE.TXT  Makefile  nmea.ico  nmea.sln  README.TXT  samples  src

make

root@ubuntu:/home/wy/nmealib# make
mkdir -p build/nmea_gcc
gcc  -I include  -Llib -lnmea -lm -c src/generate.c -o build/nmea_gcc/generate.o
gcc  -I include  -Llib -lnmea -lm -c src/generator.c -o build/nmea_gcc/generator.o
gcc  -I include  -Llib -lnmea -lm -c src/parse.c -o build/nmea_gcc/parse.o
gcc  -I include  -Llib -lnmea -lm -c src/parser.c -o build/nmea_gcc/parser.o
gcc  -I include  -Llib -lnmea -lm -c src/tok.c -o build/nmea_gcc/tok.o
gcc  -I include  -Llib -lnmea -lm -c src/context.c -o build/nmea_gcc/context.o
gcc  -I include  -Llib -lnmea -lm -c src/time.c -o build/nmea_gcc/time.o
gcc  -I include  -Llib -lnmea -lm -c src/info.c -o build/nmea_gcc/info.o
gcc  -I include  -Llib -lnmea -lm -c src/gmath.c -o build/nmea_gcc/gmath.o
gcc  -I include  -Llib -lnmea -lm -c src/sentence.c -o build/nmea_gcc/sentence.o
ar rsc lib/libnmea.a build/nmea_gcc/generate.o build/nmea_gcc/generator.o build/nmea_gcc/parse.o build/nmea_gcc/parser.o build/nmea_gcc/tok.o build/nmea_gcc/context.o build/nmea_gcc/time.o build/nmea_gcc/info.o build/nmea_gcc/gmath.o build/nmea_gcc/sentence.o
ranlib lib/libnmea.a
gcc  -I include  -Llib -lnmea -lm  -c samples/generate/main.c -o samples/generate/main.o
gcc   samples/generate/main.o -Llib -lnmea -lm -o build/samples_generate 
gcc  -I include  -Llib -lnmea -lm  -c samples/generator/main.c -o samples/generator/main.o
gcc   samples/generator/main.o -Llib -lnmea -lm -o build/samples_generator 
gcc  -I include  -Llib -lnmea -lm  -c samples/parse/main.c -o samples/parse/main.o
gcc   samples/parse/main.o -Llib -lnmea -lm -o build/samples_parse 
gcc  -I include  -Llib -lnmea -lm  -c samples/parse_file/main.c -o samples/parse_file/main.o
samples/parse_file/main.c: In function ‘trace’:
samples/parse_file/main.c:13:5: warning: implicit declaration of function ‘write’; did you mean ‘fwrite’? [-Wimplicit-function-declaration]
     write(1, str, str_size);
     ^~~~~
     fwrite
gcc   samples/parse_file/main.o -Llib -lnmea -lm -o build/samples_parse_file 
gcc  -I include  -Llib -lnmea -lm  -c samples/math/main.c -o samples/math/main.o
gcc   samples/math/main.o -Llib -lnmea -lm -o build/samples_math 
rm samples/math/main.o samples/generator/main.o samples/parse/main.o samples/generate/main.o samples/parse_file/main.o

samples/parse_file/main.c 主函数

#include <nmea/nmea.h>

#include <string.h>
#include <stdio.h>

#ifdef NMEA_WIN
#   include <io.h>
#endif

void trace(const char *str, int str_size)

    printf("Trace: ");
    write(1, str, str_size);
    printf("\\n");

void error(const char *str, int str_size)

    printf("Error: ");
    write(1, str, str_size);
    printf("\\n");


int main()

    nmeaINFO info;
    nmeaPARSER parser;
    FILE *file;
    char buff[2048];
    int size, it = 0;
    nmeaPOS dpos;

    file = fopen("gpslog.txt", "rb");

    if(!file)
        return -1;

    nmea_property()->trace_func = &trace;
    nmea_property()->error_func = &error;

    nmea_zero_INFO(&info);
    nmea_parser_init(&parser);

    while(!feof(file))
    
        size = (int)fread(&buff[0], 1, 100, file);
        nmea_parse(&parser, &buff[0], size, &info);
        nmea_info2pos(&info, &dpos);
        printf(
            "%03d, Lat: %f, Lon: %f, Sig: %d, Fix: %d\\n",
            it++, dpos.lat, dpos.lon, info.sig, info.fix
            );
    
    fseek(file, 0, SEEK_SET);
    nmea_parser_destroy(&parser);
    fclose(file);
    return 0;

生成全部可执行文件路径以及文件

root@ubuntu:/home/wy/nmealib/build# ls
nmea_gcc  samples_generate  samples_generator  samples_math  samples_parse  samples_parse_file

准备gpslog.txt文件

root@ubuntu:/home/wy/nmealib/build# cp ../samples/parse_file/gpslog.txt .
root@ubuntu:/home/wy/nmealib/build# ls
gpslog.txt  nmea_gcc  samples_generate  samples_generator  samples_math  samples_parse  samples_parse_file

运行samples_parse_file,可以看到转换后的经纬度

root@ubuntu:/home/wy/nmealib/build# ./samples_parse_file
...
$GPGGA,213923.000,4221.1129,N,07102.9146,W,1,04,3.9,129.7,M,-33.7,M,,0000*6F
Trace: 
130, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPGSA,A,3,26,07,06,21,,,,,,,,,4.1,3.9,1.0*3A
Trace: 
131, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPRMC,213923.000,A,4221.1129,N,07102.9146,W,0.00,,010207,,,A*6E
Trace: 
$GPGGA,213924.000,4221.1129,N,07102.9146,W,1,04,3.9,129.7,M,-33.7,M,,0000*68
Trace: 
132, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPGSA,A,3,26,07,06,21,,,,,,,,,4.0,3.9,1.0*3B
Trace: 
133, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPRMC,213924.000,A,4221.1129,N,07102.9146,W,0.00,,010207,,,A*69
Trace: 
$GPGGA,213925.000,4221.1129,N,07102.9146,W,1,04,3.9,129.7,M,-33.7,M,,0000*69
Trace: 
134, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPGSA,A,3,26,07,06,21,,,,,,,,,4.0,3.9,1.0*3B
Trace: 
$GPRMC,213925.000,A,4221.1129,N,07102.9146,W,0.00,,010207,,,A*68
Trace: 
135, Lat: 0.739180, Lon: -1.240032, Sig: 1, Fix: 3
$GPGGA,213926.000,4221.1112,N,07102.9177,W,1,04,3.9,136.5,M,-33.7,M,,0000*6C

以上是关于STM32 GPS+BD ATGM332D定位的主要内容,如果未能解决你的问题,请参考以下文章

iOS 百度坐标、GPS坐标、 高德坐标相互转换

基于STM32实现的的短信实时传送位置----GPS+GSM

GPS坐标(WGS84)转换百度坐标(BD09) python测试

基于STM32设计的遥控小车(手机APP+GPS+温湿度+ESP8266)

基于STM32设计的遥控小车(手机APP+GPS+温湿度+ESP8266)

SIM800C连接OneNet平台HTTP协议上传GPS数据