Yahoo Groups archive

AVR-Chat

Index last updated: 2026-04-28 22:41 UTC

Message

Optimization levels in WinAVR, wierd problem.

2009-04-30 by David VanHorn

Bear with me, this isn't simple.

I have two sensors, each outputs a square wave.
I need to accurately measure the period of each, and determine the
difference in the two periods.

Depending on how I set the optimization, I get different results.

At -Os, I see values like 292, 304, 316.
The values are spaced by 12!
I won't ever see 305, 306, 307...

If I recompile with -O0, the spacing between the values is different,
but still mostly three discrete steps in values with nothing in
between.

I'm using an M644 at 20 MHz, T1 is running at CK/1

The basics are that I stop the clock to T1, and clear it.. Then I wait
till I see a low, then wait till I see a high, then I start the timer.
 With the timer running, I wait till I see low, high, low high... till
five periods have passed, then I stop the clock to T1, and take the
data.

Having done that, I do the same thing for the other sensor, then
subtract the second sensor from the first, which should give me some
small-ish value. The exact number isn't important, but what is
puzzling me is that the intermediate values are missing. Like somehow
I'm loosing low bits, but the delta is 12, which makes no sense from a
binary perspective.



// Prep for aquisition
TCCR1B &= ~(1<<CS10);				
// Stop T1 (should already BE stopped,
// but it's cheap insurance)

TCNT1=0;			
// Clear T1	
		
// Sync to the A channel
while (  Sensor_Pin & (1<<ChannelA));
// Wait for a low, so we know we're not seeing
// a high level yet
while (!(Sensor_Pin & (1<<ChannelA))); 	
// Wait for the high edge

TCCR1B |=(1<<CS10);// START the clock to T1

// T1 is now counting the period width.
// That can be as little as 25us
// (5 periods *  5us * 20 MHz =  500 counts)
// or as much as 138 uS
// (5 periods * 23uS * 20 MHz = 2300 counts)

while (  Sensor_Pin & (1<<ChannelA));
// Wait for a low on PD2
while (!(Sensor_Pin & (1<<ChannelA)));
//  Wait for a high on PD2	
// One pulse has gone
while (  Sensor_Pin & (1<<ChannelA));
while (!(Sensor_Pin & (1<<ChannelA)));		
// Now two
while (  Sensor_Pin & (1<<ChannelA));
while (!(Sensor_Pin & (1<<ChannelA)));		
// Now three
while (  Sensor_Pin & (1<<ChannelA));
while (!(Sensor_Pin & (1<<ChannelA)));	
// Now four
while (  Sensor_Pin & (1<<ChannelA));
while (!(Sensor_Pin & (1<<ChannelA)));	
// Now five

TCCR1B &= ~(1<<CS10);	
// Stop T1
A_Sensor_Raw = TCNT1;	
// Grab the data
TCNT1=0;		
// Clear T1 for the next measurement.

// Sync to the B channel, and proceed as above
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
TCCR1B |=(1<<CS10);
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
while (  Sensor_Pin & (1<<ChannelB));
while (!(Sensor_Pin & (1<<ChannelB)));
TCCR1B &= ~(1<<CS10);	
Temp2 = TCNT1;
TCNT1=0;					

//**********
// Condition according to sensor
// Scale to fit the histogram array
// Take the difference, and add half
  A_Sensor_Raw = ((A_Sensor_Raw - Temp2) + (Sample_Bins/2));
 // If the value is out of range then wrap it
 A_Sensor_Raw = (A_Sensor_Raw & 0x01FF);


Why do I not see output like 290,291,292... ?

-- 
There is no computer problem which cannot be solved by proper
application of a sufficiently large hammer.

Attachments

Move to quarantaine

This moves the raw source file on disk only. The archive index is not changed automatically, so you still need to run a manual refresh afterward.