CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

PIC18F26K22 + 2 PORT RS232 + INT

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
ALCION



Joined: 31 May 2007
Posts: 16

View user's profile Send private message

PIC18F26K22 + 2 PORT RS232 + INT
PostPosted: Sun Jan 18, 2015 8:44 pm     Reply with quote

hi, in a project need to use 2 RS232 serial ports used a PIC16F886 and had hw port and another sw but I want to try with 2 ports for hw.

Anyone have any example of how to configure the two RS232 hw ports and which interrupts use?

I see that there is only one Int_RDA I can not use Int_RDA1

I use MPLAB 8.80 and CCS vr 4,140

Thank You! Wink
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Jan 18, 2015 9:27 pm     Reply with quote

This post has an example of using #int_rda2:
http://www.ccsinfo.com/forum/viewtopic.php?t=44394&start=14
ALCION



Joined: 31 May 2007
Posts: 16

View user's profile Send private message

PostPosted: Sun Jan 25, 2015 5:25 pm     Reply with quote

Thanks PCM programmer and excuse the delay in responding but was testing, the example you send me works well, but still have problems using two rs232, I use a pic18f26k22 and each serial port I connect to a lap top via a USB-RS232 converter.
The problem is that it is frozen and does not send any data.
you have any example where hw 2 serial ports are used?
Thanks for the support.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Sun Jan 25, 2015 7:14 pm     Reply with quote

Explain what you are doing, in detail.

Do you have two USB-to-RS232 converter cables ?
Is each cable connected to a different USB connector on your laptop ?
Does each cable connect to a MAX232 chip on your PIC board ?

What software are you using on the laptop ? Are you running two
instances of TeraTerm simultaneously, with each one configured for
a different COMx port ?

How do you know what ports the USB-to-serial converters are using ?
Have you checked in Windows Device Manager to see what COM ports
have been assigned to the USB-to-Serial converters ?

The above is my guess of your test setup. If it's not true, then you need
to describe the actual setup in detail.
Ttelmah



Joined: 11 Mar 2010
Posts: 19539

View user's profile Send private message

PostPosted: Mon Jan 26, 2015 2:13 am     Reply with quote

This was originally written in a V4 compiler. Now using V5.
Code:

//your processor include and fuses here
//your clock setup here

#use rs232(baud=9600,parity=N,UART1,bits=8,stream=PORT1,errors) //U1
#use rs232(baud=57600,parity=N,UART2,bits=8,stream=PORT2,errors) //U2

//This is using Uart1 at 9600bps, and Uart2 at 57600bps

//Buffer tests and handling - actually in a separate file 'serial_buffer.h' for me
char btempU1RX,btempU2RX,btempU1TX,btempU2TX;
#define SIBUFF (32) //buffer sizes
typedef struct {
   unsigned int8 in;
   unsigned int8 out;
   char buff[SIBUFF];
} buffer; //definition of a 'buffer' data type
buffer U1RX,U1TX,U2RX,U2TX; //four 32byte buffers

//macros to handle the buffer operations
#define incin(buff) ((buff.in==(SIBUFF-1))?0:buff.in+1)
#define incout(buff) ((buff.out==(SIBUFF-1))?0:buff.out+1)
#define isempty(buff) (buff.in==buff.out)
#define hasdata(buff) (buff.in!=buff.out)
#define isfull(buff) ((incin(buff)==buff.out)
#define tobuff(bname,c) { bname.buff[bname.in]=c;\
   bname.in=incin(bname);\
   if (bname.in==bname.out) bname.out=incout(bname);\
   }
#define frombuff(bname) (btemp##bname=bname.buff[bname.out],\
   bname.out=incout(bname), \
   btemp##bname)
//note the building of the temporary variable name here
#define clrbuff(buff) buff.in=buff.out=0

#define bkbhit(BUFF) hasdata(BUFF)
#define bgetc(BUFF) frombuff(BUFF);

void U1putc(int chr)
{
   tobuff(U1TX,chr);
   enable_interrupts(INT_TBE);
}

void U2putc(int chr)
{
   tobuff(U2TX,chr);
   enable_interrupts(INT_TBE2);
}

//Interrupt code
#INT_RDA
void uart1rx(void)
{
   char temp;
   temp=fgetc(PORT1);
   tobuff(U1RX, temp); //save character to circular buffer
}

#INT_RDA2
void uart2rx(void)
{
   char temp;
   temp=fgetc(PORT2);
   tobuff(U2RX, temp);
}

#INT_TBE
void uart1tx(void)
{
   char temp;
   temp=bgetc(U1TX);
   fputc(temp,PORT1);
   if (isempty(U1TX)) disable_interrupts(INT_TBE);
   //stop INT_TBE if nothing left to send
}

#INT_TBE2
void uart2tx(void)
{
   char temp;
   temp=bgetc(U2TX);
   fputc(temp,PORT2);
   if (isempty(U2TX)) disable_interrupts(INT_TBE2);
   //as above for INT_TBE2
}

//Then the main
void main(void)
{
    char temp;
    //Again this is in fact in an include file 'init' routine
    clrbuff(U1RX);
    clrbuff(U2RX);
    clrbuff(U1TX);
    clrbuff(U2TX); //initialise the four buffers
    //Now enable the RX interrupts
    enable_interrupts(INT_RDA);
    enable_interrupts(INT_RDA2);
    enable_interrupts(GLOBAL);

    //To write to UART1:
    printf(U1putc,"Message to the first UART\n\r");
    //To write to UART2:
    printf(U2putc,"Message to second UART\n\r");
    //Understand that _both_ these message will now be transmitting
    //at the same time, from the buffers.

    while (TRUE)
    {
        if (bkbhit(U1RX))
        {
           //Here data has been received on UART1
           temp=bgetc(U1RX);
           U1putc(temp); //echo it back
        }
        if (bkbhit(U2RX))
        {
           //Here there is data on UART2
           temp=bgetc(U2RX);
           U2putc(temp); //echo it back
        }
     }
}

This illustrates the key points. _everything_ needs to be buffered. Problem is that unless this is done, if (for instance) you go and transmit a message on UART1, then UART2 is idle while you do this transmission. If you sit waiting for data on UART1, then you will miss things on UART2 while doing this. etc. ect.. You need to be receiving, and transmitting using the interrupts and each interrupt routine must return ASAP, or another channel may miss being service.
These routines throw the oldest character, if a buffer overflows.
The comments about getting out of the interrupt quickly, also apply to any 'other' interrupts you are running. Timers etc.. You need to always make sure that interrupts are serviced faster than the time between any possible combination of sequential characters arriving. Also that things in your main code, do not result in interrupts being disabled. There was a bug in the early V5 compilers, that may have existed in the late V4's (haven't checked your version), with 'printf' resulting sometimes in GIE being disabled. Add the line 'enable_interrupts(GLOBAL);' after every call to printf if you think you might have this.
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
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