|
|
View previous topic :: View next topic |
Author |
Message |
nuno12345
Joined: 16 Jul 2008 Posts: 50
|
Help with serial communication |
Posted: Sun Aug 22, 2010 1:57 pm |
|
|
Hello,
I have 2 pics, for now I'm testing the communication between both, in the future I will implement a RF Link.
My code:
16F88(receiver):
Code: | #include <16F88.h>
#fuses INTRC_IO, NOWDT, NOPUT, NOBROWNOUT, NOMCLR, NOLVP, NOPROTECT
#use delay(clock=8000000)
#use rs232(baud=9600,xmit=PIN_B5,rcv=PIN_B2,parity=N,bits=8,ERRORS,STREAM=COM_A)
unsigned int8 data;
int1 flag=0;
#int_rda
void rd_isr(void)
{
disable_interrupts(INT_RDA); // Disable Serial Recieve Interrupt
disable_interrupts(GLOBAL); // Disable Global Interrupts
data= fgetc(COM_A);
if(data=='T')
{
flag=1;
}
enable_interrupts(GLOBAL);
enable_interrupts(INT_RDA);
}
void main()
{
enable_interrupts(global);
enable_interrupts(int_rda);
while(true)
{
if(flag==1)
{
output_high(PIN_B1);
delay_ms(100);
output_low(PIN_B1);
delay_ms(100);
flag=0;
}
else
{
delay_ms(100);
delay_ms(20);
fputc('T',COM_A);
delay_ms(20);
delay_ms(100);
}
output_high(PIN_B0);
delay_ms(100);
output_low(PIN_B0);
delay_ms(100);
}
}
|
16F628A(transmitter):
Code: | #include <16F628A.h>
#fuses INTRC_IO, NOWDT, NOPUT, NOBROWNOUT, NOMCLR, NOLVP, NOPROTECT
#use delay(clock=8000000)
#use rs232(baud=9600, xmit=PIN_B2, rcv=PIN_B1, ERRORS)
void main()
{
while(1)
{
delay_ms(20);
putc('T');
delay_ms(20);
output_high(PIN_B0);
delay_ms(100);
output_low(PIN_B0);
delay_ms(100);
}
}
|
Both LED's flash so I know both PIC's are working properly, but when I connect 16F628A PIN B2 to 16F88 PIN B2 LED B1 does not flash, although if I connect 16F88 PIN B5 to B2 it works.
Help?
Thanks |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Sun Aug 22, 2010 2:14 pm |
|
|
I didn't look closely at your code, but I have these comments:
Quote: |
#int_rda
void rd_isr(void)
{
disable_interrupts(INT_RDA); // Disable Serial Recieve Interrupt
disable_interrupts(GLOBAL); // Disable Global Interrupts
data= fgetc(COM_A);
if(data=='T')
{
flag=1;
}
enable_interrupts(GLOBAL);
enable_interrupts(INT_RDA);
}
|
Delete the lines shown in bold. It's either not needed (INT_RDA) or
wrong (GLOBAL). The compiler and the PIC hardware handle all of
this for you.
Also, when you connect the Tx to the Rx between the two PICs, do you
also have a ground connection between the two boards ? You need one. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19499
|
|
Posted: Sun Aug 22, 2010 3:02 pm |
|
|
And particularly, 'enable_interrupts(GLOBAL)', must _never_ be used inside a PIC interrupt handler. It is _lethal_ to the code, to do so.
The problem here is that the PIC does not support interrupts interrupting themselves. There is quite a bit more to the interrupt handler that happens after you return from the code you have written. As PCM programmer says, the PIC _hardware_ re-enables the interrupts when you actually return from the handling code. By enabling them earlier, you can cause interrupts to be acccepted before you return, which _will_ result in data being corrupted, killing the program.
Seperately though think how often characters may arrive, and how long your loop takes. Make your loop faster than the expected time between characters, and wait for one to arrive. Currently, the loop in your slave, takes 400mSec if 'T' has been seen, and 440mSec, if not. The 'master' is sending a character every 240mSec, so how can the slave expect to keep up?. This in fact makes the above problem _certain_ to cause problems, since two characters can be waiting in the hardware buffers, there will be a second interrupt when you enable the interrupts inside the handler, and a crash will result...
Best Wishes |
|
|
nuno12345
Joined: 16 Jul 2008 Posts: 50
|
|
Posted: Tue Aug 24, 2010 11:44 am |
|
|
Thank you both
Ok, I will remove those lines from my code.
PCM both pics share the same supply.
I fixed the problem in a simulator, I'm using 16F88 and 16F628A, I tested the transmitter code on both pics, in 16F88 it was working but it wasn't in 16F628A, I realized that if I changed the baud rate to half it was working, so I thought in the clock, I changed pic's 16F628A clock to 4M and it worked .
Now I got another problem, a bit off topic but, I don't know why but it seems some of my PIC's stop working randomly, they won't even start.
In 16F88 I can't even run the simplest code, the PIC won't start, but its as simple as leave it alone or sometimes reprogram it with the same code and it works :/.
Also another problem with this PIC is that the programmer only detects it once, but I cant program it, if I "ask" the programmer to identify the PIC again it says UNKNOWN
In 12F675 if I disconnect and reconnect the supply, sometimes it runs. Also it seems to run with different clocks even if its the same exact program, the test I did was just to make a LED flash and sometimes it flashes faster than others.
16F628A does not have any problem at all, it starts first time.
Fuses maybe?
Last edited by nuno12345 on Tue Aug 24, 2010 12:07 pm; edited 1 time in total |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Tue Aug 24, 2010 12:06 pm |
|
|
1. Enable the Brownout fuse.
2. Enable the Power-Up Timer fuse (PUT).
3. If you have MCLR enabled, make sure you have a pull-up resistor on it.
Use 10K for Microchip ICD2, or 47K for CCS ICD-U40.
4. Make sure you have a 100 nF ceramic capacitor between each Vdd pin
on the PIC and ground. Place the cap very close to the chip.
5. Make sure you have a clean, solid, correct Vdd voltage for the PIC.
6. If using a crystal, make sure you have the correct value of caps
installed in the crystal circuit. (22 pf will work for 4 MHz to 20 MHz). |
|
|
nuno12345
Joined: 16 Jul 2008 Posts: 50
|
|
Posted: Tue Aug 24, 2010 3:53 pm |
|
|
Looks like the fuse PUT is doing something to the PIC.
my code:
Code: | #include <12F675.h>
//#device ADC=10
#fuses INTRC_IO, NOWDT, PUT, NOBROWNOUT, NOMCLR, NOPROTECT
#use delay(clock=4000000)
#use rs232(baud=9600, xmit=PIN_A1, rcv=PIN_A2, ERRORS,STREAM=COM_A)
void main()
{
while(1)
{
output_high(PIN_A0);
delay_ms(100);
output_low(PIN_A0);
delay_ms(100);
}
} |
When I have the fuse PUT enabled I can only get it to work if I disconnect the supply and reconnect it really fast. Also, when it works looks like the clock changed.
With NOPUT it only works sometimes and when it does work looks like everything is alright, timings etc... |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Tue Aug 24, 2010 4:14 pm |
|
|
What's your Vdd voltage on the PIC ? What device is supplying it ?
Is it a bench power supply ? Or a voltage regulator I.C. ? Or a
debugger ?
I notice you still have the NOBROWNOUT fuse.
You should add BROWNOUT, and do everything on my list. |
|
|
nuno12345
Joined: 16 Jul 2008 Posts: 50
|
|
Posted: Tue Aug 24, 2010 5:03 pm |
|
|
I did, I tested every single fuse, no difference.
Hmm, probably you wont like it :P my supply is the computer USB |
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|