Time Measurement, IR decoding

advertisement
Time Measurement
Measuring pushbutton pulse width
• Capture Mode of the Capture/Compare/PWM module
is used for time measurement.
TMR1 16bit value
transferred
to 16-bit
capture
register on
edge detect.
PICF16873
RC2/CCP1
Pulse Width
1. Capture TMR1 value on falling edge (Tf)
2. Capture TMR1 value on rising edge (Tr)
3. Pulse width = Tr - Tf
Rising or falling edge detect, with interrupt flag
set.
V 0.1
1
swdet.c (configuration)
V 0.1
configure for falling edge
set edge_type = 0 (falling) so ISR knows what
edge has happened.
/* set up capture */
bitset(TRISC,2); /* set CCP1 input */
/*capture every falling edge 0100 */
bitclr(CCP1CON, 3);
bitset(CCP1CON, 2);
Setup falling edge capture
bitclr(CCP1CON, 1);
bitclr(CCP1CON, 0);
2
swdet.c
(main loop)
wait for interrupt
// enable interrupts
// CCP1IF = 0; clear capture interrupt flag
bitclr(PIR1,2);
// enable capture interrupt CCP1IE = 1;
bitset(PIE1, 2) ;
Interrupt
// enable peripheral interrupts, PEIE
enables
bitset(INTCON,6);
(CCP1, PEIE,
//enable global interrupts, GIE
GIE)
bitset(INTCON,7);
V 0.1
Use interrupt to save timer values.
configure for rising edge
set edge_type = 1 (rising) so ISR knows what
edge has happened.
wait for interrupt
print pulse width
3
V 0.1
4
Get 16-bit capture value (CCPR1H:CCPR1L)
swdet.c (main loop)
0 (falling)
for(;;) {
CCP1CON = 0; /* turn off when changing modes */
CCP1CON = 0x4; /* capture every falling edge */
edge_type = 0; /* looking for falling edge */|
capture_flag = 0;
while(!capture_flag);
capture_flag = 0;
CCP1CON = 0; /* turn off when changing modes */
CCP1CON = 0x5; /* capture every rising edge */
edge_type = 1; /* looking for rising edge*/
while(!capture_flag);
printf ("Switch pressed, timer ticks: %u",delta);
pcrlf();
1 (rising)
edge_type?
delta_time =
current_time –
last_time
save timer
value
interrupt
service
capture_flag = 1
return
}
V 0.1
5
V 0.1
6
1
Interrupt Service
Timer1 Overflow
unsigned int last_capture, this_capture;
timer_isr(void){
// CCP1IF = 0; clear capture interrupt flag
bitclr(PIR1,2);
pack 2 bytes
this_capture = CCPR1H << 8 ;
this_capture = this_capture | CCPR1L ;
into one
if (edge_type == 0) {
integer.
last_capture = this_capture;
} else {
/* compute delta */
if (this_capture > last_capture) {
delta = this_capture - last_capture;
} else {
/* this is timer overflow case */
delta = this_capture + ~last_capture + 1;
}
this_capture, last_capture unsigned
}
capture_flag = 1;
integers so can represent 0 to 65535
}
V 0.1
7
Timer1 is free running, captured at any time
0x0000
0x0000
Second capture (B)
First capture (A)
First capture (A)
Second capture (B)
0xFFFF
0xFFFF
overflow case (A > B)
no overflow case (B > A)
delta = B + (0 – A)
2’s complement
=B–A
= B + (~A + 1)
V 0.1
8
delta = B - A
Timer1 Scaling
Implementing a Clock/Calendar
Use 32.768KHz crystal on T1OS0/T1OS1 pins, this crystal
frequency good for accurate time keeping
32.768KHz = 32768 Hz
Æ when 16-bit counter rolls over, then exactly 2 seconds
Æ when counter = 0x8000, exactly 1 sec
No error in time keeping, good for long term
clock/calendar function.
Only options are 1,2,4,8. However, can be clocked by an
source independent of main oscillator.
V 0.1
9
V 0.1
Intensity Based Infrared
How to block Ambient Light?
Vdd
Rout (dc volt)
emitter
Vref
receiver
+
Vout
amplifier
Vdd
~
~
Vout = Vdd, IR present (Rout > Vref)
Vout = 0v, IR absent (Rout < Vref)
voltage
Increase in ambient light
raises DC bias
Vref
voltage
time
Transmitter
Problem: value for Vref
changes depending on
ambient light!
Vref
time
V 0.1
10
Receiver
capacitor blocks
DC
Open/Close switch at particular frequency
Transmitter
DC voltage here
depends only how
fast transmitter is
switched
switch
opening/closing
Waveform
11
V 0.1
12
2
Integrated IR Receiver
IR Waveform
Waveform produced by receiver when stimulated by a
universal remote control depends on function and
manufacturer.
Actual IR receiver a bit more complicated
# of bits depends
on IR remote
function
Start
All of this is in here
V 0.1
Out 1
23
13
Gnd
Space-Width Encoding Examples
T
Bit Value
2T
T
3T
‘0’
2T
Bit Value
T
T
2T
‘0’
T
Using ‘swdet.c’ as a starting point, decode the first two bytes of
a frame and print these two bytes out to the screen via
Hyperterm. Choose a particular prescale for Timer1 to give you
enough fidelity on Timer1 to distinguish ‘1’,’0’ periods.
‘0’
‘1’
T
14
Use the scope and determine the periods of ‘start’, ‘0’, and ‘1’
(assume a ‘0’ the short period, a ‘1’ is the long period).
Sony code: ‘0’ period = 2T, ‘1’ period= 3T
Bit Time
Length of start period, ’0’ period, ‘1’ period will vary with
function. ‘0’, ‘1’ waveforms may be inverted. Called spaceV 0.1
width modulation.
You will be assigned a function on the Universal Remote.
T
‘1’
Stop
‘1’
Lab #12: Decoding IR Waveform
REC-80 code, Panasonic: ‘0’ period = 3T, ‘1’ period = 4T
Bit Time
‘0’
T
Your particular function may have LOTs of bits in a frame, just
decode the first two bytes (16 bits). If your function does NOT
have at least 16 bits, then get the TA to assign you a different IR
remote function (or find one, and show this to the TA).
‘0’
From: “A Primer on Remote Control Technology”, Innotech
V 0.1 Systems, Inc.
15
V 0.1
16
Biphase Encoding
Example Waveform
In a previous example, ‘1’ and ‘0’ were distinguished by having
different periods.
‘0’ ‘0’ ‘0’ ‘1’ ‘0’ ‘1’ ‘1’
assume
LSB first
‘1’ ‘0’ ‘1’ ‘0’ ‘0’ ‘1’
‘1’ ‘0’ ‘0’
Second Byte
First Byte
11101000 = 0xE8
Some Remote function/manufacturer use biphase encoding; ‘1’
and ‘0’ have same period, but use different transition in middle of
the period (low-to-high or high-to-low).
‘0’
‘0’
‘0’
‘1’
‘0’
‘1’
‘1’
‘1’
00110010 = 0x32
Print first two bytes of frame to screen.
transition low-to-high is a ‘1’
transition high-to-low is a ‘0’
V 0.1
17
V 0.1
18
3
Experiment 12 Notes
Ensure that your assigned IR Remote function does NOT use
biphase encoding (must use space-width encoding).
Simply measure the time between falling edges – the first period
will be the start period, the periods after that will be either ‘1’ or
‘0’.
Compute the number of timer tics for a ‘1’ or ‘0’, and compare
what is measured. Use some slack, if you compute 2000 timer
ticks for a ‘0’, and 4000 for a ‘1’, then distinguish a ‘1’ as being
greater than 3000 tics.
You must compute an appropriate prescale for timer1 so that your
timer tics will have necessary fidelity to distinguish between ‘0’
and ‘1’.
V 0.1
19
4
Download