time-nuts@lists.febo.com

Discussion of precise time and frequency measurement

View all threads

TruePosition and Arduino Progress

BH
Ben Hall
Sun, May 21, 2017 1:45 PM

Good morning all,

A quick update for those interested on my Arduino code development for
the TruePosition boards.  I've got Arduino code together than can read
in the serial stream, parse it, and display time, date, number of
satellites, and TFOM on a 2x16 LCD display.  It does not do multiple
screens, handle survey, or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to
use the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there
is a clock message, an extstatus message, and a status message, it seems
like it is still parsing when the 1PPS tick comes in...so it will
display seconds as follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock on
one computer, but seems a half second slow per GPSCon's time display on
the Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to
figure out how much time elapses between the clock, extstatus, status,
and 1PPS tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't
make that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb

Good morning all, A quick update for those interested on my Arduino code development for the TruePosition boards. I've got Arduino code together than can read in the serial stream, parse it, and display time, date, number of satellites, and TFOM on a 2x16 LCD display. It does not do multiple screens, handle survey, or display lat/long yet. What I'm having issues with is handling the 1 PPS. Ideally, I want to use the 1PPS signal to trigger the display update. IE: void loop() { getSerialString() // uses serial.available to pull in the serial data parser() // this parses the data wait for 1PPS tick to go high if there has been a clock message, updateDispay() // update the display } This works great when there is a just a clock message. But when there is a clock message, an extstatus message, and a status message, it seems like it is still parsing when the 1PPS tick comes in...so it will display seconds as follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... (If I don't wait for the 1PPS tick, it seems that my clock is one second fast. I say "seems" to be fast, as the time agrees with an NTP clock on one computer, but seems a half second slow per GPSCon's time display on the Z3801. I think I need to put up the antenna and check against WWV.) I've got one of those cheap little USB logic analyzers on order to figure out how much time elapses between the clock, extstatus, status, and 1PPS tick. I may need something faster than an Arduino Uno to do this. I'm sure there is a way to do this with an interrupt...but I couldn't make that work yesterday. More to follow. thanks much and 73, ben, kd5byb
CA
Chris Albertson
Sun, May 21, 2017 6:20 PM

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for the
TruePosition boards.  I've got Arduino code together than can read in the
serial stream, parse it, and display time, date, number of satellites, and
TFOM on a 2x16 LCD display.  It does not do multiple screens, handle survey,
or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to use
the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there is a
clock message, an extstatus message, and a status message, it seems like it
is still parsing when the 1PPS tick comes in...so it will display seconds as
follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock on one
computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to figure
out how much time elapses between the clock, extstatus, status, and 1PPS
tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't make
that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

The problem is that you get the ENTIRE string then parse it. This is not going to work well as you found out. Your CPU spends almost the entire time waiting for characters to come in slowly off the serial line. You are just waiting on bits and wasting CPU cycles What you need to do is parse one character at a time. I bet your parser reads one character at a time from the string. Have it read one character at a time directly from the serial port. (Use a state machine. It will work for such a simple job as this) Yes if your CPU was MUCH faster your plan could work. But on some GPSes the data never has a break. You are trying to do ALL the work in the break but actually most of the down time when you should be working is between the characters. There is not a lot of work a finite state machine needs to do between characters, just move state based on a 'character class" table. I you ever studied this formally, what you are building here is a "lexer" not a parcer. The "Language" is not recursive and you never need to backtrack so it can be de-coded literally one character at a time. You DO really want the 1PPS to drive an interrupt. Thisway you just continue working on the data stream and don't wait for the PPS. When the PPS happens you do something QUICK. never do anything time consuming in the ISR or you will miss the next serial character. increment a seconds count and write two bytes the the LCD and exit On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: > Good morning all, > > A quick update for those interested on my Arduino code development for the > TruePosition boards. I've got Arduino code together than can read in the > serial stream, parse it, and display time, date, number of satellites, and > TFOM on a 2x16 LCD display. It does not do multiple screens, handle survey, > or display lat/long yet. > > What I'm having issues with is handling the 1 PPS. Ideally, I want to use > the 1PPS signal to trigger the display update. IE: > > void loop() > { > getSerialString() // uses serial.available to pull in the serial data > > parser() // this parses the data > > wait for 1PPS tick to go high > > if there has been a clock message, updateDispay() // update the display > } > > This works great when there is a just a clock message. But when there is a > clock message, an extstatus message, and a status message, it seems like it > is still parsing when the 1PPS tick comes in...so it will display seconds as > follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... > > (If I don't wait for the 1PPS tick, it seems that my clock is one second > fast. I say "seems" to be fast, as the time agrees with an NTP clock on one > computer, but seems a half second slow per GPSCon's time display on the > Z3801. I think I need to put up the antenna and check against WWV.) > > I've got one of those cheap little USB logic analyzers on order to figure > out how much time elapses between the clock, extstatus, status, and 1PPS > tick. I may need something faster than an Arduino Uno to do this. > > I'm sure there is a way to do this with an interrupt...but I couldn't make > that work yesterday. More to follow. > > thanks much and 73, > ben, kd5byb > _______________________________________________ > time-nuts mailing list -- time-nuts@febo.com > To unsubscribe, go to > https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts > and follow the instructions there. -- Chris Albertson Redondo Beach, California
CA
Chris Albertson
Sun, May 21, 2017 6:32 PM

To add to my last message.

You CAN collect all the data then parse it like you are doing if you
were to move to an interrupt driven serial port reader.  Each
character is then read by the interrupt handler anyplace in a large
circular buffer.  The parcer then reads out of the other and of this
buffer.

The phlegm with the current code is the parse ingnores serial input
and will drop data, in also ignore the PPS and will as you found drop
pulses.

Typically in real time processors like your that must be interrupt
driven or they must poll MANY times laster then the data arrives

so as I wrote before, parsing the data stream one character at a tie
is in effect pooling the serial port much faster then characters
arrive.    Adding a ring buffer and interrupts guarantees yo never
miss a character and certainly you need to interrupt in the PPS to
handle the case there three s serial data and the PPS at the same
time.

The ring buffer is like you big string except you data data onto one
end at the same time as soured data off the other.  Hopefully the ring
buffer never has much data in it as the parser should be fathers then
the serial line.  BUT if a PPS happens then the parser in interrupted
while the display updates so th ring buffer might get filled up a
little.  But the ISR terminals the parser clears the buffer.

On Sun, May 21, 2017 at 11:20 AM, Chris Albertson
albertson.chris@gmail.com wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for the
TruePosition boards.  I've got Arduino code together than can read in the
serial stream, parse it, and display time, date, number of satellites, and
TFOM on a 2x16 LCD display.  It does not do multiple screens, handle survey,
or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to use
the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there is a
clock message, an extstatus message, and a status message, it seems like it
is still parsing when the 1PPS tick comes in...so it will display seconds as
follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock on one
computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to figure
out how much time elapses between the clock, extstatus, status, and 1PPS
tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't make
that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

--

Chris Albertson
Redondo Beach, California

To add to my last message. You CAN collect all the data then parse it like you are doing if you were to move to an interrupt driven serial port reader. Each character is then read by the interrupt handler anyplace in a large circular buffer. The parcer then reads out of the other and of this buffer. The phlegm with the current code is the parse ingnores serial input and will drop data, in also ignore the PPS and will as you found drop pulses. Typically in real time processors like your that must be interrupt driven or they must poll MANY times laster then the data arrives so as I wrote before, parsing the data stream one character at a tie is in effect pooling the serial port much faster then characters arrive. Adding a ring buffer and interrupts guarantees yo never miss a character and certainly you need to interrupt in the PPS to handle the case there three s serial data and the PPS at the same time. The ring buffer is like you big string except you data data onto one end at the same time as soured data off the other. Hopefully the ring buffer never has much data in it as the parser should be fathers then the serial line. BUT if a PPS happens then the parser in interrupted while the display updates so th ring buffer might get filled up a little. But the ISR terminals the parser clears the buffer. On Sun, May 21, 2017 at 11:20 AM, Chris Albertson <albertson.chris@gmail.com> wrote: > The problem is that you get the ENTIRE string then parse it. This is > not going to work well as you found out. Your CPU spends almost the > entire time waiting for characters to come in slowly off the serial > line. You are just waiting on bits and wasting CPU cycles > > What you need to do is parse one character at a time. I bet your > parser reads one character at a time from the string. Have it read > one character at a time directly from the serial port. (Use a state > machine. It will work for such a simple job as this) > > Yes if your CPU was MUCH faster your plan could work. But on some > GPSes the data never has a break. You are trying to do ALL the work > in the break but actually most of the down time when you should be > working is between the characters. There is not a lot of work a > finite state machine needs to do between characters, just move state > based on a 'character class" table. I you ever studied this > formally, what you are building here is a "lexer" not a parcer. The > "Language" is not recursive and you never need to backtrack so it can > be de-coded literally one character at a time. > > You DO really want the 1PPS to drive an interrupt. Thisway you just > continue working on the data stream and don't wait for the PPS. When > the PPS happens you do something QUICK. never do anything time > consuming in the ISR or you will miss the next serial character. > increment a seconds count and write two bytes the the LCD and exit > > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: >> Good morning all, >> >> A quick update for those interested on my Arduino code development for the >> TruePosition boards. I've got Arduino code together than can read in the >> serial stream, parse it, and display time, date, number of satellites, and >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle survey, >> or display lat/long yet. >> >> What I'm having issues with is handling the 1 PPS. Ideally, I want to use >> the 1PPS signal to trigger the display update. IE: >> >> void loop() >> { >> getSerialString() // uses serial.available to pull in the serial data >> >> parser() // this parses the data >> >> wait for 1PPS tick to go high >> >> if there has been a clock message, updateDispay() // update the display >> } >> >> This works great when there is a just a clock message. But when there is a >> clock message, an extstatus message, and a status message, it seems like it >> is still parsing when the 1PPS tick comes in...so it will display seconds as >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... >> >> (If I don't wait for the 1PPS tick, it seems that my clock is one second >> fast. I say "seems" to be fast, as the time agrees with an NTP clock on one >> computer, but seems a half second slow per GPSCon's time display on the >> Z3801. I think I need to put up the antenna and check against WWV.) >> >> I've got one of those cheap little USB logic analyzers on order to figure >> out how much time elapses between the clock, extstatus, status, and 1PPS >> tick. I may need something faster than an Arduino Uno to do this. >> >> I'm sure there is a way to do this with an interrupt...but I couldn't make >> that work yesterday. More to follow. >> >> thanks much and 73, >> ben, kd5byb >> _______________________________________________ >> time-nuts mailing list -- time-nuts@febo.com >> To unsubscribe, go to >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts >> and follow the instructions there. > > > > -- > > Chris Albertson > Redondo Beach, California -- Chris Albertson Redondo Beach, California
JH
Jim Harman
Sun, May 21, 2017 6:56 PM

Another way to do is to use the 1 PPS to trigger an interrupt on the
Arduino. Look at the documentation for attachInterrupt(). In the interrupt
routine, have it set a flag. The flag variable should be declared up front
as volatile.

Then in your main loop, do all your parsing then loop waiting for the flag
to be set. When set, update the clock then clear the flag and repeat.

On Sun, May 21, 2017 at 2:32 PM, Chris Albertson albertson.chris@gmail.com
wrote:

To add to my last message.

You CAN collect all the data then parse it like you are doing if you
were to move to an interrupt driven serial port reader.  Each
character is then read by the interrupt handler anyplace in a large
circular buffer.  The parcer then reads out of the other and of this
buffer.

The phlegm with the current code is the parse ingnores serial input
and will drop data, in also ignore the PPS and will as you found drop
pulses.

Typically in real time processors like your that must be interrupt
driven or they must poll MANY times laster then the data arrives

so as I wrote before, parsing the data stream one character at a tie
is in effect pooling the serial port much faster then characters
arrive.    Adding a ring buffer and interrupts guarantees yo never
miss a character and certainly you need to interrupt in the PPS to
handle the case there three s serial data and the PPS at the same
time.

The ring buffer is like you big string except you data data onto one
end at the same time as soured data off the other.  Hopefully the ring
buffer never has much data in it as the parser should be fathers then
the serial line.  BUT if a PPS happens then the parser in interrupted
while the display updates so th ring buffer might get filled up a
little.  But the ISR terminals the parser clears the buffer.

On Sun, May 21, 2017 at 11:20 AM, Chris Albertson
albertson.chris@gmail.com wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for

the

TruePosition boards.  I've got Arduino code together than can read in

the

serial stream, parse it, and display time, date, number of satellites,

and

TFOM on a 2x16 LCD display.  It does not do multiple screens, handle

survey,

or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to

use

the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there

is a

clock message, an extstatus message, and a status message, it seems

like it

is still parsing when the 1PPS tick comes in...so it will display

seconds as

follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock

on one

computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to

figure

out how much time elapses between the clock, extstatus, status, and 1PPS
tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't

make

that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

--

Chris Albertson
Redondo Beach, California


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/
mailman/listinfo/time-nuts
and follow the instructions there.

--

--Jim Harman

Another way to do is to use the 1 PPS to trigger an interrupt on the Arduino. Look at the documentation for attachInterrupt(). In the interrupt routine, have it set a flag. The flag variable should be declared up front as volatile. Then in your main loop, do all your parsing then loop waiting for the flag to be set. When set, update the clock then clear the flag and repeat. On Sun, May 21, 2017 at 2:32 PM, Chris Albertson <albertson.chris@gmail.com> wrote: > To add to my last message. > > You CAN collect all the data then parse it like you are doing if you > were to move to an interrupt driven serial port reader. Each > character is then read by the interrupt handler anyplace in a large > circular buffer. The parcer then reads out of the other and of this > buffer. > > The phlegm with the current code is the parse ingnores serial input > and will drop data, in also ignore the PPS and will as you found drop > pulses. > > Typically in real time processors like your that must be interrupt > driven or they must poll MANY times laster then the data arrives > > so as I wrote before, parsing the data stream one character at a tie > is in effect pooling the serial port much faster then characters > arrive. Adding a ring buffer and interrupts guarantees yo never > miss a character and certainly you need to interrupt in the PPS to > handle the case there three s serial data and the PPS at the same > time. > > The ring buffer is like you big string except you data data onto one > end at the same time as soured data off the other. Hopefully the ring > buffer never has much data in it as the parser should be fathers then > the serial line. BUT if a PPS happens then the parser in interrupted > while the display updates so th ring buffer might get filled up a > little. But the ISR terminals the parser clears the buffer. > > On Sun, May 21, 2017 at 11:20 AM, Chris Albertson > <albertson.chris@gmail.com> wrote: > > The problem is that you get the ENTIRE string then parse it. This is > > not going to work well as you found out. Your CPU spends almost the > > entire time waiting for characters to come in slowly off the serial > > line. You are just waiting on bits and wasting CPU cycles > > > > What you need to do is parse one character at a time. I bet your > > parser reads one character at a time from the string. Have it read > > one character at a time directly from the serial port. (Use a state > > machine. It will work for such a simple job as this) > > > > Yes if your CPU was MUCH faster your plan could work. But on some > > GPSes the data never has a break. You are trying to do ALL the work > > in the break but actually most of the down time when you should be > > working is between the characters. There is not a lot of work a > > finite state machine needs to do between characters, just move state > > based on a 'character class" table. I you ever studied this > > formally, what you are building here is a "lexer" not a parcer. The > > "Language" is not recursive and you never need to backtrack so it can > > be de-coded literally one character at a time. > > > > You DO really want the 1PPS to drive an interrupt. Thisway you just > > continue working on the data stream and don't wait for the PPS. When > > the PPS happens you do something QUICK. never do anything time > > consuming in the ISR or you will miss the next serial character. > > increment a seconds count and write two bytes the the LCD and exit > > > > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: > >> Good morning all, > >> > >> A quick update for those interested on my Arduino code development for > the > >> TruePosition boards. I've got Arduino code together than can read in > the > >> serial stream, parse it, and display time, date, number of satellites, > and > >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle > survey, > >> or display lat/long yet. > >> > >> What I'm having issues with is handling the 1 PPS. Ideally, I want to > use > >> the 1PPS signal to trigger the display update. IE: > >> > >> void loop() > >> { > >> getSerialString() // uses serial.available to pull in the serial data > >> > >> parser() // this parses the data > >> > >> wait for 1PPS tick to go high > >> > >> if there has been a clock message, updateDispay() // update the display > >> } > >> > >> This works great when there is a just a clock message. But when there > is a > >> clock message, an extstatus message, and a status message, it seems > like it > >> is still parsing when the 1PPS tick comes in...so it will display > seconds as > >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... > >> > >> (If I don't wait for the 1PPS tick, it seems that my clock is one second > >> fast. I say "seems" to be fast, as the time agrees with an NTP clock > on one > >> computer, but seems a half second slow per GPSCon's time display on the > >> Z3801. I think I need to put up the antenna and check against WWV.) > >> > >> I've got one of those cheap little USB logic analyzers on order to > figure > >> out how much time elapses between the clock, extstatus, status, and 1PPS > >> tick. I may need something faster than an Arduino Uno to do this. > >> > >> I'm sure there is a way to do this with an interrupt...but I couldn't > make > >> that work yesterday. More to follow. > >> > >> thanks much and 73, > >> ben, kd5byb > >> _______________________________________________ > >> time-nuts mailing list -- time-nuts@febo.com > >> To unsubscribe, go to > >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts > >> and follow the instructions there. > > > > > > > > -- > > > > Chris Albertson > > Redondo Beach, California > > > > -- > > Chris Albertson > Redondo Beach, California > _______________________________________________ > time-nuts mailing list -- time-nuts@febo.com > To unsubscribe, go to https://www.febo.com/cgi-bin/ > mailman/listinfo/time-nuts > and follow the instructions there. > -- --Jim Harman
JH
Jim Harman
Sun, May 21, 2017 7:24 PM

Sorry, I may have over-simplified. You sketch might look something like
this, assuming the PPS is connected to pin D2 and the rising edge makes the
second:

volatile boolean PPS_ReadFlag = false;

void setup () {
...

attachInterrupt(digitalPinToInterrupt(2), serviceRoutine, RISING);

...
}

void serviceRoutine() {
PPS_ReadFlag = true;
}

void loop () {
while (!PPS_ReadFlag) {
while(Serial.available()) {
--parse the next character and set a flag if the time is valid--
}
}

if(timeValid) {
-- update display or whatever --
PPS_ReadFlag = false;
}
}

On Sun, May 21, 2017 at 2:56 PM, Jim Harman j99harman@gmail.com wrote:

Another way to do is to use the 1 PPS to trigger an interrupt on the
Arduino. Look at the documentation for attachInterrupt(). In the interrupt
routine, have it set a flag. The flag variable should be declared up front
as volatile.

Then in your main loop, do all your parsing then loop waiting for the flag
to be set. When set, update the clock then clear the flag and repeat.

On Sun, May 21, 2017 at 2:32 PM, Chris Albertson <
albertson.chris@gmail.com> wrote:

To add to my last message.

You CAN collect all the data then parse it like you are doing if you
were to move to an interrupt driven serial port reader.  Each
character is then read by the interrupt handler anyplace in a large
circular buffer.  The parcer then reads out of the other and of this
buffer.

The phlegm with the current code is the parse ingnores serial input
and will drop data, in also ignore the PPS and will as you found drop
pulses.

Typically in real time processors like your that must be interrupt
driven or they must poll MANY times laster then the data arrives

so as I wrote before, parsing the data stream one character at a tie
is in effect pooling the serial port much faster then characters
arrive.    Adding a ring buffer and interrupts guarantees yo never
miss a character and certainly you need to interrupt in the PPS to
handle the case there three s serial data and the PPS at the same
time.

The ring buffer is like you big string except you data data onto one
end at the same time as soured data off the other.  Hopefully the ring
buffer never has much data in it as the parser should be fathers then
the serial line.  BUT if a PPS happens then the parser in interrupted
while the display updates so th ring buffer might get filled up a
little.  But the ISR terminals the parser clears the buffer.

On Sun, May 21, 2017 at 11:20 AM, Chris Albertson
albertson.chris@gmail.com wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for

the

TruePosition boards.  I've got Arduino code together than can read in

the

serial stream, parse it, and display time, date, number of satellites,

and

TFOM on a 2x16 LCD display.  It does not do multiple screens, handle

survey,

or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to

use

the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the

display

}

This works great when there is a just a clock message.  But when there

is a

clock message, an extstatus message, and a status message, it seems

like it

is still parsing when the 1PPS tick comes in...so it will display

seconds as

follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one

second

fast.  I say "seems" to be fast, as the time agrees with an NTP clock

on one

computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to

figure

out how much time elapses between the clock, extstatus, status, and

1PPS

tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't

make

that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

--

Chris Albertson
Redondo Beach, California


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/m
ailman/listinfo/time-nuts
and follow the instructions there.

--

--Jim Harman

--

--Jim Harman

Sorry, I may have over-simplified. You sketch might look something like this, assuming the PPS is connected to pin D2 and the rising edge makes the second: volatile boolean PPS_ReadFlag = false; void setup () { ... attachInterrupt(digitalPinToInterrupt(2), serviceRoutine, RISING); ... } void serviceRoutine() { PPS_ReadFlag = true; } void loop () { while (!PPS_ReadFlag) { while(Serial.available()) { --parse the next character and set a flag if the time is valid-- } } if(timeValid) { -- update display or whatever -- PPS_ReadFlag = false; } } On Sun, May 21, 2017 at 2:56 PM, Jim Harman <j99harman@gmail.com> wrote: > Another way to do is to use the 1 PPS to trigger an interrupt on the > Arduino. Look at the documentation for attachInterrupt(). In the interrupt > routine, have it set a flag. The flag variable should be declared up front > as volatile. > > Then in your main loop, do all your parsing then loop waiting for the flag > to be set. When set, update the clock then clear the flag and repeat. > > > > On Sun, May 21, 2017 at 2:32 PM, Chris Albertson < > albertson.chris@gmail.com> wrote: > >> To add to my last message. >> >> You CAN collect all the data then parse it like you are doing if you >> were to move to an interrupt driven serial port reader. Each >> character is then read by the interrupt handler anyplace in a large >> circular buffer. The parcer then reads out of the other and of this >> buffer. >> >> The phlegm with the current code is the parse ingnores serial input >> and will drop data, in also ignore the PPS and will as you found drop >> pulses. >> >> Typically in real time processors like your that must be interrupt >> driven or they must poll MANY times laster then the data arrives >> >> so as I wrote before, parsing the data stream one character at a tie >> is in effect pooling the serial port much faster then characters >> arrive. Adding a ring buffer and interrupts guarantees yo never >> miss a character and certainly you need to interrupt in the PPS to >> handle the case there three s serial data and the PPS at the same >> time. >> >> The ring buffer is like you big string except you data data onto one >> end at the same time as soured data off the other. Hopefully the ring >> buffer never has much data in it as the parser should be fathers then >> the serial line. BUT if a PPS happens then the parser in interrupted >> while the display updates so th ring buffer might get filled up a >> little. But the ISR terminals the parser clears the buffer. >> >> On Sun, May 21, 2017 at 11:20 AM, Chris Albertson >> <albertson.chris@gmail.com> wrote: >> > The problem is that you get the ENTIRE string then parse it. This is >> > not going to work well as you found out. Your CPU spends almost the >> > entire time waiting for characters to come in slowly off the serial >> > line. You are just waiting on bits and wasting CPU cycles >> > >> > What you need to do is parse one character at a time. I bet your >> > parser reads one character at a time from the string. Have it read >> > one character at a time directly from the serial port. (Use a state >> > machine. It will work for such a simple job as this) >> > >> > Yes if your CPU was MUCH faster your plan could work. But on some >> > GPSes the data never has a break. You are trying to do ALL the work >> > in the break but actually most of the down time when you should be >> > working is between the characters. There is not a lot of work a >> > finite state machine needs to do between characters, just move state >> > based on a 'character class" table. I you ever studied this >> > formally, what you are building here is a "lexer" not a parcer. The >> > "Language" is not recursive and you never need to backtrack so it can >> > be de-coded literally one character at a time. >> > >> > You DO really want the 1PPS to drive an interrupt. Thisway you just >> > continue working on the data stream and don't wait for the PPS. When >> > the PPS happens you do something QUICK. never do anything time >> > consuming in the ISR or you will miss the next serial character. >> > increment a seconds count and write two bytes the the LCD and exit >> > >> > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: >> >> Good morning all, >> >> >> >> A quick update for those interested on my Arduino code development for >> the >> >> TruePosition boards. I've got Arduino code together than can read in >> the >> >> serial stream, parse it, and display time, date, number of satellites, >> and >> >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle >> survey, >> >> or display lat/long yet. >> >> >> >> What I'm having issues with is handling the 1 PPS. Ideally, I want to >> use >> >> the 1PPS signal to trigger the display update. IE: >> >> >> >> void loop() >> >> { >> >> getSerialString() // uses serial.available to pull in the serial data >> >> >> >> parser() // this parses the data >> >> >> >> wait for 1PPS tick to go high >> >> >> >> if there has been a clock message, updateDispay() // update the >> display >> >> } >> >> >> >> This works great when there is a just a clock message. But when there >> is a >> >> clock message, an extstatus message, and a status message, it seems >> like it >> >> is still parsing when the 1PPS tick comes in...so it will display >> seconds as >> >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... >> >> >> >> (If I don't wait for the 1PPS tick, it seems that my clock is one >> second >> >> fast. I say "seems" to be fast, as the time agrees with an NTP clock >> on one >> >> computer, but seems a half second slow per GPSCon's time display on the >> >> Z3801. I think I need to put up the antenna and check against WWV.) >> >> >> >> I've got one of those cheap little USB logic analyzers on order to >> figure >> >> out how much time elapses between the clock, extstatus, status, and >> 1PPS >> >> tick. I may need something faster than an Arduino Uno to do this. >> >> >> >> I'm sure there is a way to do this with an interrupt...but I couldn't >> make >> >> that work yesterday. More to follow. >> >> >> >> thanks much and 73, >> >> ben, kd5byb >> >> _______________________________________________ >> >> time-nuts mailing list -- time-nuts@febo.com >> >> To unsubscribe, go to >> >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts >> >> and follow the instructions there. >> > >> > >> > >> > -- >> > >> > Chris Albertson >> > Redondo Beach, California >> >> >> >> -- >> >> Chris Albertson >> Redondo Beach, California >> _______________________________________________ >> time-nuts mailing list -- time-nuts@febo.com >> To unsubscribe, go to https://www.febo.com/cgi-bin/m >> ailman/listinfo/time-nuts >> and follow the instructions there. >> > > > > -- > > --Jim Harman > > -- --Jim Harman
CA
Chris Albertson
Sun, May 21, 2017 9:48 PM

The root of the problem is that he is doing all the parking at once
and ignoring inputs from both the serial line and the 1PPS

Even if the iPPS were connected to an interrupt (and it should be) he
is still busy parking input when the ISR sets the flag.

He needs to read the data fro the serial line one character at a time
and not wait to start parsing.

Either that or he needs to insert calls to some kind of CHECKINPUTS()
every few lines in the parser and that just look ugly.

On Sun, May 21, 2017 at 11:56 AM, Jim Harman j99harman@gmail.com wrote:

Another way to do is to use the 1 PPS to trigger an interrupt on the
Arduino. Look at the documentation for attachInterrupt(). In the interrupt
routine, have it set a flag. The flag variable should be declared up front
as volatile.

Then in your main loop, do all your parsing then loop waiting for the flag
to be set. When set, update the clock then clear the flag and repeat.

On Sun, May 21, 2017 at 2:32 PM, Chris Albertson albertson.chris@gmail.com
wrote:

To add to my last message.

You CAN collect all the data then parse it like you are doing if you
were to move to an interrupt driven serial port reader.  Each
character is then read by the interrupt handler anyplace in a large
circular buffer.  The parcer then reads out of the other and of this
buffer.

The phlegm with the current code is the parse ingnores serial input
and will drop data, in also ignore the PPS and will as you found drop
pulses.

Typically in real time processors like your that must be interrupt
driven or they must poll MANY times laster then the data arrives

so as I wrote before, parsing the data stream one character at a tie
is in effect pooling the serial port much faster then characters
arrive.    Adding a ring buffer and interrupts guarantees yo never
miss a character and certainly you need to interrupt in the PPS to
handle the case there three s serial data and the PPS at the same
time.

The ring buffer is like you big string except you data data onto one
end at the same time as soured data off the other.  Hopefully the ring
buffer never has much data in it as the parser should be fathers then
the serial line.  BUT if a PPS happens then the parser in interrupted
while the display updates so th ring buffer might get filled up a
little.  But the ISR terminals the parser clears the buffer.

On Sun, May 21, 2017 at 11:20 AM, Chris Albertson
albertson.chris@gmail.com wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for

the

TruePosition boards.  I've got Arduino code together than can read in

the

serial stream, parse it, and display time, date, number of satellites,

and

TFOM on a 2x16 LCD display.  It does not do multiple screens, handle

survey,

or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to

use

the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there

is a

clock message, an extstatus message, and a status message, it seems

like it

is still parsing when the 1PPS tick comes in...so it will display

seconds as

follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock

on one

computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to

figure

out how much time elapses between the clock, extstatus, status, and 1PPS
tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't

make

that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

--

Chris Albertson
Redondo Beach, California


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/
mailman/listinfo/time-nuts
and follow the instructions there.

--

--Jim Harman


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

The root of the problem is that he is doing all the parking at once and ignoring inputs from both the serial line and the 1PPS Even if the iPPS were connected to an interrupt (and it should be) he is still busy parking input when the ISR sets the flag. He needs to read the data fro the serial line one character at a time and not wait to start parsing. Either that or he needs to insert calls to some kind of CHECKINPUTS() every few lines in the parser and that just look ugly. On Sun, May 21, 2017 at 11:56 AM, Jim Harman <j99harman@gmail.com> wrote: > Another way to do is to use the 1 PPS to trigger an interrupt on the > Arduino. Look at the documentation for attachInterrupt(). In the interrupt > routine, have it set a flag. The flag variable should be declared up front > as volatile. > > Then in your main loop, do all your parsing then loop waiting for the flag > to be set. When set, update the clock then clear the flag and repeat. > > > > On Sun, May 21, 2017 at 2:32 PM, Chris Albertson <albertson.chris@gmail.com> > wrote: > >> To add to my last message. >> >> You CAN collect all the data then parse it like you are doing if you >> were to move to an interrupt driven serial port reader. Each >> character is then read by the interrupt handler anyplace in a large >> circular buffer. The parcer then reads out of the other and of this >> buffer. >> >> The phlegm with the current code is the parse ingnores serial input >> and will drop data, in also ignore the PPS and will as you found drop >> pulses. >> >> Typically in real time processors like your that must be interrupt >> driven or they must poll MANY times laster then the data arrives >> >> so as I wrote before, parsing the data stream one character at a tie >> is in effect pooling the serial port much faster then characters >> arrive. Adding a ring buffer and interrupts guarantees yo never >> miss a character and certainly you need to interrupt in the PPS to >> handle the case there three s serial data and the PPS at the same >> time. >> >> The ring buffer is like you big string except you data data onto one >> end at the same time as soured data off the other. Hopefully the ring >> buffer never has much data in it as the parser should be fathers then >> the serial line. BUT if a PPS happens then the parser in interrupted >> while the display updates so th ring buffer might get filled up a >> little. But the ISR terminals the parser clears the buffer. >> >> On Sun, May 21, 2017 at 11:20 AM, Chris Albertson >> <albertson.chris@gmail.com> wrote: >> > The problem is that you get the ENTIRE string then parse it. This is >> > not going to work well as you found out. Your CPU spends almost the >> > entire time waiting for characters to come in slowly off the serial >> > line. You are just waiting on bits and wasting CPU cycles >> > >> > What you need to do is parse one character at a time. I bet your >> > parser reads one character at a time from the string. Have it read >> > one character at a time directly from the serial port. (Use a state >> > machine. It will work for such a simple job as this) >> > >> > Yes if your CPU was MUCH faster your plan could work. But on some >> > GPSes the data never has a break. You are trying to do ALL the work >> > in the break but actually most of the down time when you should be >> > working is between the characters. There is not a lot of work a >> > finite state machine needs to do between characters, just move state >> > based on a 'character class" table. I you ever studied this >> > formally, what you are building here is a "lexer" not a parcer. The >> > "Language" is not recursive and you never need to backtrack so it can >> > be de-coded literally one character at a time. >> > >> > You DO really want the 1PPS to drive an interrupt. Thisway you just >> > continue working on the data stream and don't wait for the PPS. When >> > the PPS happens you do something QUICK. never do anything time >> > consuming in the ISR or you will miss the next serial character. >> > increment a seconds count and write two bytes the the LCD and exit >> > >> > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: >> >> Good morning all, >> >> >> >> A quick update for those interested on my Arduino code development for >> the >> >> TruePosition boards. I've got Arduino code together than can read in >> the >> >> serial stream, parse it, and display time, date, number of satellites, >> and >> >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle >> survey, >> >> or display lat/long yet. >> >> >> >> What I'm having issues with is handling the 1 PPS. Ideally, I want to >> use >> >> the 1PPS signal to trigger the display update. IE: >> >> >> >> void loop() >> >> { >> >> getSerialString() // uses serial.available to pull in the serial data >> >> >> >> parser() // this parses the data >> >> >> >> wait for 1PPS tick to go high >> >> >> >> if there has been a clock message, updateDispay() // update the display >> >> } >> >> >> >> This works great when there is a just a clock message. But when there >> is a >> >> clock message, an extstatus message, and a status message, it seems >> like it >> >> is still parsing when the 1PPS tick comes in...so it will display >> seconds as >> >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... >> >> >> >> (If I don't wait for the 1PPS tick, it seems that my clock is one second >> >> fast. I say "seems" to be fast, as the time agrees with an NTP clock >> on one >> >> computer, but seems a half second slow per GPSCon's time display on the >> >> Z3801. I think I need to put up the antenna and check against WWV.) >> >> >> >> I've got one of those cheap little USB logic analyzers on order to >> figure >> >> out how much time elapses between the clock, extstatus, status, and 1PPS >> >> tick. I may need something faster than an Arduino Uno to do this. >> >> >> >> I'm sure there is a way to do this with an interrupt...but I couldn't >> make >> >> that work yesterday. More to follow. >> >> >> >> thanks much and 73, >> >> ben, kd5byb >> >> _______________________________________________ >> >> time-nuts mailing list -- time-nuts@febo.com >> >> To unsubscribe, go to >> >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts >> >> and follow the instructions there. >> > >> > >> > >> > -- >> > >> > Chris Albertson >> > Redondo Beach, California >> >> >> >> -- >> >> Chris Albertson >> Redondo Beach, California >> _______________________________________________ >> time-nuts mailing list -- time-nuts@febo.com >> To unsubscribe, go to https://www.febo.com/cgi-bin/ >> mailman/listinfo/time-nuts >> and follow the instructions there. >> > > > > -- > > --Jim Harman > _______________________________________________ > time-nuts mailing list -- time-nuts@febo.com > To unsubscribe, go to https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts > and follow the instructions there. -- Chris Albertson Redondo Beach, California
J
jimlux
Sun, May 21, 2017 11:16 PM

On 5/21/17 11:20 AM, Chris Albertson wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

On many Arduinos these days, the "getSerialString()" is a
buffered/interrupt driven routine under the hood - it's not burning many
cycles.

That said, even if your serial port code was "spin on a bit", you can do
a lot of parsing/processing pretty quickly.  Arduinos aren't 4 MHz Z80s
or 8051s.  The modern crop have 50 MHz clocks and a millisecond is a lot
of instructions.

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.

I think that would be overkill, it's a lot harder to write a state
machine than a simple "is the first N characters $GPPGA?" kind of thing.
You'd want to write a generalized parser first if only to make sure that
you're decoding the strings properly.  You'd run your arduino code with
a "getSerialString()" then a "Serial.print(str)" in a loop, then cut and
paste from the console display into a file, then run your decoder
against it.

I you ever studied this

formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

Thats what the Arduino "AttachInterrupt()" is for

attachInterrupt(digitalPinToInterrupt(pin), ISR, mode);
where mode is probably going to be "RISING".

Nothing fancy in the ISR, just a "1ppsdetected++;" or something.

then in the void loop(), you do a test on 1ppsdetected

if (1ppsdetected>0){
1ppsdetected = 0;
update_display();
}

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development for the
TruePosition boards.  I've got Arduino code together than can read in the
serial stream, parse it, and display time, date, number of satellites, and
TFOM on a 2x16 LCD display.  It does not do multiple screens, handle survey,
or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want to use
the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the display
}

This works great when there is a just a clock message.  But when there is a
clock message, an extstatus message, and a status message, it seems like it
is still parsing when the 1PPS tick comes in...so it will display seconds as
follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one second
fast.  I say "seems" to be fast, as the time agrees with an NTP clock on one
computer, but seems a half second slow per GPSCon's time display on the
Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to figure
out how much time elapses between the clock, extstatus, status, and 1PPS
tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't make
that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

On 5/21/17 11:20 AM, Chris Albertson wrote: > The problem is that you get the ENTIRE string then parse it. This is > not going to work well as you found out. Your CPU spends almost the > entire time waiting for characters to come in slowly off the serial > line. You are just waiting on bits and wasting CPU cycles On many Arduinos these days, the "getSerialString()" is a buffered/interrupt driven routine under the hood - it's not burning many cycles. That said, even if your serial port code was "spin on a bit", you can do a lot of parsing/processing pretty quickly. Arduinos aren't 4 MHz Z80s or 8051s. The modern crop have 50 MHz clocks and a millisecond is a lot of instructions. > > What you need to do is parse one character at a time. I bet your > parser reads one character at a time from the string. Have it read > one character at a time directly from the serial port. (Use a state > machine. It will work for such a simple job as this) > > Yes if your CPU was MUCH faster your plan could work. But on some > GPSes the data never has a break. You are trying to do ALL the work > in the break but actually most of the down time when you should be > working is between the characters. There is not a lot of work a > finite state machine needs to do between characters, just move state > based on a 'character class" table. I think that would be overkill, it's a lot harder to write a state machine than a simple "is the first N characters $GPPGA?" kind of thing. You'd want to write a generalized parser first if only to make sure that you're decoding the strings properly. You'd run your arduino code with a "getSerialString()" then a "Serial.print(str)" in a loop, then cut and paste from the console display into a file, then run your decoder against it. I you ever studied this > formally, what you are building here is a "lexer" not a parcer. The > "Language" is not recursive and you never need to backtrack so it can > be de-coded literally one character at a time. > > You DO really want the 1PPS to drive an interrupt. Thisway you just > continue working on the data stream and don't wait for the PPS. When > the PPS happens you do something QUICK. never do anything time > consuming in the ISR or you will miss the next serial character. > increment a seconds count and write two bytes the the LCD and exit Thats what the Arduino "AttachInterrupt()" is for attachInterrupt(digitalPinToInterrupt(pin), ISR, mode); where mode is probably going to be "RISING". Nothing fancy in the ISR, just a "1ppsdetected++;" or something. then in the void loop(), you do a test on 1ppsdetected if (1ppsdetected>0){ 1ppsdetected = 0; update_display(); } > > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: >> Good morning all, >> >> A quick update for those interested on my Arduino code development for the >> TruePosition boards. I've got Arduino code together than can read in the >> serial stream, parse it, and display time, date, number of satellites, and >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle survey, >> or display lat/long yet. >> >> What I'm having issues with is handling the 1 PPS. Ideally, I want to use >> the 1PPS signal to trigger the display update. IE: >> >> void loop() >> { >> getSerialString() // uses serial.available to pull in the serial data >> >> parser() // this parses the data >> >> wait for 1PPS tick to go high >> >> if there has been a clock message, updateDispay() // update the display >> } >> >> This works great when there is a just a clock message. But when there is a >> clock message, an extstatus message, and a status message, it seems like it >> is still parsing when the 1PPS tick comes in...so it will display seconds as >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... >> >> (If I don't wait for the 1PPS tick, it seems that my clock is one second >> fast. I say "seems" to be fast, as the time agrees with an NTP clock on one >> computer, but seems a half second slow per GPSCon's time display on the >> Z3801. I think I need to put up the antenna and check against WWV.) >> >> I've got one of those cheap little USB logic analyzers on order to figure >> out how much time elapses between the clock, extstatus, status, and 1PPS >> tick. I may need something faster than an Arduino Uno to do this. >> >> I'm sure there is a way to do this with an interrupt...but I couldn't make >> that work yesterday. More to follow. >> >> thanks much and 73, >> ben, kd5byb >> _______________________________________________ >> time-nuts mailing list -- time-nuts@febo.com >> To unsubscribe, go to >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts >> and follow the instructions there. > > >
DW
Daniel Watson
Mon, May 22, 2017 3:11 AM

Hi,

Here's an interesting addition to the project once you get the serial
parser and display driver worked out. It is quite easy to generate the
$GPZDA NMEA message in your program. You can send this off to a Raspberry
Pi or BBB along with the PPS signal and drive an NTP server. :)

[image: Inline image 2]

Dan

On Sun, May 21, 2017 at 5:48 PM, Chris Albertson albertson.chris@gmail.com
wrote:

The root of the problem is that he is doing all the parking at once
and ignoring inputs from both the serial line and the 1PPS

Even if the iPPS were connected to an interrupt (and it should be) he
is still busy parking input when the ISR sets the flag.

He needs to read the data fro the serial line one character at a time
and not wait to start parsing.

Either that or he needs to insert calls to some kind of CHECKINPUTS()
every few lines in the parser and that just look ugly.

On Sun, May 21, 2017 at 11:56 AM, Jim Harman j99harman@gmail.com wrote:

Another way to do is to use the 1 PPS to trigger an interrupt on the
Arduino. Look at the documentation for attachInterrupt(). In the

interrupt

routine, have it set a flag. The flag variable should be declared up

front

as volatile.

Then in your main loop, do all your parsing then loop waiting for the

flag

to be set. When set, update the clock then clear the flag and repeat.

On Sun, May 21, 2017 at 2:32 PM, Chris Albertson <

wrote:

To add to my last message.

You CAN collect all the data then parse it like you are doing if you
were to move to an interrupt driven serial port reader.  Each
character is then read by the interrupt handler anyplace in a large
circular buffer.  The parcer then reads out of the other and of this
buffer.

The phlegm with the current code is the parse ingnores serial input
and will drop data, in also ignore the PPS and will as you found drop
pulses.

Typically in real time processors like your that must be interrupt
driven or they must poll MANY times laster then the data arrives

so as I wrote before, parsing the data stream one character at a tie
is in effect pooling the serial port much faster then characters
arrive.    Adding a ring buffer and interrupts guarantees yo never
miss a character and certainly you need to interrupt in the PPS to
handle the case there three s serial data and the PPS at the same
time.

The ring buffer is like you big string except you data data onto one
end at the same time as soured data off the other.  Hopefully the ring
buffer never has much data in it as the parser should be fathers then
the serial line.  BUT if a PPS happens then the parser in interrupted
while the display updates so th ring buffer might get filled up a
little.  But the ISR terminals the parser clears the buffer.

On Sun, May 21, 2017 at 11:20 AM, Chris Albertson
albertson.chris@gmail.com wrote:

The problem is that you get the ENTIRE string then parse it.  This is
not going to work well as you found out.  Your CPU spends almost the
entire time waiting for characters to come in slowly off the serial
line.  You are just waiting on bits and wasting CPU cycles

What you need to do is parse one character at a time.  I bet your
parser reads one character at a time from the string.  Have it read
one character at a time directly from the serial port.  (Use a state
machine.  It will work for such a simple  job as this)

Yes if your CPU was MUCH faster your plan could work.  But on some
GPSes the data never has a break.  You are trying to do ALL the work
in the break but actually most of the down time when you should be
working is between the characters.    There is not a lot of work a
finite state machine needs to do between characters, just move state
based on a 'character class" table.      I you ever studied this
formally, what you are building here is a "lexer" not a parcer.  The
"Language" is not recursive and you never need to backtrack so it can
be de-coded literally one character at a time.

You DO really want the 1PPS to drive an interrupt.  Thisway you just
continue working on the data stream and don't wait for the PPS.  When
the PPS happens you do something QUICK. never do anything time
consuming in the ISR or you will miss the next serial character.
increment a seconds count and write two bytes the the LCD and exit

On Sun, May 21, 2017 at 6:45 AM, Ben Hall kd5byb@gmail.com wrote:

Good morning all,

A quick update for those interested on my Arduino code development

for

the

TruePosition boards.  I've got Arduino code together than can read in

the

serial stream, parse it, and display time, date, number of

satellites,

and

TFOM on a 2x16 LCD display.  It does not do multiple screens, handle

survey,

or display lat/long yet.

What I'm having issues with is handling the 1 PPS.  Ideally, I want

to

use

the 1PPS signal to trigger the display update.  IE:

void loop()
{
getSerialString()  // uses serial.available to pull in the serial

data

parser()  // this parses the data

wait for 1PPS tick to go high

if there has been a clock message, updateDispay()  // update the

display

}

This works great when there is a just a clock message.  But when

there

is a

clock message, an extstatus message, and a status message, it seems

like it

is still parsing when the 1PPS tick comes in...so it will display

seconds as

follows:  30, 31, 33, 34, 35, 36, 37, 39, etc...

(If I don't wait for the 1PPS tick, it seems that my clock is one

second

fast.  I say "seems" to be fast, as the time agrees with an NTP clock

on one

computer, but seems a half second slow per GPSCon's time display on

the

Z3801.  I think I need to put up the antenna and check against WWV.)

I've got one of those cheap little USB logic analyzers on order to

figure

out how much time elapses between the clock, extstatus, status, and

1PPS

tick.  I may need something faster than an Arduino Uno to do this.

I'm sure there is a way to do this with an interrupt...but I couldn't

make

that work yesterday.  More to follow.

thanks much and 73,
ben, kd5byb


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to
https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts
and follow the instructions there.

--

Chris Albertson
Redondo Beach, California

--

Chris Albertson
Redondo Beach, California


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/
mailman/listinfo/time-nuts
and follow the instructions there.

--

--Jim Harman


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/

mailman/listinfo/time-nuts

and follow the instructions there.

--

Chris Albertson
Redondo Beach, California


time-nuts mailing list -- time-nuts@febo.com
To unsubscribe, go to https://www.febo.com/cgi-bin/
mailman/listinfo/time-nuts
and follow the instructions there.

Hi, Here's an interesting addition to the project once you get the serial parser and display driver worked out. It is quite easy to generate the $GPZDA NMEA message in your program. You can send this off to a Raspberry Pi or BBB along with the PPS signal and drive an NTP server. :) [image: Inline image 2] Dan On Sun, May 21, 2017 at 5:48 PM, Chris Albertson <albertson.chris@gmail.com> wrote: > The root of the problem is that he is doing all the parking at once > and ignoring inputs from both the serial line and the 1PPS > > Even if the iPPS were connected to an interrupt (and it should be) he > is still busy parking input when the ISR sets the flag. > > He needs to read the data fro the serial line one character at a time > and not wait to start parsing. > > Either that or he needs to insert calls to some kind of CHECKINPUTS() > every few lines in the parser and that just look ugly. > > On Sun, May 21, 2017 at 11:56 AM, Jim Harman <j99harman@gmail.com> wrote: > > Another way to do is to use the 1 PPS to trigger an interrupt on the > > Arduino. Look at the documentation for attachInterrupt(). In the > interrupt > > routine, have it set a flag. The flag variable should be declared up > front > > as volatile. > > > > Then in your main loop, do all your parsing then loop waiting for the > flag > > to be set. When set, update the clock then clear the flag and repeat. > > > > > > > > On Sun, May 21, 2017 at 2:32 PM, Chris Albertson < > albertson.chris@gmail.com> > > wrote: > > > >> To add to my last message. > >> > >> You CAN collect all the data then parse it like you are doing if you > >> were to move to an interrupt driven serial port reader. Each > >> character is then read by the interrupt handler anyplace in a large > >> circular buffer. The parcer then reads out of the other and of this > >> buffer. > >> > >> The phlegm with the current code is the parse ingnores serial input > >> and will drop data, in also ignore the PPS and will as you found drop > >> pulses. > >> > >> Typically in real time processors like your that must be interrupt > >> driven or they must poll MANY times laster then the data arrives > >> > >> so as I wrote before, parsing the data stream one character at a tie > >> is in effect pooling the serial port much faster then characters > >> arrive. Adding a ring buffer and interrupts guarantees yo never > >> miss a character and certainly you need to interrupt in the PPS to > >> handle the case there three s serial data and the PPS at the same > >> time. > >> > >> The ring buffer is like you big string except you data data onto one > >> end at the same time as soured data off the other. Hopefully the ring > >> buffer never has much data in it as the parser should be fathers then > >> the serial line. BUT if a PPS happens then the parser in interrupted > >> while the display updates so th ring buffer might get filled up a > >> little. But the ISR terminals the parser clears the buffer. > >> > >> On Sun, May 21, 2017 at 11:20 AM, Chris Albertson > >> <albertson.chris@gmail.com> wrote: > >> > The problem is that you get the ENTIRE string then parse it. This is > >> > not going to work well as you found out. Your CPU spends almost the > >> > entire time waiting for characters to come in slowly off the serial > >> > line. You are just waiting on bits and wasting CPU cycles > >> > > >> > What you need to do is parse one character at a time. I bet your > >> > parser reads one character at a time from the string. Have it read > >> > one character at a time directly from the serial port. (Use a state > >> > machine. It will work for such a simple job as this) > >> > > >> > Yes if your CPU was MUCH faster your plan could work. But on some > >> > GPSes the data never has a break. You are trying to do ALL the work > >> > in the break but actually most of the down time when you should be > >> > working is between the characters. There is not a lot of work a > >> > finite state machine needs to do between characters, just move state > >> > based on a 'character class" table. I you ever studied this > >> > formally, what you are building here is a "lexer" not a parcer. The > >> > "Language" is not recursive and you never need to backtrack so it can > >> > be de-coded literally one character at a time. > >> > > >> > You DO really want the 1PPS to drive an interrupt. Thisway you just > >> > continue working on the data stream and don't wait for the PPS. When > >> > the PPS happens you do something QUICK. never do anything time > >> > consuming in the ISR or you will miss the next serial character. > >> > increment a seconds count and write two bytes the the LCD and exit > >> > > >> > On Sun, May 21, 2017 at 6:45 AM, Ben Hall <kd5byb@gmail.com> wrote: > >> >> Good morning all, > >> >> > >> >> A quick update for those interested on my Arduino code development > for > >> the > >> >> TruePosition boards. I've got Arduino code together than can read in > >> the > >> >> serial stream, parse it, and display time, date, number of > satellites, > >> and > >> >> TFOM on a 2x16 LCD display. It does not do multiple screens, handle > >> survey, > >> >> or display lat/long yet. > >> >> > >> >> What I'm having issues with is handling the 1 PPS. Ideally, I want > to > >> use > >> >> the 1PPS signal to trigger the display update. IE: > >> >> > >> >> void loop() > >> >> { > >> >> getSerialString() // uses serial.available to pull in the serial > data > >> >> > >> >> parser() // this parses the data > >> >> > >> >> wait for 1PPS tick to go high > >> >> > >> >> if there has been a clock message, updateDispay() // update the > display > >> >> } > >> >> > >> >> This works great when there is a just a clock message. But when > there > >> is a > >> >> clock message, an extstatus message, and a status message, it seems > >> like it > >> >> is still parsing when the 1PPS tick comes in...so it will display > >> seconds as > >> >> follows: 30, 31, 33, 34, 35, 36, 37, 39, etc... > >> >> > >> >> (If I don't wait for the 1PPS tick, it seems that my clock is one > second > >> >> fast. I say "seems" to be fast, as the time agrees with an NTP clock > >> on one > >> >> computer, but seems a half second slow per GPSCon's time display on > the > >> >> Z3801. I think I need to put up the antenna and check against WWV.) > >> >> > >> >> I've got one of those cheap little USB logic analyzers on order to > >> figure > >> >> out how much time elapses between the clock, extstatus, status, and > 1PPS > >> >> tick. I may need something faster than an Arduino Uno to do this. > >> >> > >> >> I'm sure there is a way to do this with an interrupt...but I couldn't > >> make > >> >> that work yesterday. More to follow. > >> >> > >> >> thanks much and 73, > >> >> ben, kd5byb > >> >> _______________________________________________ > >> >> time-nuts mailing list -- time-nuts@febo.com > >> >> To unsubscribe, go to > >> >> https://www.febo.com/cgi-bin/mailman/listinfo/time-nuts > >> >> and follow the instructions there. > >> > > >> > > >> > > >> > -- > >> > > >> > Chris Albertson > >> > Redondo Beach, California > >> > >> > >> > >> -- > >> > >> Chris Albertson > >> Redondo Beach, California > >> _______________________________________________ > >> time-nuts mailing list -- time-nuts@febo.com > >> To unsubscribe, go to https://www.febo.com/cgi-bin/ > >> mailman/listinfo/time-nuts > >> and follow the instructions there. > >> > > > > > > > > -- > > > > --Jim Harman > > _______________________________________________ > > time-nuts mailing list -- time-nuts@febo.com > > To unsubscribe, go to https://www.febo.com/cgi-bin/ > mailman/listinfo/time-nuts > > and follow the instructions there. > > > > -- > > Chris Albertson > Redondo Beach, California > _______________________________________________ > time-nuts mailing list -- time-nuts@febo.com > To unsubscribe, go to https://www.febo.com/cgi-bin/ > mailman/listinfo/time-nuts > and follow the instructions there. >