PDA

View Full Version : PulsIn question.



Peter Oors
- 22nd November 2005, 21:02
Can somebody give me an answer?
How many µs does the PulsIn command take?
I would like to measure a pulsetrain with 2 kind of pulses,
91µs high and 13µs low (long), 13µs high and 91µs low (short).
I use the 16F819 and the 16F628 with 20MHz X-tal.

air1kdf
- 23rd November 2005, 05:24
I would also like to know how long the pulsin command overhead itself takes with a given frequency.

For example assume that the pulsin returned 1000 with a 20Mhz crystal would be 2000 microseconds. If It started measuring just after a change in state it would have taken say 1999 + 2000 or 3999 microseconds. Now add the overhead of the command itself and that would be the total time that the command takes.

Peter Oors
- 13th January 2006, 19:18
Today I measured a time from the end of a pulse to the end of the PulsIn command of about 12us.
For me the PulsIn command is useless.
In assembler it's the best way, but I don't know how to do this in assembler.

mister_e
- 14th January 2006, 00:22
Even in PBP you'll be able to do it with a decent result. Just use the internal timer. The following example is more than enough to start.



' Pulse High and Low Timer
' ========================
'
' File name : PulseHighLowTimer.bas
' Company : Mister E
' Programmer : Steve Monfette
' Date : 13/01/2006
' Device : PIC16F88
'

'
' This program measure and send to PC, the value of incomming pulses.
' The program will send measure of High pulse and Low Pulse length in uSec.

'
' Hardware configuration
' ======================
DEFINE OSC 20
DEFINE LOADER_USED 1
TRISB = %00000100 ' RB2 as input => Serial RX
TRISA = 255 ' PORTA As input
CMCON = 7 ' Disable analog comparator
ANSEL = 0 ' Disable all A/d
T1CON = 0 ' TIMER1:
' Clock Internal
' Pre-scaller 1:1
'
' Hardware connection
' ===================
SignalInput var PORTA.2

'
' Serial Communication definition
' ===============================
DEFINE HSER_RCSTA 90h
DEFINE HSER_TXSTA 24h
DEFINE HSER_SPBRG 129 ' 9600 Bauds
DEFINE HSER_CLROERR 1
'
' Alias Definition definition
' ===========================
T1ON var T1CON.0

'
' Variables definition
' ===================
PulseHigh var word
PulseLow var word

'
' Software/Hardware initialisation
' ================================
CLEAR
GOSUB ClearTimer
'
' ////////////////////////////////|\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
'
' Program Start Here
'
' ////////////////////////////////|\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
'
Start:
'
' Waiting for falling edge
' ========================
'
WHILE SIGNALINPUT=0 : WEND
WHILE SIGNALINPUT=1 : WEND
'
' Measure low pulse
' =================
'
T1ON=1 ' start Timer
WHILE SIGNALINPUT=0 : WEND ' wait for next rising edge
T1ON=0 ' stop timer
PULSElow.HIGHBYTE=TMR1H ' store results
PULSElow.LOWBYTE=TMR1L '
pulselow=pulselow / 5 ' 1 tick = 0.2 Usec @ 20MHZ
' Divide by 5 to have 1 uSec
' Resolution
gosub Cleartimer ' reset Timer1 register (TMR1L, TMR1H)
'
' Waiting for rising edge
' =======================
'
while Signalinput=1 : Wend
while signalinput=0 : wend
'
' Measure high pulse
' ==================
'
T1ON=1 ' Start timer
WHILE SIGNALINPUT=1 : WEND ' wait for next falling edge
T1ON=0 ' Stop Timer
PULSEhigh.HIGHBYTE=TMR1H ' Store result
PULSEhigh.LOWBYTE=TMR1L '
pulsehigh=pulsehigh / 5 ' match results to 1 uSec resolution
gosub Cleartimer ' reset Timer1 register (TMR1L, TMR1H)

'
' Send results to PC via RS-232
' =============================
'
hserout ["PulseLow =",dec pulselow, " uSec",13,10,_
"PulseHigh=",dec pulsehigh," uSec",13,10,_
rep "*"\50,13,10]
pause 1000
goto start

ClearTimer:
TMR1L=0
TMR1H=0
RETURN

I agree, you can have a bit more accuracy in pure assembler... but test with the above first.

It's only one way to do it... that's the results of a 10 minutes coding... on friday 13 ;)

Peter Oors
- 15th January 2006, 22:03
Thanks very much mister_e, you are a great help.
The text was very helpfull. The accuracy is perfect for me.

When I measured more pulses, there was a problem.
Something goes wrong.
Dividing by 5 gives problems.

=====================================
T1ON=1 ' start Timer
While SIGNALINPUT=0 : Wend ' wait for next rising edge
T1ON=0 ' stop timer
PULSElow.HIGHBYTE=TMR1H ' store results
PULSElow.LOWBYTE=TMR1L '
pulselow=pulselow / 5
=====================================

The above part I changed in (not the most beautiful way):

Start:
GoSub meten
PULSEhigh1.HIGHBYTE=TMR1H ' Store result
PULSEhigh1.LOWBYTE=TMR1L
GoSub meten
PULSEhigh2.HIGHBYTE=TMR1H ' Store result
PULSEhigh2.LOWBYTE=TMR1L
GoSub meten
PULSEhigh3.HIGHBYTE=TMR1H ' Store result
PULSEhigh3.LOWBYTE=TMR1L
GoSub meten
PULSEhigh4.HIGHBYTE=TMR1H ' Store result
PULSEhigh4.LOWBYTE=TMR1L
GoSub Cleartimer
GoSub meten
PULSEhigh5.HIGHBYTE=TMR1H ' Store result
PULSEhigh5.LOWBYTE=TMR1L
GoSub meten
PULSEhigh6.HIGHBYTE=TMR1H ' Store result
PULSEhigh6.LOWBYTE=TMR1L
GoSub meten
PULSEhigh7.HIGHBYTE=TMR1H ' Store result
PULSEhigh7.LOWBYTE=TMR1L
GoSub meten
PULSEhigh8.HIGHBYTE=TMR1H ' Store result
PULSEhigh8.LOWBYTE=TMR1L
GoSub meten
PULSEhigh9.HIGHBYTE=TMR1H ' Store result
PULSEhigh9.LOWBYTE=TMR1L
GoSub meten
PULSEhigh10.HIGHBYTE=TMR1H ' Store result
PULSEhigh10.LOWBYTE=TMR1L
GoSub Cleartimer

Pulsehigh1=pulsehigh1 / 5
Pulsehigh2=pulsehigh2 / 5
Pulsehigh3=pulsehigh3 / 5
Pulsehigh4=pulsehigh4 / 5
Pulsehigh5=pulsehigh5 / 5
Pulsehigh6=pulsehigh6 / 5
Pulsehigh7=pulsehigh7 / 5
Pulsehigh8=pulsehigh8 / 5
Pulsehigh9=pulsehigh9 / 5
Pulsehigh10=pulsehigh10 / 5

Write 1, pulsehigh1
Write 2 ,Pulsehigh2
Write 3 ,Pulsehigh3
Write 4 ,Pulsehigh4
Write 5 ,Pulsehigh5
Write 6 ,Pulsehigh6
Write 7 ,Pulsehigh7
Write 8 ,Pulsehigh8
Write 9 ,Pulsehigh9
Write 10 ,Pulsehigh10
Stop
==================================
meten:
GoSub Cleartimer
While signalinput=0 : Wend ' Waiting for rising edge
T1ON=1 ' Start timer, measure High pulse
While SIGNALINPUT=1 : Wend ' Wait for next falling edge
T1ON=0 ' Stop Timer
Return
Cleartimer:
TMR1L=0
TMR1H=0
Return

It works fine, not beautiful, I know.
Thanks for the help.