|
|
View previous topic :: View next topic |
Author |
Message |
winson
Joined: 03 Dec 2008 Posts: 24
|
UART Transmitting Problem |
Posted: Wed Dec 03, 2008 11:46 am |
|
|
Hello everybody,
I was trying to write a UART program to send out few bytes of data by using PIC16F877A, CCS C compiler, MPLAB IDE, MPLAB SIM. The problem of my program is the code fail to transmit out the data to pin RC6 of Port C. So far i am just use MPLAB SIM to simulate my program and using Watch window to monitor all the register and symbol. To simulate the program i was pressing the "step into" button, and the first 2 bytes of data was load to TXREG and TSR but after that not able to load the third bytes of data beacuse TXIF flag is not set, this showing that TXREG was still full and the data look like "jam" already. from the Watch window the Port C does not show any value(0x00), i also try to press "animate" and let the program run for few minutes but still no data was show on Port C. Anybody can help to solve the problem or give some suggestion?
Below is my program,
Code: |
#include <16F877A.h>
//***** Function prototype ******//
void init(void);
void transmit (void);
void transmit_empty (void);
//*****variable declaration******//
unsigned char TXSTA,RCSTA,SPBRG,INTCON,PIR1,PIE1,TXREG,PORTC,TRISC;
int count;
//****** define sfr address *****//
#byte TXSTA = 0x98
#byte RCSTA = 0x18
#byte SPBRG = 0x99
#byte PIE1 = 0x8c
#byte INTCON = 0x8b
#byte TXREG = 0x19
#byte RCREG = 0x1A
#byte PIR1 = 0x0c
#byte PORTC = 0x07
#byte TRISC = 0x87
char ucIPOD_packet_origin[2][7]={
{0xff,0x55,0x03,0x02,0x00,0x01,0xfa}, /* " play/pause " */
{0xff,0x55,0x03,0x02,0x00,0x08,0xf3} /* " fwd " */
};
/********************************************************************
FUNCTION : main()
DESCRIPTION : main loop
INPUT : Null
OUTPUT : Null
CREATE :
DATE : 07/10/08
********************************************************************/
void main()
{
init ();
transmit ();
while (1)
{
}
}
/********************************************************************
FUNCTION : init()
DESCRIPTION : sfr initialization
INPUT : Null
OUTPUT : Null
CREATE :
DATE : 07/10/08
********************************************************************/
void init ()
{
PORTC = 0x00; //0b 0000 0000 //Clear Port C
TRISC = 0xFF; //0b 1111 1111 //Enable USART Transmitter
TXSTA = 0x24; //0b 0010 0100 //Transmit Enable //SYNC = 0, Asynchronous Mode
RCSTA = 0x90; //0b 1001 0000 //Receive Enable //Serial Port Enable
SPBRG = 0x40; //0b 0100 0000 //SPBRG = 64, Baudrate = 19.231KBAUD, High Baud Rate
INTCON = 0x00; //0b 0000 0000 //Disable Global and Peripheral Interrupt
PIR1 = 0x10; //0b 0001 0000 //USART transmit/Receive Interrupt Flag bit
PIE1 = 0x00; //0b 0000 0000; //Individual enable bits for the peripheral interrupts.
count = 0;
}
/********************************************************************
FUNCTION : transmit()
DESCRIPTION : uart transmission
INPUT : Null
OUTPUT : Null
CREATE :
DATE : 07/10/08
********************************************************************/
void transmit ()
{
while (1) //Keep on looping
{
if (PIR1 == 0x10) //Check TXIF flag
{ //If TXREG is empty
TXREG = ucIPOD_packet_origin[0][count]; //Load
data
count++; //Counter increment
}
}
}
|
I am really no idea why such condition happen, everything look like set properly but it is not run.
Is it my simualtion methods is wrong or my code was having problem?
Any suggestion is appreciate.
Thanks |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Wed Dec 03, 2008 12:43 pm |
|
|
You don't have to do all this stuff in CCS. Please download the manual
and look at the example programs, and read the forum. The program
below shows how to send a string out the serial port with CCS.
Please re-write your program, using CCS methods.
Code: |
#include <16F877A.H>
#fuses XT, NOWDT, NOPROTECT, BROWNOUT, PUT, NOLVP
#use delay(clock=4000000)
#use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7, ERRORS)
//======================================
void main()
{
printf("Hello World\n\r");
while(1);
} |
See this post for instructions on how to use the "UART1" feature of
the MPLAB simulator to display printf output in MPLAB:
http://www.ccsinfo.com/forum/viewtopic.php?t=23408&start=1 |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Thu Dec 04, 2008 12:52 pm |
|
|
I already successfully simulate my UART program by using Uart1 IO tab in MPLAB SIM. Press "run" to simulate the UART program and the transmitted data will show in output window as ASCII character, just have to refer ASCII table and verify the transmitted data.
Thanks everybody!
Special Thanks to ! PCM programmer ! |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Wed Dec 31, 2008 11:11 am |
|
|
Hi everybody.
I already try my UART transmiting program on the real hardware with a breadboard but the result is not successful. I was using an oscilloscope to trace the signal that send out from the USART Tx pin of 16F877A but the scope does not show any pulses and just maintain at 0V. This program is run well in MPLAB Simulation.
The peripheral circuitry of the 877A is simple, i was put the 20MHz crystal's leg to OSC1 and OSC2 with a 22pF capacitor from each crystal leg to ground. I connect 5V(3A) supply to the two VDD pin of 877A and 0V to the two VSS pin finally i also connect 5V supply to the MCLR pin for the reset purpose and i also try to put a 20k resistor to the VDD to limit the current but the result is still the same. This is all the thing that i do, but the scope does not show any digital pulses. Anybody can give me some suggestion or alert me some of the error that i done?
My latest version of code is show below, Thanks...
Code: |
#include <16F877A.h>
//***** Function prototype ******//
void init(void);
void transmit (void);
//*****variable declaration******//
unsigned char TXSTA,RCSTA,SPBRG,INTCON,PIR1,PIE1,TXREG,PORTC,TRISC;
int count, next;
//****** define sfr address *****//
#byte TXSTA = 0x98
#byte RCSTA = 0x18
#byte SPBRG = 0x99
#byte PIE1 = 0x8c
#byte INTCON = 0x8b
#byte TXREG = 0x19
#byte RCREG = 0x1A
#byte PIR1 = 0x0c
#byte PORTC = 0x07
#byte TRISC = 0x87
#bit TXIF = PIR1.4
#bit TRMT =TXSTA.1
char remote_command_basic[3][10]=
{
{0xff,0x55,0x06,0x02,0x00,0x01,0x00,0x00,0x00,0xf7}, //0 Play/Pause
{0xff,0x55,0x06,0x02,0x00,0x01,0x00,0x00,0x00,0xf7}, //1 Play/Pause
{0xff,0x55,0x06,0x02,0x00,0x00,0x00,0x00,0x00,0xf8} //2 Button Release
};
/*****************************************************************************
FUNCTION : main()
DESCRIPTION : main loop
*****************************************************************************/
void main()
{
init ();
transmit ();
while (1)
{
}
}
/*****************************************************************************
FUNCTION : init()
DESCRIPTION : sfr initialization
*****************************************************************************/
void init ()
{
//#use delay(clock = 20000000)
//#use rs232(baud=19200,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8,errors)
PORTC = 0x00; //0b 0000 0000 //Clear Port C
TRISC = 0xFF; //0b 1111 1111 //Enable USART Transmitter and Receiver
TXSTA = 0x24; //0b 0010 0100 //Transmit Enable //Asynchronous
RCSTA = 0x90; //0b 1001 0000 //Receive Enable //Serial Port Enable
SPBRG = 0x40; //0b 0100 0000 //SPBRG=64, 19.231KBAUD, High Baud Rate
INTCON = 0x00; //0b 0000 0000 // Interrupt Disable
PIR1 = 0x10; //0b 0001 0000 //USART Interrupt Flag bit
PIE1 = 0x00; //0b 0000 0000; // peripheral interrupts.
count = 0;
next = 0;
}
/******************************************************************************
FUNCTION : transmit()
DESCRIPTION : uart transmission
******************************************************************************/
void transmit ()
{
while (1) //Keep on looping
{
if (TXIF == 1) //Check TXIF flag
{ //If TXREG is empty
TXREG = remote_command_basic[next][count]; //Load data
delay_cycles( 1 ); //NOP
delay_cycles( 1 );
delay_cycles( 1 );
if (count > 8) //After 10th byte
{
next++; //Next packet
if (next > 2) //After 3rd packet
{
return; //Return to main()
}
}
count++; //Counter increment
if (count > 9) //After 10th byte
{
count = 0; //Reset counter
}
} //End first if loop
} //End while loop
}
| [/code] |
|
|
ckielstra
Joined: 18 Mar 2004 Posts: 3680 Location: The Netherlands
|
|
Posted: Wed Dec 31, 2008 1:06 pm |
|
|
Start with something simple and only when that works extend it with a new part and test again. Repeat this process until your application is finished.
Starting with a (relative) large program makes it hard to find the problem.
Code: | //****** define sfr address *****//
#byte TXSTA = 0x98
#byte RCSTA = 0x18
#byte SPBRG = 0x99
#byte PIE1 = 0x8c
#byte INTCON = 0x8b
#byte TXREG = 0x19
#byte RCREG = 0x1A
#byte PIR1 = 0x0c
#byte PORTC = 0x07
#byte TRISC = 0x87
#bit TXIF = PIR1.4
#bit TRMT =TXSTA.1 | This is how an assembly programmer would write a program. In the CCS C-compiler none of these are required and can be replaced by a more readable and portable C command.
for example: Code: | if (TXIF == 1) //Check TXIF flag
{ //If TXREG is empty
TXREG = remote_command_basic[next][count]; //Load data
| is equivalent to: Code: | putc( remote_command_basic[next][count] ); |
Most likely your program doesn't work because of an error in the RS-232 setup (hint: are you sure all port-C pins need to be inputs?)
A good starting point is the program as posted by PCM. Have you tried this on your hardware and does it work? |
|
|
Ttelmah Guest
|
|
Posted: Wed Dec 31, 2008 4:35 pm |
|
|
Also,
"I see no fuses". The chip is not going to work without these programmed....
PCM Programmers code shows exactly what is needed to get the chip running.
Also, no mention of a decoupling capacitor close to the PIC. Though you will sometimes (rarely) get away without this, it really should be there.
Best Wishes |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Mon Jan 05, 2009 8:55 am |
|
|
Hi everybody i have spend few days to work for my project, and the results is no output again plus two of my PIC16F877A damaged. This project really give me a big challenge! Now the work is stop and have to wait for the new processor to reach...
ckielstra wrote: | Start with something simple and only when that works extend it with a new part and test again. Repeat this process until your application is finished.
Starting with a (relative) large program makes it hard to find the problem.
|
Thanks for this advice
I have try to write a small program to flash an output pin for "high" and then "low", but after i test it on the controller the pin does not show any output from oscilloscope, i think may be pulse width of the "high" is too short in time thus the scope cant show the digital pulse, later when the new processor reach i will try to make the "high" pulse to 1 sec then 1 sec "low".
Quote: |
This is how an assembly programmer would write a program. In the CCS C-compiler none of these are required and can be replaced by a more readable and portable C command.
|
Now i was spending some time to read thru in detail the ccs manual, but so far i just know how to use ccs method to setup UART, make delay, use putc to transmit data, but i think the non ccs method also can work because the program was work well in MPLAB SIM simulation, but anyway i will try my best to transform my code to CCS form.
Quote: |
Most likely your program doesn't work because of an error in the RS-232 setup (hint: are you sure all port-C pins need to be inputs?)
|
From the data sheet of PIC16F877A there are one section say that the TRISC6 and TRISC7 need to be "set" in order to configure it as USART Tx and Rx pin. So for simplicity i just set all PORTC pins to input.
Quote: |
Bit SPEN (RCSTA<7>) and bits TRISC<7:6> have to be
set in order to configure pins RC6/TX/CK and RC7/RX/DT
as the Universal Synchronous Asynchronous Receiver
Transmitter.
|
This sentence i get it from page 111 of the data sheet, the "set" in the sentence i was not sure whether it is means set to "high" or just simply means set them to either become input or output that is means configure it but not set to "high". Some body said both RC6 and RC7 need to be set as input but there are also people say need to set RC6 as output then RC7 as input. Later when the processor reach i will test both. Any body have comment about this?
Thanks a lot!
Last edited by winson on Mon Jan 05, 2009 9:41 am; edited 1 time in total |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Mon Jan 05, 2009 9:28 am |
|
|
Ttelmah wrote: | Also,
"I see no fuses". The chip is not going to work without these programmed....
PCM Programmers code shows exactly what is needed to get the chip running.
Also, no mention of a decoupling capacitor close to the PIC. Though you will sometimes (rarely) get away without this, it really should be there.
Best Wishes |
Thanks
I think the difference between my code and PCM is the #fuses so I have modified my UART setup section as below
Code: |
#use delay(clock = 20000000)
#fuses HS, NOWDT, NOLVP, NOPROTECT, BROWNOUT, NOPUT
#use rs232(baud=19200,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8,errors)
|
During the time when i download this program to my controller chip, i found out that there is one configuration tap in the programmer software that also allow us to choose the setting just what the #fuses can do, then i was also choose some setting from this programmer software, may be because of double-setting in the configuration bit by both the #fuses and the programmer software, when the downloading process reach 50% the process was stop and show "error 2100".
Later, no matter what program or what configuration bit i putting in to the controller, the chip also fail to program and every time also showing "error 2100", it look like the controller already damaged or locked, after that i also try doing the same thing to my second processor and then it also become damaged, may be because of double-choosing of configuration bit.
Anybody can give me some comments on this?
Thanks in advance. |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Mon Jan 05, 2009 9:36 am |
|
|
Regarding the de-coupling capacitor, before the 16F877A controller chip is damaged, i was try it with a controller which is downloaded with a non #fuses program, for that, the controller does not giving any output. Later when the new controller reach i will put a de-coupling capacitor and test with a #fuses program.
Thanks for that. |
|
|
winson
Joined: 03 Dec 2008 Posts: 24
|
|
Posted: Fri Jan 16, 2009 7:44 pm |
|
|
After the new processor come, i have immediately add the following code line to my program
#fuses hs, nowdt, nolvp, noprotect
and the program is working finally, all data was able to send out. |
|
|
|
|
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
|