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

reading the pin
Goto page 1, 2, 3  Next
 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
TT
Guest







reading the pin
PostPosted: Sun Oct 11, 2009 2:38 am     Reply with quote

Hey all, I'm really sorry but I'm getting stuck on something really simple and I can't figure out where I'm going wrong.

I'm using a pic16f690 and one of its pins (PIN_C1) is programmed to go HIGH every few seconds. Just quickly.

I have verified this with a multimeter and the osc and it does go high. Meanwhile, I've programmed the PIC to read this input and light up an led. But the led doesn't light up at all. I've also programmed the PIC to send info up to the computer if it detects pin C1 at high at any stage. Even this doesn't happen.

Is there something I am overlooking?

My simple code is below
Code:

#include <16F690.h>

#fuses INTRC, NOWDT, NOPROTECT, BROWNOUT, PUT
#use delay(clock = 4000000)
#use rs232(baud=19200, xmit=PIN_B7, rcv=PIN_B5)

void main()
{
   set_tris_c(0b00100111);
   setup_adc_ports(NO_ANALOGS);     //Port A/C all digital outputs

 for(;;){
   
   contact_slave3();

         if(input(PIN_C1) == 1){
             printf("\r\nValid RF Message from Slave 3 received\r\n");   
         }
         
   delay_ms(1000);
   }

}

contact_slave3 is a simple function that uses rf to get pin_c1 to high. That bit works. Is there something about C1 I should know ?

Thanks all.
TT
Guest







PostPosted: Sun Oct 11, 2009 2:41 am     Reply with quote

sorry, in the above code, theres meant to be a part on lighting the relevant LED. i removed it while debugging. so just imagine that bits in there and working.
Ttelmah
Guest







PostPosted: Sun Oct 11, 2009 3:16 am     Reply with quote

The 'odds' are you are just missing it....
You send this 'contact_slave3' command (which you don't show), and presumably the pin is meant to go high at some interval after this. You then test the pin just once, immediately after returning from this, and if it is high, print your message, but if it is not high, _at the exact instant you read the pin_, you pause for a second, and go round again.
So, unless the pin is actually high at the exact moment you test it, you will miss it.
Is the pin just going high at an interval (as you imply), or does it go high in response to the 'contact slave' command?. If the latter, how long after the command is sent, does the event happen?.
You probably need something like:
Code:

int16 ctr; //at the start of main


 for(;;){
     contact_slave3();
     //Now wait for about 1/10th second to see if there is a response:
     for (ctr=0;ctr<8000;ctr++) {
        if(input(PIN_C1)) {
            ctr=0;
            break;
        }
    }
    if (ctr==0)
        printf("\r\nValid RF Message from Slave 3 received\r\n"); 
    delay_ms(1000);
 }

The 'ctr' loop, will probably take about 10 to 15uSec to execute at 4MHz, so looping 8000 times, will be somewhere in the order of 1/10th second. If a 'high' is seen, it'll exit with ctr cleared, otherwise ctr will be 8000 at the exit. So if ctr is zero, then a 'high' was seen, and your message is printed.
The odds are that the slave takes some time to respond to the command, and the line doesn't go high in time for your test.

Best Wishes
hobby_85



Joined: 17 Aug 2009
Posts: 50

View user's profile Send private message

hey
PostPosted: Sun Oct 11, 2009 5:21 am     Reply with quote

hey tlmah,

thanks so much. i know the mistake i was makin. it works now

thanks again
hobby_855
Guest







timer
PostPosted: Sun Oct 11, 2009 6:16 am     Reply with quote

ttelmah,

if I were to start the timer when the pin went high, and stopped it when another pin went high, would this be ok? the other input is on C5, so im trying to use the CCP capabilities of the PIC.

this is what Ive got so far:

Code:


#int_ccp1
setup_ccp1(CCP_CAPTURE_RE);   //configure pin to capture rise on pin C5

contact_slave3();

for (ctr=0;ctr<16000;ctr++) {        //Wait till timeout
            if(input(PIN_C1)) {
               ctr=0;
               break;
            }
}
   
 
 if (ctr==0){     
         setup_timer_1(T1_INTERNAL);      //start timer 1
         received_US = CCP_1  ;              //stores the timer value into received_US when rising edge is detected
         
// *at this point, I need to take the difference in timer values, but am getting confused on how to do so*//

   }else{
        printf("\r\nSlave 3 is uncontactable\r\n");
      }



could you lead me in the right direction with regard to this. Im getting confused on how to start the timer when pin c1 is high, and stop when pin c5 (ccp pin) is high.

thanks again.
bungee-



Joined: 27 Jun 2007
Posts: 206

View user's profile Send private message

PostPosted: Sun Oct 11, 2009 7:03 am     Reply with quote

Why do you want to start/stop the timer? Do you need a measurmet for how long some event took.

Then you can do that in a few ways. One is to wait until the first signal appears and then set corresponding timer to 0 and then wait for another signal and then you just read the value of the timer (no need to start/stop).

Another way would be use of CCP module, but not in a way you wrote it.

The best thing would be that you specify what you want to achieve and we can give you advice/code ... Wink
Guest








PostPosted: Sun Oct 11, 2009 7:55 am     Reply with quote

bungee- wrote:
Why do you want to start/stop the timer? Do you need a measurmet for how long some event took.

Then you can do that in a few ways. One is to wait until the first signal appears and then set corresponding timer to 0 and then wait for another signal and then you just read the value of the timer (no need to start/stop).

Another way would be use of CCP module, but not in a way you wrote it.

The best thing would be that you specify what you want to achieve and we can give you advice/code ... Wink


hey bungee, thanks for the tip. yes, i am trying to find the time between the two pins (c1 and c5) getting high.

im using a pic16f690 so only c5 has a ccp module, and im getting confused on how to use the timer and ccp together. (just so i get a more accurate reading)

how to i go about doing this?

thanks heaps
Guest








PostPosted: Sun Oct 11, 2009 7:56 am     Reply with quote

In the meanwhile, I'll trying writing code for the other way....setting the timer to 0 and reading it again.

Thanks heaps
bungee-



Joined: 27 Jun 2007
Posts: 206

View user's profile Send private message

PostPosted: Sun Oct 11, 2009 2:42 pm     Reply with quote

If you are not tied to ports, you could use port A/B so you can use "on change" interrupt. That would improve accuracy.

Another option would be use RA2/INT (external interrupt in CCS) for first signal. In ISR for that interrupt you just set timer1 to zero and arm the CCP interrupt. When CCP interrupt would happen you read the value in CCP register save it to your variable and raise the event flag, so the main part of program would know that something happened etc.

Here is the code, that I think can be usefull to you. First signal is inputed in RA2 and the second on RC5.

Code:
#include <16F690.h>
#device adc=8

#FUSES NOWDT                    //No Watch Dog Timer
#FUSES INTRC_IO                 //Internal RC Osc, no CLKOUT
#FUSES NOPROTECT                //Code not protected from reading
#FUSES NOBROWNOUT               //No brownout reset
#FUSES NOMCLR                   //Master Clear pin used for I/O
#FUSES NOCPD                    //No EE protection
#FUSES PUT                      //Power Up Timer
#FUSES NOIESO                   //Internal External Switch Over mode disabled
#FUSES NOFCMEN                  //Fail-safe clock monitor disabled

#use delay(clock=8000000)
#use rs232(baud=9600,parity=N,xmit=PIN_B7,rcv=PIN_B5,bits=8,errors)

int tripped=0;
int16 value=0;

#int_EXT
void  EXT_isr(void)
{
   set_timer1(0);
   tripped=0;
   value=0;
   enable_interrupts(INT_CCP1);
   disable_interrupts(INT_EXT);
}

#int_CCP1
void  CCP1_isr(void)
{
   value=CCP_1;
   disable_interrupts(INT_CCP1);
   enable_interrupts(INT_EXT);
   tripped=1;
}



void main()
{

   setup_adc_ports(NO_ANALOGS|VSS_VDD);
   setup_adc(ADC_OFF);
   setup_spi(SPI_SS_DISABLED);
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
   setup_timer_1(T1_INTERNAL|T1_DIV_BY_1);
   setup_timer_2(T2_DISABLED,0,1);
   setup_ccp1(CCP_CAPTURE_RE);
   setup_comparator(NC_NC_NC_NC);
   enable_interrupts(INT_EXT);
   enable_interrupts(GLOBAL);
   setup_oscillator(OSC_8MHZ);

while (1)
{
   if (tripped)
   {
      printf("Value is: %Lu",value);
      tripped=0;
   }
}

}
HOBBY_885
Guest







PostPosted: Sun Oct 11, 2009 9:55 pm     Reply with quote

hey bungee, thanks for your help.

Unfortunately, my ports are tied, so I'm stuck with C1 and C5. But I do understand what your trying to do.

I guess the only other option is to set timer to 0 when the first high signal is received and check its contents when C5 goes high?

Is there no way I can use the CCP on C5 in conjunction with the timer?

Thanks for the help so far, really appreciate it.
bungee-



Joined: 27 Jun 2007
Posts: 206

View user's profile Send private message

PostPosted: Mon Oct 12, 2009 5:19 am     Reply with quote

You can use the similar code I wrote. You will just change first ISR so that you'll run it inside main program loop. And the other part could stay almost the same (throw out the EXT interrupt part ;) )
hobby_85



Joined: 17 Aug 2009
Posts: 50

View user's profile Send private message

PostPosted: Mon Oct 12, 2009 8:36 am     Reply with quote

bungee- wrote:

You can use the similar code I wrote. You will just change first ISR so
that you'll run it inside main program loop. And the other part could stay
almost the same (throw out the EXT interrupt part ;) )

Hey bungee, I have attached what I think is the right way to do it.\
Can you run your eyes over to see if I managed to get it right?

Here's the code. So basically I want to find out the time difference
between PINC1 going HIGH and PINC5 going high. I'm using a simple for
loop to find C1 going high and the CCP for PINC5.
Code:

#include <16F690.h>

#fuses INTRC, NOWDT, NOPROTECT, BROWNOUT, PUT
#use delay(clock = 4000000)
#use rs232(baud=19200, xmit=PIN_B7, rcv=PIN_B5)

   int16 ctr;
   int16 ctr1;
   int tripped=0;
   int16 value=0;
 
 
#int_CCP1
void  CCP1_isr(void)
{
   value=CCP_1;
   disable_interrupts(INT_CCP1);
   enable_interrupts(INT_EXT);
   tripped=1;
}
 

void main()
{

   
   set_tris_a(0b00111111);          //sets IO pins
   set_tris_b(0b01000000);          //sets IO pins
   set_tris_c(0b00100111);          //sets IO pins
 
   setup_adc_ports(NO_ANALOGS|VSS_VDD);
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
   setup_ccp1(CCP_CAPTURE_RE);
         
   for(;;){
   
      output_high(PIN_B4);              //disable RF output signal
      output_low(PIN_C4);               //turn off at start LED

   
      contact_slave3();                 //After this, PINC1 should go high, followed closely by PINC5 after about 500ms
   
      for (ctr=0;ctr<32000;ctr++) {     //Wait for PINC1 to go high until timeout
         if(input(PIN_C1)) {
            ctr=0;                      //PINC1 went high, set ctr=0, break
            break;
         }
      }
     
      if (ctr==0){         //at this point, C1 went high, start timer and wait for C5 to go high
         printf("\r\nRF Received, Starting timer\r\n");
        set_timer1(0);     //set timer value to 0
        tripped = 0;       //set tripped to 0
        enable_interrupts(INT_CCP1);  //wait for rising edge of pinC5 until timeout
       
         for (ctr1=0;ctr1<32000;ctr1++) {     //Wait for PINC5 to go high until timeout
            if(tripped) {
               printf("Value is: %Lu",value);
               tripped=0;

            }else{         
               printf("PINC5 did not go HIGH, Error");
            }
         }
               
       
      }else{                             //PINC1 did not go high, error
        printf("\r\nPINC1 did not go HIGH in the first place\r\n");
      }
     
     
   }
   
   
delay_ms(2000);

}

When I connect it up, 'Slave 3 contacted' and 'RF Received, Starting timer', but nothing about pin C5.

I must be doing something wrong with the timing. Either I'm polling the
pin too fast or something. Is there something wrong with the code?
I haven't used the compare function of CCP before so I'm still new.

Thanks
hobbby_85
Guest







PostPosted: Tue Oct 13, 2009 6:09 pm     Reply with quote

anyone?
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Tue Oct 13, 2009 6:24 pm     Reply with quote

1. Your program above never enables global interrupts, so it will never
get to the #int_ccp routine.

2. You are enabling INT_EXT interrupts inside the #int_ccp1 isr, but you
don't have an #int_ext routine. I don't see anywhere in your code
where you poll the INT_EXT interrupt flag, so presumably you do want
to have an #int_ext isr. If you don't need one, then delete that line
inside the #int_ccp1 isr.

3. You're setting the TRIS at the start of main(), but you don't have
#fast_io() mode specified, so the TRIS will be overridden by the
compiler (if it's different than yours) as required, when it does the
output_low(), output_high(), etc., functions. My advice is to delete
the set_tris_x() functions and let the compiler set the TRIS, unless
you have some compelling reason to set it yourself.
HOBBY_855
Guest







PostPosted: Tue Oct 13, 2009 7:42 pm     Reply with quote

Hey PCM, thanks alot for the help. I've fixed the code and posted it below. Ill be checking it tonight, but could you have a look if I've made any mistakes. Sorry about this, I'm still pretty new to CCS and ever used the CCP function.

Here's the code. So basically I want to find out the time difference
between PINC1 going HIGH and PINC5 going high. I'm using a simple for
loop to find C1 going high and the CCP for PINC5.

Code:

#include <16F690.h>

#fuses INTRC, NOWDT, NOPROTECT, BROWNOUT, PUT
#use delay(clock = 4000000)
#use rs232(baud=19200, xmit=PIN_B7, rcv=PIN_B5)

   int16 ctr;
   int16 ctr1;
   int tripped=0;
   int16 value=0;
 
 
#int_CCP1
void  CCP1_isr(void)
{
   value=CCP_1;
   disable_interrupts(INT_CCP1);
   tripped=1;
}
 

void main()
{

   
 
   setup_adc_ports(NO_ANALOGS|VSS_VDD);
   enable_interrupts(GLOBAL);
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
   setup_ccp1(CCP_CAPTURE_RE);
         
   for(;;){
   
       
      contact_slave3();                 //After this, PINC1 should go high, followed closely by PINC5 after about 500ms
   
      for (ctr=0;ctr<32000;ctr++) {     //Wait for PINC1 to go high until timeout
         if(input(PIN_C1)) {
            ctr=0;                                 //PINC1 went high, set ctr=0, break
            break;
         }
      }
     
      if (ctr==0){                                      //at this point, C1 went high, start timer and wait for C5 to go high
         printf("\r\PIN C5 has gone high\r\n");
        set_timer1(0);                            //set timer value to 0
        tripped = 0;                              //set tripped to 0
        enable_interrupts(INT_CCP1);      //wait for rising edge of pinC5 until timeout
       
         for (ctr1=0;ctr1<32000;ctr1++) {     //Wait for PINC5 to go high until timeout
            if(tripped) {
               printf("Value is: %Lu",value);
               tripped=0;

            }else{         
               printf("PINC5 did not go HIGH, Error");
            }
         }
               
       
      }else{                                        //PINC1 did not go high, error
        printf("\r\nPINC1 did not go HIGH in the first place\r\n");
      }
     
     
   }
   
   
delay_ms(2000);

}

What do you think?
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Goto page 1, 2, 3  Next
Page 1 of 3

 
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