1
\$\begingroup\$

I wrote a function for interacting with my 'PIC16F1788'. The code sends pulses out the 'RC4' port at a specific frequency, to make an LED blink according to that frequency. So the LED will blink faster or slower depending on the magnitude of the frequency. I decided to take a blinking code and vary the delay time according to my input frequency as follows.

void blink(int frequency){
/* starts the LED blinking at a particular frequency */

     PORTCbits.RC4=0XFF;  // RC4 on
     __delay_ms(1000/frequency);   // time in ms dealing with frequency values in kHz
     PORTcbits.RC4=0X00;   // RC4 off
     __delay_ms(1000/frequency);   // time in ms dealing with frequency values in kHz

}

would this code work, is this a good idea ,and is there anyway that I could improve it?

Update #1

I changes my code based on some of your inputs But still no luck running it. it compiles just fine but the LED doesn't Blink =(

#include <htc.h>
#include <pic.h>
#include <pic16f1788.h>
#include <xc.h>
// Config word
#define frequ  100000
#define _XTAL_FREQ   20000000


void main()

{

   // output

TRISB5 = 0;

// configure CCP3

CCP3CONbits.CCP3M = 0x0C;   // set it to PWM mode; and active high

// configure Timer 2
PR2 = ((_XTAL_FREQ)/(4*16*frequ))-1;  // Timer 2 max value is (20MHz / 4*16*f)-1 = max duty, fosc=20MHz, prescaler of 16
CCPR3 = 0.5*(PR2+1);        // CCP3 compare value is 50% duty cycle
T2CONbits.T2OUTPS = 0x02;   // Timer 2 prescaler 16
T2CONbits.TMR2ON = 1;       // Timer 2 on

}
\$\endgroup\$
5
  • 1
    \$\begingroup\$ blinking frequency will be frequency/2. \$\endgroup\$
    – nidhin
    Feb 22, 2015 at 15:58
  • \$\begingroup\$ well 1/frequency gives us the period(seconds). so in order to convert that to ms i multiplied by 1000 since i am going to be working with frequencies in the kHz. please explain your reasoning. \$\endgroup\$ Feb 22, 2015 at 16:03
  • \$\begingroup\$ There's nothing wrong with your period calculations. nidhin is saying that the led will toggle at "frequency" meaning that it will actually only blink at the rate "frequency/2" \$\endgroup\$ Feb 28, 2015 at 3:54
  • \$\begingroup\$ Please take a look at the most recent code I uploaded below. Thanks \$\endgroup\$ Feb 28, 2015 at 3:57
  • \$\begingroup\$ It looks like you've already rejected your original code for other reasons, but I just wanted to point out that dividing by a variable is one of the most expensive things you can do on a non-floating point (integer-only) processor. Since you're using it to calculate a delay, it's probably fine in that case, but you may need to tweak the delay if you care about accuracy. There are many creative ways to get around that problem, most of which are overly complicated to a mathematician, but are also much faster than a real division. \$\endgroup\$
    – AaronD
    Mar 30, 2015 at 18:24

2 Answers 2

1
\$\begingroup\$

My guess to your problem is that your problem is with the data type being used for the attributes of the delay function. When you are using 'integer' as the attribute data type, you can't express values less than 1 but greater than 0. If your frequency is greater than 1000, the code won't work. you need to manipulate the frequency variable in such a way that the division won't go below 1 but will still be related to frequency. Try dividing frequency with a constant.

\$\endgroup\$
0
\$\begingroup\$

Instead of deliberate delays, I'd use a counter to divide the input frequency to make the output frequency.

\$\endgroup\$
1
  • \$\begingroup\$ Can you give an example? thanks \$\endgroup\$ Feb 22, 2015 at 16:07

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.