📄 lowr.c
字号:
/* -------------------------------------------------------------------------- */
PROCX void SendLowrIcons(void)
{
INT i,maxi;
short num;
struct SendIcons {
short IconNumber;
long Latitude;
long Longitude;
BYTE IconSymbol;
} SendIcons;
//
// Get the number of Icons the unit supports
//
num=LowrID.NumOfIcons;
maxi=icons;
if(num<icons) {
fprintf(stderr,"This unit supports %d icons.\n",num);
fprintf(stderr,"Sending %d of %d Icons.\n",num,icons);
maxi=num;
}
//
// Send the # of Icons we're sending
//
num=icons;
LastCommand=0x030A;
SendLowrMessage(LastCommand, (BYTE*)&num, 2, "SendNumOfIconsToSend");
GetLowrMessage(1);
//
// Send each icon separately
//
fprintf(stderr,"I%05d of %05d\r",0,maxi);
for(i=1;i<=maxi;i++) {
fill_icon(i,(unsigned char*)"",0);
LastCommand=0x030B;
SendIcons.IconNumber=i-1;
set_sign();
SendIcons.Latitude=LatDegtoMM(record.la);
SendIcons.Longitude=LongDegtoMM(record.lo);
SendIcons.IconSymbol=convert_to_Lowr(record.icon_smbl);
SendLowrMessage(LastCommand, (BYTE*)&SendIcons, sizeof(struct SendIcons),"SendLowrIcons");
GetLowrMessage(1);
fprintf(stderr,"I%05d\r",i);
}
fprintf(stderr,"\n");
} // void SendLowrIcons(void)
/* -------------------------------------------------------------------------- */
PROCX void SendLowrRoutes(void)
{
INT i,j,cc,points;
INT maxr,maxp;
maxr=LowrID.NumOfRoutes;
maxp=LowrID.NumOfWaypointsPerRoute;
RteGet.Reserved=LowrID.Reserved;
for(i=0;i<maxr;i++) {
in_route=1;
route_number=i;
points=0;
for(j=1;j<=maxp;j++) {
if(route_push[i][j] == NULL) continue;
++points;
strcpy((char*)bin,route_push[i][j]);
if(j==1) {
fill_waypoint_from_push(i,ROUTE_1_WP,0);
strupr(route_comment);
strcpy((char*)RteGet.Name,route_comment);
}
else {
fill_waypoint_from_push(i,ROUTE_WP,0);
}
RteGet.Waypoints[points-1]=(short)MatchRoute(record.ident,record.la,record.lo)-2+LwrStartPt;
if(RteGet.Waypoints[points-1] < 0) {
fprintf(stderr,"Waypoint missing in route. Route %d skipped.\n",i+1);
goto skiproute;
}
cc=kbraw();
cc=toupper(cc);
if( cc=='Y') {
fprintf(stderr,"\nOperator Abort SendLowrRoutes\n");
in_route=0;
return;
} else if(cc=='X') {
fprintf(stderr,"\nOperator Exit SendLowrRoutes\n");
byebye(0);
}
} // for(j=0;j<=MAXPOINTS;j++)
if(points) {
RteGet.RouteNumber=i;
RteGet.NumOfWaypoints=points;
LastCommand=0x0306;
SendLowrMessage(LastCommand,(BYTE*)&RteGet.RouteNumber,(INT)(16+2*points),"SendLowrRoutes");
GetLowrMessage(1);
fprintf(stderr, "R%05d Sent\n",i);
} // if(points)
skiproute:;
points=0;
} // for(i=0;i<=MAXROUTES;i++) {
in_route=0;
} // void SendLowrRoutes()
/* -------------------------------------------------------------------------- */
PROCX void OutputLowr(void)
{
INT i;
if(input_files) {
if(waypoints) {
SendLowrWaypoints();
} // if(waypoints)
if(routes) {
SendLowrRoutes();
if(AbortNow==1) return;
}
if(tracks) {
if(LowrID.ProtocolVersion==0) {
if(to_lowr_track==0) {
for(i=1;i<=LowrID.NumOfPlotTrails;i++)
SendLowrTracksMem(i); // Protocol version 1.0 tracks
}
else {
SendLowrTracksMem(to_lowr_track); // Protocol version 1.0 tracks
}
}
else {
if(to_lowr_track==0) {
for(i=1;i<=LowrID.NumOfPlotTrails;i++)
SendLowrTracks(i); // Protocol version 2.0 tracks
}
else {
SendLowrTracks(to_lowr_track); // Protocol version 2.0 tracks
}
}
} // if(tracks)
if(icons) {
SendLowrIcons();
} // if(icons
}
} // OutputLowr()
/* -------------------------------------------------------------------------- */
PROCX BYTE ChkLowrChkSum(BYTE * s, INT l)
{
BYTE sum=0;
INT i;
for(i=0;i<l;i++) {
sum+=s[i];
// if(l==8) printf("%2d %02x %02x\n",i, sum, s[i]);
}
return sum;
} // ChkLowrChkSum();
/* -------------------------------------------------------------------------- */
PROCX void LowrParse()
{
INT hdr;
if((Hdr.hdrs.command & 0x80) == 0) { // Not a response, print msg
fprintf(stderr,"Warning: Header command:%04x is not a response command\n",Hdr.hdrs.command);
}
//
// Clear response bit. All from here on should be a response
//
hdr = Hdr.hdrs.command&=0xff7f;
switch(hdr) {
case 0x0008: // ReadMem -- Read from a memory location
LowrMemBytesRead=Hdr.hdrs.length; // don't copy checksum
DoLowrMemRead();
break;
case 0x0009: // WriteMem -- Write to a memory location
//fprintf(stderr,"LowrParse of %04x not written yet\n",Hdr.hdrs.command);
break;
case 0x000D: // Login -- Wake up external serial port
LowrLogin=SerialMessage[0];
break;
case 0x010A: // BaudChange -- Change NMEA Baud Rate
fprintf(stderr,"LowrParse of %04x not written yet\n",Hdr.hdrs.command); break;
case 0x0301: // GetScreenPointer -- Request Screen Pointer to download the current Screen
DoScreenPointer();
break;
case 0x0302: // UnfreezeScreen -- unfreeze the current screen
break;
// (happens after downloading screen)
case 0x0303: // GetWaypoint -- Get a Waypoint
DoLowrWPT();
break;
case 0x0304: // SendWaypoint -- Send a Waypoint response
break;
case 0x0305: // GetRoute -- Get a Route
DoLowrRoute();
break;
case 0x0306: // SendRoute -- Send a Route
break;
case 0x0307: // GetPlotTrail -- Get plot trail Pointer
DoLowrTrackMem();
break;
case 0x0308: // GetNumIcons -- Get number of icons
DoNumIcons();
break;
case 0x0309: // GetIconSymbol -- Get icon symbol
DoLowrIcons();
break;
case 0x030A: // SetNumIcons -- Set number of icons
break;
case 0x030B: // SendIcon -- Send icon
break;
case 0x030C: // GetNumGraphSymbols -- Get number of Graphical symbols
DoNumGraphSymbols();
break;
case 0x030D: // GetIconGraphSymbol -- Get Icon Graphical symbol
fprintf(stderr,"LowrParse of %04x not written yet\n",Hdr.hdrs.command); break;
case 0x030E: // GetProductInfo -- Get product information
DoLowrID();
break;
case 0x0312: // GetPlotTrailOrigin -- Get Plot Trail Origin (Protocol version 2.0)
DoLowrPlotTrailOrigin();
break;
case 0x0313: // GetPlotTrailDeltas -- Get Plot Trail Deltas (Protocol version 2.0)
DoLowrPlotTrailDeltas();
break;
case 0x0314: // SetPlotTrailOrigin -- Set Plot Trail Origin (Protocol version 2.0)
break; // just used as an ACK
case 0x0315: // SetPlotTrailDeltas -- Set Plot Trail Deltas (Protocol version 2.0)
break; // just used as an ACK
} // switch(Hdr.hdrs.command)
} // LowrParse()
#if DEBUGREAD
FILE *qq;
INT fileopen=0;
PROCX void GetLowrMessage(INT exit_on_error)
{
char bun[777];
char *p;
BYTE qqq;
INT done,j,c,i;
if(fileopen==0) {
qq=fopen(debugin_name,"r");
if(qq==NULL) {
fprintf(stderr,"Can't open debug input file: %s\n",debugin_name);
byebye(0);
}
}
fileopen=1;
memset(SerialMessage,0,MAX_LENGTH);
done=0;
//
// Read until next "Received" line--looking for 'good' header
//
while(done==0) {
if(fgets(bun,777,qq)==NULL) {
fprintf(stderr,"EOF in file %s\n",debugin_name);
byebye(0);
}
if(instr(bun,"and skipped")) continue;
if(instr(bun,"Received")) done=1;
}
done=0;
//
// Read until we have a valid header data line
//
while(done==0) {
if(fgets(bun,777,qq)==NULL) {
fprintf(stderr,"EOF in file %s\n",debugin_name);
byebye(0);
}
if(bun[1] != '5') continue; // first non space character in a received
// header data line is always '5'
done=1;
}
//
// We now have first line of code. read and process line until line is completed
//
null_newline(bun);
trim(bun);
strupr(bun);
p=strtok(bun," ");
if(strlen(p)>2) p[2]=0;
Hdr.Header[0]=htoi(p);
for(i=1;i<8;i++) {
p=strtok(NULL," ");
if(p==NULL) break;
if(p[0]==0) break;
if(strlen(p)>2) p[2]=0;
Hdr.Header[i]=htoi(p);
}
if(Hdr.hdrs.length==0) goto linedone;
//
// finished reading header, now read any data
//
// Read until next "Received" line
//
done=0;
while(done==0) {
if(fgets(bun,777,qq)==NULL) {
fprintf(stderr,"EOF in file %s\n",debugin_name);
byebye(0);
}
if(instr(bun,"and skipped")) continue;
if(instr(bun,"Received")) done=1;
}
done=0;
j=0;
processnext:;
if(fgets(bun,777,qq)==NULL) {
fclose(qq);
j=0;
fileopen=0;
goto linedone;
}
if(instr(bun,"Sending")) goto linedone;
if(strlen(bun) == 0) goto processnext;
if(bun[0] != ' ') goto processnext;
//
// Read bytes into SerialMessage
//
null_newline(bun);
trim(bun);
strupr(bun);
p=strtok(bun," ");
if(strlen(p)>2) p[2]=0;
SerialMessage[j]=htoi(p);
j++;
while(1) {
p=strtok(NULL," ");
if(p==NULL) break;
if(p[0]==0) break;
if(strlen(p)>2) p[2]=0;
SerialMessage[j]=htoi(p);
j++;
}
goto processnext;
linedone:;
if(Gdebug==1) {
fprintf(Gdebug_out,"\nfake Received:\n");
c=0;
for(i=0;i<j;i++) {
fprintf(Gdebug_out,outfmt,qqq=*(SerialMessage+i));
if(qqq>=32 && qqq<=126) fprintf(Gdebug_out,"%c ",qqq);
else fprintf(Gdebug_out," ");
if(++c>15) {
fprintf(Gdebug_out,"\n");
c=0;
}
}
if(c)fprintf(Gdebug_out,"\n");
fflush(Gdebug_out);
}
// if(exit_on_error)return; // len=SerialMsgLen=j;
len=SerialMsgLen=j;
LowrParse();
} // GetLowrMessage(INT exit_on_error)
#else
/* -------------------------------------------------------------------------- */
/*
* GetLowrMessage(1) reads and decodes the header 'Hdr.Header[]' then reads the data into the
* message buffer 'SerialMessage' and calls LowrParse.
*
* The string SerialMessage contains the entire data string returned
* from the GPS
*/
PROCX void GetLowrMessage(INT exit_on_error)
{
INT i, fails;
time_t t;
BYTE c;
Lowr_NAKS_Sent=0;
redoit:
memset(SerialMessage,0,MAX_LENGTH);
memset(Hdr.Header,0,8);
SerialMsgLen = 0;
t = time(NULL);
COMtimeout=fails=0;
for (;;) {
if ((time(NULL)-t) >= TIMEOUT/timeoutp) {
if(++fails>=3/timeoutp) {
COMtimeout=1;
if(exit_on_error==1) byebye(5);
return;
}
t=time(NULL);
//
// Re-send last message
//
SendLowrMessage(LastCommand, LastLowrGPSMsg, LastLowrLen,"Re-send");
}
COMtimeout=0;
while (AsyncInStat()) {
fails=0;
c=AsyncIn();
t = time(NULL); /* reset time */
if(c!=0x81 || Hdr.Header[0]!=0x55) {
Hdr.Header[0]=c;
continue; // Hdr.Header Preamble is 0x8155 in Little Endian format
}
Hdr.Header[1]=c;
//
// we have a header preamble, now read 6 more bytes. In this first pass of the code
// there is a real chance of a 'hang' because no error checking is performed. That
// will be added later when I know more about how the Lowrance GPS's behave.
//
for(i=2;i<8;i++) {
while(!AsyncInStat()); // look out! a hang is possible
Hdr.Header[i]=AsyncIn();
}
if((i=ChkLowrChkSum(Hdr.Header,8))!=0) {
fprintf(stderr,"Bad Lowrance Header: sum:%d\n ",i);
for(i=0;i<8;i++) fprintf(stderr,"%02x ",Hdr.Header[i]);
fprintf(stderr,"\n");
}
if(LastCommand==Hdr.hdrs.command) {
if(Gdebug == 1) {
fprintf(Gdebug_out,"Received (and skipped): Header\n");
debugOUT(Hdr.Header,8);
}
goto redoit; // an echo of our command?
}
if(Gdebug==1) {
fprintf(Gdebug_out,"Received: Header\n");
debugOUT(Hdr.Header,8);
}
//
// we now have a valid header. What is the command? How do we read and decode it:
//
if(Hdr.hdrs.length) { // non-zero length data
for(i=0;i<=Hdr.hdrs.length;i++) {
while(!AsyncInStat()); // look out! a hang is possible
SerialMessage[i]=AsyncIn();
}
}
if(Gdebug==1 && Hdr.hdrs.length) {
fprintf(Gdebug_out,"Received:\n");
debugOUT(SerialMessage,(INT)(Hdr.hdrs.length+1));
}
//
// decode by Hdr (Header)...
//
LowrParse();
return;
} // while
} // for (;;)
} /* GetLowrMessage(INT exit_on_error) */
#endif
/* -------------------------------------------------------------------------- */
// rounds to dig places using sprintf
PROCX double round(double n, int dig)
{
char buf[50], buf1[50];
sprintf(buf,"%%.%dlf",dig);
sprintf(buf1,buf,n);
return atof(buf1);
} // round
/* -------------------------------------------------------------------------- */
//Convert Latitude in degrees to Mercator meters
PROCX long LatDegtoMM(double d)
{
double temp;
temp=((d*DEGtoRAD) + PIdiv2)/2.0;
temp=tan(temp);
temp=log(temp); // natural log?
temp=temp * EarthRad;
return (long)temp;
} // LatDegtoMM
/* -------------------------------------------------------------------------- */
// Convert Mercator meters to Latitude Degrees
PROCX double LatMMtoDeg(long m)
{
double temp;
temp=(double)m / (double) EarthRad;
temp=exp(temp);
temp=(2.0 * atan(temp)) - (double)PIdiv2;
return (temp * (double)RADtoDEG);
} // LatMMtoDeg
/* -------------------------------------------------------------------------- */
// Convert Longitude in degrees to Mercator Meters
PROCX long LongDegtoMM(double d)
{
return (long)(d * EarthRad * DEGtoRAD);
} // LongDegtoMM
/* -------------------------------------------------------------------------- */
//Convert Mercator Meters to Longitude degrees
PROCX double LongMMtoDeg(long m)
{
double t;
t = (double)m / (double) 6356752.3142;
t = t * RADtoDEG;
return t;
} // LongMMtoDeg
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -