Go Down

Topic: Why doesn't the pulseIn display duration more than 170ms??? (Read 3 times) previous topic - next topic

Mr.Debugger

Oct 09, 2011, 09:43 am Last Edit: Oct 09, 2011, 09:47 am by Mrxnoxious991 Reason: 1
Hey,

I am trying to measure the duration of an active LOW signal using pulseIn function.
The results are pretty confusing!
The controller only displays results of pulses that are fast ( i.e. less than 170ms) and returns "0" if the duration of the pulse exceeds more than 170. The max. value I could capture was 169250 usec.
I suspect it has something to do with the the overflow or the time out function.

Any help would be appreciated

Thanks!

Here's the code:
Code: [Select]
unsigned long duration;
int counter = 0;
void setup()
{
pinMode (5, INPUT);
Serial.begin(9600);
}
void loop()
{
  duration = pulseIn(5, LOW);
{
  Serial.println (duration);
   
}
}



robtillaart


In wiring_pulse.c  (its in the Arduino distribution ) the pulsein function is defined. It returns 0 if there is a timeout, so that is not the case as you get nr > 0.

The signature is :   unsigned long pulseIn(uint8_t pin, uint8_t state, unsigned long timeout)

you call it with 2 parameters so where does the 3rd param (timeout)  comes from.... I even wondered that it compiled ....

Can you explicitly pass a timeout value?


Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

robtillaart

Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

PaulS

Quote
you call it with 2 parameters so where does the 3rd param (timeout)  comes from.... I even wondered that it compiled ....

You need to look at the header file for the function, too. The timeout argument is defined with a default value, making it optional.

The pulseIn function is designed to measure events that occur within a reasonably short period of time. 169250 microseconds is not what pulseIn was designed to measure. For servo PPM pulses, for example, that time-frame would indicate that the pulse sender was dead in the water.

robtillaart


OK, forgot about the headerfile and the optional parameter  :smiley-red: :smiley-red: :smiley-red: :)

But stil, the default value for the parameter = 1.000000L  which is 5x bigger that the max value the OP got.

Code: [Select]

  ...
  return clockCyclesToMicroseconds(width * 21 + 16);
}

#define clockCyclesToMicroseconds(a) ( ((a) * 1000L) / (F_CPU / 1000L) )


These two lines together cause an overflow...   Looking at the math it can be replaced with something simpler

return ((width*21+16) / clockCyclesPerMicrosecond() );


which overflows less fast as the factors 1000 (twice) is removed from the equation. This makes the PulseIn() function "behave better" in a larger range. Probably the division will be optimized to a shift so it will be a few cycles faster too.

Reported as bug/enhancement  in - http://code.google.com/p/arduino/issues/detail?id=675 -






Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

Go Up