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

PIC Problems 101

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



Joined: 21 Sep 2003
Posts: 5
Location: Saginaw, MI

View user's profile Send private message Visit poster's website AIM Address MSN Messenger ICQ Number

PIC Problems 101
PostPosted: Thu Oct 16, 2003 1:56 pm     Reply with quote

I have a nice working circuit that I am utilizing to control a set of H-Bridges for control of a robot. Yet, the oddest thing happens. When I energize the system, the PIC does not begin its program right away every time. Many times i'll see a brief (1-2s) delay, other times it will never come on. Yet again, other times it begins right away. This circuit used to work right away, so I swapped out the PIC, and the same results occur. It doesn't seem like it could be my code since the results are almost random. I'll post what I am running though. Any ideas?


Thanks

#include "C:\Documents and Settings\Admin Bin\My Documents\ECE497\Code\motorcode.h"

// GLOBALS
int16 RRotations=0, LRotations=0, RClicks=0, LClicks=0;
char command = '.', P1=0, P2=0;


// PIN REDEFINITIONS
#define LBRAKE PIN_D0
#define LDIR PIN_D1
#define RBRAKE PIN_D3
#define RDIR PIN_D2
// Both CCP set to PWM with Duty from 0 to 500
#define MAXDUTY 480; // True max is 500
// Constants to normalize motors, not used yet
#define LMC 1.0
#define RMC 1.0

// ENCODER 1, not implemented
#int_RB
RB_isr() {

}

// ENCODER 2, not implemented
#int_EXT
EXT_isr() {

}

// EASE OF USE MOTOR FUNCTIONS
/*
DIR = 0 : Forward
DIR = 1 : Reverse
*/

inline void LeftMotor(int duty, short dir, short brake)
{
int dutycycle;

if(dir == 1)output_low(LDIR);
else output_high(LDIR);

if(brake == 1)output_high(LBRAKE);
else output_low(LBRAKE);

if(duty>100)duty=100;

dutycycle = (duty/100)*MAXDUTY;
set_pwm2_duty(dutycycle);
}

inline void RightMotor(int duty, short dir, short brake)
{
int dutycycle;

if(dir == 1)output_high(RDIR);
else output_low(RDIR);

if(brake == 1)output_high(RBRAKE);
else output_low(RBRAKE);

if(duty>100)duty=100;

dutycycle = (duty/100)*MAXDUTY;
set_pwm1_duty(dutycycle);
}

void main() {

setup_adc_ports(NO_ANALOGS);
setup_adc(ADC_CLOCK_DIV_2);
setup_spi(FALSE);
setup_psp(PSP_DISABLED);
setup_counters(RTCC_INTERNAL,RTCC_DIV_2);
setup_timer_1(T1_INTERNAL|T1_DIV_BY_1);
setup_timer_2(T2_DIV_BY_16,124,1);
setup_ccp1(CCP_PWM);
setup_ccp2(CCP_PWM);
enable_interrupts(INT_RB);
enable_interrupts(INT_EXT);
enable_interrupts(global);

// PORT SETUP
set_tris_a(0x00);
set_tris_b(0x00);
set_tris_c(0x00);
set_tris_d(0x00);
set_tris_e(0x00);

for(;;){ // START MAIN LOOP

LeftMotor(100, 1, 0);
RightMotor(100, 1, 0);
delay_ms(50);
LeftMotor(100, 0, 1);
RightMotor(100, 0, 1);
delay_ms(50);

} // END MAIN LOOP
}
_________________
- - - - -
-- Wrocko --
- - - - -
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Thu Oct 16, 2003 2:10 pm     Reply with quote

1. What PIC are you using ?

2. What version of the compiler ?

3. What do you have connected to the MCLR pin ?

4. Post the first part of your program, that shows all
the pre-processor statements. (Including #fuses,
#use statements, etc.)
Neutone



Joined: 08 Sep 2003
Posts: 839
Location: Houston

View user's profile Send private message

PostPosted: Thu Oct 16, 2003 2:18 pm     Reply with quote

Remove unused interupt enables that cause the processor to wake from sleep on interupt but no other function.
Code:

enable_interrupts(INT_RB);
enable_interrupts(INT_EXT);


Code:
for(;;){ // START MAIN LOOP
...
} // END MAIN LOOP

Replace with a while loop. I don't know what to expect from for(;;) but think it should be a syntax error. I'll bet it just goes to sleep.
Code:
While(1){ // START MAIN LOOP
...
} // END MAIN LOOP
fpgeh



Joined: 07 Sep 2003
Posts: 19
Location: Vancouver, BC

View user's profile Send private message

PostPosted: Thu Oct 16, 2003 3:29 pm     Reply with quote

Check your circuit and power supply. Motors draw more current than most typical CMOS circuits. Is your supply voltage correct and noise free? Do you have solid grounding? Also, do you have the correct free-wheeling diodes to prevent inductive spikes at the H-bridge? (often they are built into the H-bridge). Large inductive spikes could easily damage a PIC.
wrocko



Joined: 21 Sep 2003
Posts: 5
Location: Saginaw, MI

View user's profile Send private message Visit poster's website AIM Address MSN Messenger ICQ Number

PostPosted: Thu Oct 16, 2003 3:46 pm     Reply with quote

#include <16F877.h>
#use delay(clock=40000000)
#fuses XT,NOWDT
#use rs232(baud=9600,parity=N,xmit=PIN_C6,rcv=PIN_C7)

The chip is a PIC16F877, and i have a 1k resistor going to 5V on the MCLR pin. Compiler is V3.048

Its not the motors causing the problem, i removed them and just put logic probes on the I/O. It still reacts the same. I'll look into changing the loop type, but I have always used for(;;) with success in the past.

As to the interrupts, i'll give it a shot. Yet, if that is the problem wouldn't that happen when I do have code for them too? (I will need them for the motor encoders).

Thanks for the ideas.
_________________
- - - - -
-- Wrocko --
- - - - -
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Thu Oct 16, 2003 4:05 pm     Reply with quote

#include <16F877.h>
#use delay(clock=40000000)
#fuses XT,NOWDT
#use rs232(baud=9600,parity=N,xmit=PIN_C6,rcv=PIN_C7)


1. The #use delay is set for 40 MHz. This should be changed to 4 MHz.
Example:

#use delay(clock=4000000)


2. The #fuses should likely have NOLVP added to them. (Unless you're
using a programmer that supports LVP mode, and 99% do not).
Example:

#fuses XT, NOWDT, NOLVP


Also, I normally use the Power-up Timer and Brownout Reset.
So this might be better:

#fuses XT, NOWDT, PUT, BROWNOUT, NOLVP
ajt



Joined: 07 Sep 2003
Posts: 110

View user's profile Send private message

PostPosted: Thu Oct 16, 2003 8:58 pm     Reply with quote

Also, if the crystal is > 4MHz (not sure as both 4MHz and higher are mentioned) the HS fuse should be used not XT. Possibly, the oscillator is not starting up correclty.
_________________
Al Testani
wrocko



Joined: 21 Sep 2003
Posts: 5
Location: Saginaw, MI

View user's profile Send private message Visit poster's website AIM Address MSN Messenger ICQ Number

PostPosted: Fri Oct 17, 2003 4:01 pm     Reply with quote

Thanks for all the great ideas. The clock being set to the wrong delay was not the culprit, but was definetly something that needed to be fixed. I tried each idea seperately to see which would solve the problem.

It turned out to be the interrupts, once i added a single line of code to each, the program fired up right away every time.

Thanks again.
_________________
- - - - -
-- Wrocko --
- - - - -
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