View previous topic :: View next topic |
Author |
Message |
asmboy
Joined: 20 Nov 2007 Posts: 2128 Location: albany ny
|
stuck in struct wonderland[solved w/o union] |
Posted: Sat Nov 26, 2011 4:34 pm |
|
|
The idea is to drive timer1 with a 16 mhz clock prescaled to get
1 usec external event counts. When the timer overflows, ( 65536 usecs)
it's interrupt routine increments usecs. An random edge triggered
event on port B copies the present remainder microseconds elapsed
directly from timer1 into lowusecs, which holds the next next highest significant bit of total microseconds;
It is desired to use struct htx as a 32bit unsigned composite value
for comparison and printing of elapsed microseconds.
Code: |
STRUCT htx {
unsigned int8 top32;
unsigned int8 usecs;
unsigned int16 lowusecs;
} hlx={0,0,0};
// then later on it works
++hlx.usecs;
if (!hlx.usecs) ++hlx.top32;
// ....
hlx.lowusecs=get_timer1();
//
// THEN i have compile trouble unless i use 32 bit casting
if (131024> (unsigned int32) hlx) printf("%Lu\r", (unsigned int32) hlx);
// if (131024> hlx) printf("%Lu\r", hlx);
// above ERROR: STRUCTURE FIELD NAME REQUIRED
|
Compiler 4.085, but I assume there is some bit of declaration i have not done right. But What is it ??
Last edited by asmboy on Sun Nov 27, 2011 10:04 am; edited 1 time in total |
|
|
asmallri
Joined: 12 Aug 2004 Posts: 1635 Location: Perth, Australia
|
|
Posted: Sat Nov 26, 2011 5:19 pm |
|
|
What you need is a union of a 32 bit value and the structure. _________________ Regards, Andrew
http://www.brushelectronics.com/software
Home of Ethernet, SD card and Encrypted Serial Bootloaders for PICs!! |
|
|
FvM
Joined: 27 Aug 2008 Posts: 2337 Location: Germany
|
|
Posted: Sun Nov 27, 2011 1:39 am |
|
|
The struct layout is hard to understand. Why fields are arranged reversed order in a big endian kind? There's no chance to get a visual number when printing the 32 bit value.
Also the if (!hlx.usecs) ++hlx.top32; could be avoided by defining usecs as an unsigned int16 that is simply incremented.
Combining the fractional usecs from timer1 to get a consistent value would require a bit shift, because the 1/16 us sec value has to be left aligned.
Finally, it's impossible to perform these actions each usec. |
|
|
asmboy
Joined: 20 Nov 2007 Posts: 2128 Location: albany ny
|
|
Posted: Sun Nov 27, 2011 10:04 am |
|
|
thanks for the various tips.
the following code compiles and does everything
i need properly, and with minimal instructions generated.
and replies
THANKS for pointing out the reversed order of VARS !!
My bad -- but all fixed now
As it turns out - no union required - as code now compiles and LST
is A-ok in V4.085 anyway
as to the rest - the replies created new questions.
Quote: |
1/16 us sec value has to be left aligned.
|
what am i missing? what 1/16th sec ??
my math is is {Xtal_osc 16e6 /4= 4e6} // master clock Fosc
{ pre-scalar 4e6 /4= 1e6 } // 1 usec per timer1 "tick"
{ 1e6 /65536 = .065536 seconds } // stored in hla.usecs on overflow
// for read back - the timer provides low word's worth
I thought i was counting pure 1 usec increments with the overflow of
the low 16 counts being pure binary , and accurately reflected in the HIGH word of the STRUCT. what 1/16th sec are we talking about here?
the actual count is retrieved based on an edge sensitive interrupt
on Port B . the code is to be used for accurate frequency counting
of very low frequency events - catching the PERIOD of the waveform between positive edges and determining the frequency externally using F=1/P with floating point being done on a PC host ;-))
Quote: |
Finally, it's impossible to perform these actions each usec.
|
YES we totally agree, but where am i doing that ??
i thought i was accumulating rollovers and servicing the timer1 int every 65536 usecs - counts not on every usec. i treat timer1 16 bit register as an accumulator of single 1 us counts that is read when a port B interrupt is triggered by a positive edge, and combine with the rollovers of 65536 counts, collected on interrupt servicing.
this fragment shows the salient
details of a much larger program
Code: |
unsigned int32 basetime =0;
// .....
STRUCT htx {
unsigned int16 lowusecs;
unsigned int16 usecs;
} hla={0,0};
// ..... in the timer1 rollover
// int every 65536 uSecs
++hla.usecs;
// ...later on when edge trigger is taken from ext signal
hla.lowusecs=get_timer1();
// .....
void setbase(void){
basetime=hla;
}
// ..... later on example
if (edge_positive ) comp = hla+basetime; // transfer
|
|
|
|
gpsmikey
Joined: 16 Nov 2010 Posts: 588 Location: Kirkland, WA
|
|
Posted: Sun Nov 27, 2011 12:24 pm |
|
|
You made the comment at the start "it's interrupt routine increments usecs." - I would assume that is where folks came up with the idea you wanted to increment every microsecond ??
mikey _________________ mikey
-- you can't have too many gadgets or too much disk space !
old engineering saying: 1+1 = 3 for sufficiently large values of 1 or small values of 3 |
|
|
asmboy
Joined: 20 Nov 2007 Posts: 2128 Location: albany ny
|
|
Posted: Sun Nov 27, 2011 2:18 pm |
|
|
"it's interrupt routine increments usecs."
yes it does - in multiples of 65536
|
|
|
|