1.串口收发+六分科技差分定位官方sdk融合
1.1代码分析
1.1.1串口收发
首先,官方sdk中存在三种工作状态:初始化、start和running
while (SIXENTS_TRUE)
{
usleep(200 * 1000); // 200ms
/****************************************
* csdk_run_step: 0 sdk init
* 1 sdk start
* 2 work
****************************************/
switch (csdk_run_step)
{
case 0:
{
retVal = sixents_sdkInit(¶m);
if (retVal != SIXENTS_RET_OK)
{
printf("---MAIN case 0| sixents_sdkInit failed! retVal:%d.\r\n", retVal);
sixents_sdkFinal();
}
else
{
printf("---MAIN case 0| sixents_sdkInit success---\r\n");
csdk_run_step = 1;
}
}
break;
case 1:
{
printf("---MAIN case 1| sixents_sdkStart start---\r\n");
retVal = sixents_sdkStart();
if (retVal != SIXENTS_RET_OK)
{
printf("---MAIN case 1| sixents_sdkStart failed! retVal:%d ---\r\n", retVal);
usleep(3000 * 1000); // 3s
}
else
{
printf("---MAIN case 1| sixents_sdkStart success---\r\n");
csdk_run_step = 2;
}
}
break;
case 2:
{
if ((count % 5) == 0) // 1s发送一次GGA
{
//pthread_create(&recvthread,NULL,recv_thread,NULL);
res = read(fd, buf, 110);
if(res==0)
continue;
buf[res]=0;
printf("%s",buf);
printf("\n");
sixents_char gga_temp[3];
printf("buf_len %d\n",strlen(buf));
//if(TRUE == recv_done){
retVal = sixents_sdkSendGGAStr(buf,strlen(buf));
//GetDiffData(test,110);
if (retVal != SIXENTS_RET_OK)
{
printf("%s| Send GGA failed with error: %d.\n", __FUNCTION__, retVal);
if(retVal == SIXENTS_RET_INVALID_PARAM){
printf("!!!!!!!!!!!\n");
}
}
//}
}
retVal = sixents_sdkTick();
if (retVal != SIXENTS_RET_OK)
{
printf("%s| sdkTick failed with error: %d.\n", __FUNCTION__, retVal);
}
count++;
}
break;
default:
printf("[six-log]:switch nothing\r\n");
break;
}
} // while
return retVal;
}
只要连上网络,sdk就会初始化和start成功,我们就把串口收发写到case running:阶段。
(1)首先,打开串口/dev/ttyUSB0,然后设置波特率以及校验位。
printf("uart Start...\n");
fd = open(UART_DEVICE, O_RDWR|O_NOCTTY);
if (fd < 0) {
perror(UART_DEVICE);
exit(1);
}
printf("uart Open...\n");
set_speed(fd,115200);
if (set_parity(fd,8,1,'N') == FALSE) {
printf("Set Parity Error\n");
exit (0);
}
打开串口之后,就要到串口去读数据:
res = read(fd, buf, 110);
if(res==0)
continue;
buf[res]=0;
printf("%s",buf);
printf("\n");
printf("buf_len %d\n",strlen(buf));
读完数据就要把buf放到这里上传服务器,进行差分定位
retVal = sixents_sdkSendGGAStr(buf,strlen(buf));
//GetDiffData(test,110);
if (retVal != SIXENTS_RET_OK)
{
printf("%s| Send GGA failed with error: %d.\n", __FUNCTION__, retVal);
if(retVal == SIXENTS_RET_INVALID_PARAM)
{
printf("!!!!!!!!!!!\n");
}
}
服务器回传回来的差分数据会进入一个回调函数里,然后进行处理:
void GetDiffData( sixents_char *buff, sixents_uint32 len)
{
sixents_uint32 i;
int res = 0;
printf("len isNNNNNNNNNNNNNNNNN: %d\n",len);
// if ((buff == sixents_null) || (len == 0))
// {
// return;
// }
printf("len isBBBBBBBBBBBBBBBBB: %d\n",len);
write(fd,buff,sizeof(buff));
sixents_char test();
//sixents_char buff();
// //ToDo: 以下应该修改为客户自己对差分数据处理的逻辑
// for (i = 0; i < len; i++)
// {
// printf("%x ", (sixents_uint8)buff[i]);
// if ((i + 1) % 80u == 0)
// {
// printf("\n");
// }
// }
// write(fd,buff,sizeof(buff));
//printf("%s ", buff);
// memcpy(gga,buff,sizeof(buff));
//pthread_mutex_lock(&g_mutex_recv_info);
//pthread_cond_wait(&gCond_recv_DATA, &g_mutex_recv_info);
//write(fd, buff, strlen(buff));
///printf("\n");
//pthread_mutex_unlock(&g_mutex_recv_info);
}
以上的效果是,终端界面可以打印出GPFPD数据,但是下发是乱码
1.2存在的问题:
(1)接收数据为乱码
解决:后来自己写了一个线程
pthread_t recvthread;
char *recv_thread()
{
int c=0, res;
int i=0;
int j=0;
sixents_char buf[1024]={'\0'};
// char buff[sizeof(char)]={'\0'};
char *p_GPGGA = NULL;
p_GPGGA = (char*)malloc(1024);
char *q_GPGGA = NULL;
q_GPGGA = (char*)malloc(1024);
fd = open(UART_DEVICE, O_RDWR|O_NOCTTY);
if (fd < 0) {
perror(UART_DEVICE);
exit(1);
}
printf("uart Open...\n");
set_speed(fd,115200);
if (set_parity(fd,8,1,'N') == FALSE) {
printf("Set Parity Error\n");
}
read(fd, buf, 512);
printf("read buf len is: %d\n",strlen(buf));
for(i=0;i<strlen(buf);i++)
{
printf("%c", buf[i]);
}
printf("\n");
printf("read done\n");
for(i=0;i<strlen(buf);i++)
{
if(buf[i]==SIX_GPGGA)
{
j++;
}
}
printf("j++ done\n");
if(j!=14)
{
printf("Get Num Error");
}
p_GPGGA = strchr(buf, '*');
p_GPGGA = strchr(buf, SIX_GPGGA);
/*获取北京时间,获取到的时间格式为hhmmss.ss,小数点后的ss为毫秒*/
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.time_GPGGA = (int)(atof(p_GPGGA) * 100);
/* 获取纬度 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.lat = atof(q_GPGGA);
/* 获取是北纬还是南纬 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.lat_dir = (unsigned char)atoi(p_GPGGA);
/* 获取经度 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.lon = atof(q_GPGGA);
/* 获取西经还是东经 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.lon_dir = (unsigned char)atoi(p_GPGGA);
/* 获取当前GPS、状态 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.qual_GPGGA = (unsigned char)atoi(q_GPGGA);
/* 获取当前卫星数目 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.sats_GPGGA = (unsigned char)atoi(p_GPGGA);
/* 获取水平精度因子 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.hdop_GPGGA = (float)atof(q_GPGGA);
/* 获取天线高度 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.alt_GPGGA = atof(p_GPGGA);
/* 获取天线高度单位 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.a_unit_GPGGA = *q_GPGGA;
/* 获取大地水准面差距 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.undulation_GPGGA = atof(p_GPGGA);
/* 获取大地水准差距单位 */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, SIX_GPGGA);
*p_GPGGA = 0;
recvbuf.u_unit_GPGGA = *q_GPGGA;
/* 获取差分数据龄期,单位为秒 */
p_GPGGA++;
q_GPGGA = strchr(p_GPGGA, SIX_GPGGA);
*q_GPGGA = 0;
recvbuf.age_GPGGA = (unsigned short)atoi(p_GPGGA);
/* 获取差分基站ID */
q_GPGGA++;
p_GPGGA = strchr(q_GPGGA, '*');
*p_GPGGA = 0;
recvbuf.stn_GPGGA = (unsigned short)atoi(q_GPGGA);
recv_done = TRUE;
pthread_mutex_lock(&g_mutex_recv_info);
// memset(gga, 0, sizeof(gga));
memcpy(gga,&recvbuf,sizeof(gga));
//pthread_cond_signal(&gCond_recv_DATA);
pthread_mutex_unlock(&g_mutex_recv_info);
pthread_join(recv_thread, NULL);
free(p_GPGGA);
free(q_GPGGA);
}
(2)回调函数有问题:
这个回调函数我没看懂
void GetDiffData( sixents_char *buff, sixents_uint32 len)
{
sixents_uint32 i;
int res = 0;
printf("len isNNNNNNNNNNNNNNNNN: %d\n",len);
// if ((buff == sixents_null) || (len == 0))
// {
// return;
// }
write(fd,buff,sizeof(buff));
sixents_char test();
//sixents_char buff();
}
这是回调函数吗?
我特定去查了一下,回调函数参数是函数指针,如下形式:
/回调函数:如果函数中的参数带有函数指针,就称这个函数为回调函数
void call(void(*pl)())
{
hello();
show();
}
void hello()
{
printf("\n");
}
void show()
{
printf("\n");
}
int main(int argc, char *argv[])
{
call(hello);
call(show);
return 0;
}
接下来我仿照写了一个:
sixents_char test()
{
int i = 0;
for (i = 0; i < strlen(buf); i++)
{
printf("CCCCCCCCCCCCCc:%c ", buf[i]);
}
write(fd,buf,sizeof(buf));
}
void GetDiffData( sixents_char (*buff)(), sixents_uint32 len)
{
sixents_uint32 i;
int res = 0;
printf("len isNNNNNNNNNNNNNNNNN: %d\n",len);
// if ((buff == sixents_null) || (len == 0))
// {
// return;
// }
sixents_char test();
sixents_char buff();
}
int main()
{
retVal = sixents_sdkSendGGAStr(buf,strlen(buf));
GetDiffData(test,110);
}