View previous topic :: View next topic |
Author |
Message |
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
NEC decoder |
Posted: Sat May 29, 2021 2:05 pm |
|
|
I have some code I’m working with for a Volume and relay control. It’s working as intended except for one thing. The momentary action of pins A0 and A1 only output less than a 1VDC, they mimic the IR receiver but don’t out put the max which should be around 5VDC. I can’t find anything in the code that would cause this. Bits A2~A5 are masked off from A0 and A1. Here is the code.
Code: |
// Extended NEC protocol IR remote control decoder using PIC12F1822 CCS PIC C code
// http://ccspicc.blogspot.com/
// [email protected]
// Use at your own risk
#include <12F1822.h>
#fuses NOMCLR INTRC_IO PLL_SW
#use delay(clock=32000000)
#use fast_io(A)
#define IR_Sensor PIN_A3
unsigned int32 ir_code;
short nec_remote_read(){
unsigned int16 count = 0;
unsigned int8 i;
// Check 9ms pulse (remote control sends logic high)
SET_TIMER1(0);
while(!input(IR_Sensor) && (count < 9500))
count = GET_TIMER1();
if( (count > 9499) || (count < 8500))
return FALSE;
// Check 4.5ms space (remote control sends logic low)
SET_TIMER1(0);
count = 0;
while((input(IR_Sensor)) && (count < 5000))
count = GET_TIMER1();
if( (count > 4999) || (count < 4000))
return FALSE;
// Read message (32 bits)
for(i = 0; i < 32; i++){
SET_TIMER1(0);
count = 0;
while(!input(IR_Sensor) && (count < 650))
count = GET_TIMER1();
if( (count > 649) || (count < 500))
return FALSE;
count = 0;
SET_TIMER1(0);
while((input(IR_Sensor)) && (count < 1800))
count = GET_TIMER1();
if( (count > 1799) || (count < 400))
return FALSE;
if( count > 1000) // If space width > 1ms
bit_set(ir_code, (31 - i)); // Write 1 to bit (31 - i)
else // If space width < 1ms
bit_clear(ir_code, (31 - i)); // Write 0 to bit (31 - i)
}
return TRUE;
}
void clear_volume(void)
{ output_low(PIN_A0);
output_low(PIN_A1);
}
void set_one(int8 pin)
{ output_low(PIN_A0);
output_low(PIN_A1);
if (pin!=2) output_low(PIN_A2);
if (pin!=4) output_low(PIN_A4);
if (pin!=5) output_low(PIN_A5);
if (pin==2) output_high(PIN_A2);
if (pin==4) output_high(PIN_A4);
if (pin==5) output_high(PIN_A5);
}
void main() {
setup_oscillator(OSC_8MHZ | OSC_PLL_ON); // Set internal oscillator to 32MHz (8MHz and PLL)
output_a(0);
set_tris_a(8);
SETUP_TIMER_1(T1_INTERNAL | T1_DIV_BY_8);
while(TRUE){
while(input(IR_Sensor)); // Wait until IR_Sensor pin falls
if(nec_remote_read())
{ // See if we recognise the code
if(ir_code == 0xFFA25D)
{ output_low(PIN_A1);
output_high(PIN_A0);
} else
if(ir_code == 0xFF629D)
{ output_low(PIN_A0);
output_high(PIN_A1);
} else
if(ir_code == 0xFFE21D)
{ set_one(2);
} else
if(ir_code == 0xFF22DD)
{ set_one(4);
} else
if(ir_code == 0xFF02FD)
{ set_one(5);
} else
{ clear_volume();
}
} else
{ clear_volume();
}
}
}
|
|
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Sat May 29, 2021 3:54 pm |
|
|
easy...
cut SIMPLE code to toggle those pins at say 2 hz( 2 seconds on, 2 seconds off),use 4k7 as the 'loads', now check with scope or DVM.
if that doesn't work, post THAT program... |
|
|
dyeatman
Joined: 06 Sep 2003 Posts: 1934 Location: Norman, OK
|
|
Posted: Sat May 29, 2021 4:02 pm |
|
|
What is the circuit wired to those pins?
These pins are the ICSP programming pins. _________________ Google and Forum Search are some of your best tools!!!! |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
Posted: Sat May 29, 2021 4:34 pm |
|
|
temtronic wrote: | easy...
cut SIMPLE code to toggle those pins at say 2 hz( 2 seconds on, 2 seconds off),use 4k7 as the 'loads', now check with scope or DVM.
if that doesn't work, post THAT program... |
At the moment I just have it in a test circuit setup with an LED and a 470 ohm resistor to ground on A0 and A1, the Voltage at the LED is less than 1V, when I press the button on the encoder for both PINS. |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Sat May 29, 2021 4:59 pm |
|
|
Please post your test program for the LED setup... |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
Posted: Sat May 29, 2021 5:25 pm |
|
|
Both shouldn’t blink like this, they should be steady on and off with each button depress and release. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Sat May 29, 2021 6:22 pm |
|
|
They only do what the program says to do....
You need to post your simple test program. |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
Posted: Sat May 29, 2021 7:35 pm |
|
|
temtronic wrote: | They only do what the program says to do....
You need to post your simple test program. |
Which Program? I’ve already posted the code and posted a video of the prototype! One can compile the code and try for themselves. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
Re: NEC decoder |
Posted: Sat May 29, 2021 8:56 pm |
|
|
Denny9167 wrote: | The momentary action of pins A0 and A1 only output less than a 1VDC, they mimic the IR receiver but don’t output the max which should be around 5VDC.
|
What if the IR code is sent multiple times ? Wouldn't they blink
several times ?
You said you measured the LED voltage at the LEDs. I see from your
video that you used a multimeter. The forward voltage drop of your
LEDs is probably around 2.2 volts. A digital waveform sent to the LEDs
will be 5v peak on the left side of the resistors. But on the right side
it will be 2.2v peak. But your multimeter will average the changing
waveform to be 1.1v. This assumes a 50% duty cycle. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Sun May 30, 2021 4:50 am |
|
|
re:
The simple one that ONLY tests the 2 I/O pins at a 2Hz toggle rate.
It is possible that either there's a basic hardware problem (wrong pin, solder whisker,wrong resistor value) or a simple code issue (internal peripheral conflict, wrong pin assignment).
Coding and running the 2Hz LED program can confirm if the hardware/code is correct. Unless you have an oscilloscope, you need to 'toggle' the I/O pins slowly as all DVMs heavily filter their input, so that you can read the LCD. A DVM cannot 'see' and display a fast changing signal.
Most PICs today have several uses for a pin, so you need to disable any internal peripherals that can use them, like ADC, comp,etc. Also when using fast_io(), be SURE you configure the pins right. I prefer to use 'binary', makes it easy to 'see' which pins are inputs (1) and outputs(0).
Jay |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
Posted: Sun May 30, 2021 6:07 am |
|
|
temtronic wrote: | re:
The simple one that ONLY tests the 2 I/O pins at a 2Hz toggle rate.
It is possible that either there's a basic hardware problem (wrong pin, solder whisker,wrong resistor value) or a simple code issue (internal peripheral conflict, wrong pin assignment).
Coding and running the 2Hz LED program can confirm if the hardware/code is correct. Unless you have an oscilloscope, you need to 'toggle' the I/O pins slowly as all DVMs heavily filter their input, so that you can read the LCD. A DVM cannot 'see' and display a fast changing signal.
Most PICs today have several uses for a pin, so you need to disable any internal peripherals that can use them, like ADC, comp,etc. Also when using fast_io(), be SURE you configure the pins right. I prefer to use 'binary', makes it easy to 'see' which pins are inputs (1) and outputs(0).
Jay |
Here is a video of a system I have going, with some code I have that was a
Collaboration between myself and a gentleman from the UK, it’s all ASM, I’m
Just an Analog guy so I’m still very new to programming. I’m only doing all this to learn C coding. I’ve tried outputting to different pins on the C code but
I run into the same phenomenon.
I’ve tried adding a delay after the “output_high” directive which does help but it’s very sloppy. It looks like the code needs a timer interrupt setup, in order for those outputs to time out properly, but I’m learning that side of C coding.
https://share.icloud.com/photos/0Ow_6QhtNZce3q5O_K5FyhOcA#Graham |
|
|
Denny9167
Joined: 15 Feb 2021 Posts: 49
|
|
Posted: Sun May 30, 2021 8:06 am |
|
|
One big differences I find between traditional ASM code and C in dealing with decoders, is in the beginning, IR commands are #defined as constants, and the incoming command is XOR'ed with the constant. The way this is setup, one has to enter a different command in order to change the state of the output PIN. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Sun May 30, 2021 10:18 am |
|
|
Whatever you do in ASM, can be done in C. CCS C has a LOT of 'functions' that are code efficient, and of course for 'time sensitive' needs you can always 'inline' ASM code.
I started with PICs and ASM was the only way to program them, then 25+- years ago found CCS, probably through Circuit Cellar Ink. I've never been formally taught in 'C' but all my code for all my projects and products has worked.
There's a learning curve, but CCS does supply LOTS of example programs, drivers and of course this forum. |
|
|
|