|
|
View previous topic :: View next topic |
Author |
Message |
v1r05 Guest
|
External interrupt and CCP problem |
Posted: Wed Mar 18, 2009 7:05 pm |
|
|
hello...
I want to be able to use the external interrupt on B0,B1 while using the CCP modules to run my motors. The problem is whenever the CCP is enabled B0/B2 doesn't function... but B1 does ! I want at least 2 external interrupts to get input from 2 encoders.
Code: |
#include <18F4550.h>
#fuses HSPLL,NOWDT,NOPROTECT,NOLVP,NODEBUG,PLL5,CPUDIV1,VREGEN,USBDIV,NOPBADEN
#use delay(clock=48000000)
#use rs232(baud=19200,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8)
#include "compass.c"
#include "string.h"
#include "photo_sensor.c"
#include "motors.c"
#include "odometry.c"
unsigned char ECCP1AS;
unsigned char SSPCON1;
unsigned char ADCON;
unsigned char INTCON;
unsigned char PORTB;
#locate ECCP1AS=0x0FB6
#locate SSPCON1=0x0FC6
#locate ADCON=0x0FC2
#locate INTCON=0x0FF2
#locate PORTB =0xF81
void main()
{
setup_adc(AN0_TO_AN1);
setup_adc_ports(NO_ANALOGS);
setup_psp(PSP_DISABLED);
setup_spi(SPI_SS_DISABLED);
motors_init(); //enable CCP with PWM and pwm_duty = 0
SPEED = 0;
robot_fwd();
init_encoders();
running = 1;
while(1)
{
printf("b1: %Lu\tb2: %Lu\r\n",b1,b2);
delay_ms(1000);
output_toggle(PIN_A0);
}
}
from odometry.c
#INT_EXT2
void INT_EXT2_ISR()
{
// disable_interrupts(GLOBAL);
//if(running)
b2++;
// Encoder++;
// clear_interrupt(INT_EXT);
// enable_interrupts(GLOBAL);
}
#INT_EXT1
void INT_EXT1_ISR()
{
// disable_interrupts(GLOBAL);
// if(running)
b1++;
// clear_interrupt(INT_EXT1);
// enable_interrupts(GLOBAL);
}
void init_encoders()//reset counters etc...
{
b2 = b1 = robot_dir =0;
port_b_pullups (true);
set_tris_b(0xff);
ext_int_edge( 1, H_TO_L);
ext_int_edge( 2, L_TO_H);
//enable_interrupts(INT_EXT);
enable_interrupts(INT_EXT1);
enable_interrupts(INT_EXT2);
enable_interrupts(GLOBAL);
}
|
Please help. I've tried everything I can think of. I am stuck ! |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Thu Mar 19, 2009 12:13 pm |
|
|
You need to post a complete, compilable test program. Remove all the
#include files that are not necesary. Post all necessary variable
declarations.
Quote: | setup_adc(AN0_TO_AN1);
|
This is not a correct parameter for this function. Delete this line.
Quote: | setup_psp(PSP_DISABLED);
|
This line disables the PSP, which is already disabled upon power-up
anyway. Delete this line.
Quote: | setup_spi(SPI_SS_DISABLED); |
This line actually enables the spi module and configures some of the pins.
Delete this line.
Quote: | unsigned char ECCP1AS;
unsigned char SSPCON1;
unsigned char ADCON;
unsigned char INTCON;
unsigned char PORTB;
#locate ECCP1AS=0x0FB6
#locate SSPCON1=0x0FC6
#locate ADCON=0x0FC2
#locate INTCON=0x0FF2
#locate PORTB =0xF81 |
None of these registers are used in the test program. Delete all of this.
Quote: | #INT_EXT2
void INT_EXT2_ISR()
{
// disable_interrupts(GLOBAL);
//if(running)
b2++;
// Encoder++;
// clear_interrupt(INT_EXT);
// enable_interrupts(GLOBAL);
} |
Don't enable and disable global interrupts inside an isr. Don't clear
the interrupt in the isr (in normal programming). Let the CCS compiler
(and the PIC's hardware) handle the low level interrupt code.
It's designed to do it for you. Delete the lines shown in bold.
You need to delete all unnecessary lines from the test program, and
add any lines that are needed to demonstrate the problem. The program
must be very short and it must compile with no errors.
Finally, post your compiler version. |
|
|
v1r05 Guest
|
|
Posted: Sat Mar 21, 2009 7:13 am |
|
|
Hello pcm,
This all the code main.c
Code: |
#include <18f4520.h>
#fuses HS,NOWDT,NOPROTECT,NOLVP,NODEBUG,NOPBADEN
#use delay(clock=20000000)
#include "motors.c"
#include "odometry.c"
#use rs232(baud=19200,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8)
void main()
{
setup_adc_ports(NO_ANALOGS);
// motors_init();
port_b_pullups(0xff);
SPEED = 0;
//robot_fwd();
// robot_stop();
init_encoders();
while(1)
{
printf("b0: %Lu\tb1: %Lu\r\n",b0,b1);
delay_ms(1000);
output_toggle(PIN_A0);
}
}
|
in odometry.c:
Code: |
volatile unsigned int16 b0,b1,b2,robot_dir;
#INT_EXT
void INT_EXT_ISR()
{
b0++;
}
#INT_EXT1
void INT_EXT1_ISR()
{
b1++;
}
void init_encoders()//reset counters etc...
{
b2 = b1 = b0=robot_dir =0;
port_b_pullups (true);
set_tris_b(0xff);
ext_int_edge( 0, H_TO_L);
ext_int_edge( 1, L_TO_H);
enable_interrupts(INT_EXT);
enable_interrupts(INT_EXT1);
// enable_interrupts(INT_EXT2);
enable_interrupts(GLOBAL);
}
|
When I don't call "motor_init()" in main everything is ok. I measure the voltage on B0, B1, B2 they are all high just as they suppose to.
But when I call the function, B1 is the only pin that is pulled up. I tried to pull up the other two pin and connect the encoder but the PIC won't count the pulses on pin B0,B2 but works fine in B1.
I need only 2 INTx pins to be working.
Also at first I was using the PIC18F4550. I thought maybe they are damaged somehow. I replace it with a 4520 but same thing is happening.
Please help |
|
|
RLScott
Joined: 10 Jul 2007 Posts: 465
|
|
Posted: Sat Mar 21, 2009 2:08 pm |
|
|
v1r05 wrote: | Hello pcm,
...When I don't call "motor_init()" in main everything is ok... |
Then don't you think it would be important to post the code of motor_init() !!!!! _________________ Robert Scott
Real-Time Specialties
Embedded Systems Consulting |
|
|
Guest
|
|
Posted: Sun Mar 22, 2009 4:13 am |
|
|
ehhhhm, i thought i posted it.... here it is :
motors.c:
Code: |
/*****************************************************************/
/* Controls 4 motors, each two as a set
Motors 1,2
D0 START/STOP
D1 RUN/BREAK
D2 CW/CCW
C1 PWM1
Motors 3,4
D5 START/STOP
D4 RUN/BREAK
D3 CW/CCW
C2 PWM2
Encoder come from eith motor in a set to
B0 EXT1
B1 EXT2
*/
/*****************************************************************/
//left
#define START_STOP_2 PIN_D3
#define RUN_BREAK_2 PIN_D4
#define CW_CCW_2 PIN_D5
//right
#define START_STOP_1 PIN_D0
#define RUN_BREAK_1 PIN_D1
#define CW_CCW_1 PIN_D2
#define encoder_left PIN_B0
#define encoder_right PIN_B1
unsigned int16 SPEED = 512l;
unsigned int SPEED_ml = 20;
unsigned int SPEED_mr = 20;
void ml_run(int1 dir);//dir =1 cw , =0 ccw
void mr_run(int1 dir);
void ml_stop();
void mr_stop();
int1 sw_fr();
int1 sw_bkwd();
//int1 sw_si();
void robot_fwd();
void robot_bkd();
void robot_stop();
void motors_init();
void turn_right(unsigned int ratio,unsigned int sp);
void turn_left(unsigned int ratio,unsigned int sp);
void do_90(unsigned int sp,int1 dir);
void run_all_motors(unsigned int16 sp);
/*******************************************************/
/* initizlaize motors
/* set motor1 & motor2 to stop position
/*
/*******************************************************/
void motors_init()
{
// output_low(PIN_C1); // Set CCP2 output low
// output_low(PIN_C2); // Set CCP1 output low
/*
setup_ccp1(CCP_PWM); // Configure CCP1 as a PWM
setup_ccp2(CCP_PWM); // Configure CCP2 as a PWM
*/
setup_ccp1(CCP_PWM); // Configure CCP1 as a PWM
setup_ccp2(CCP_PWM); // Configure CCP2 as a PWM
setup_timer_2(T2_DIV_BY_4,74,1);//setup frequency
set_pwm1_duty(0);
set_pwm2_duty(0);
/* output_low(START_STOP_1);//stop
output_low(START_STOP_2);//stop
output_high(RUN_BREAK_1);//break
output_high(RUN_BREAK_2);
*/
ml_stop();
mr_stop();
}
void ml_stop()
{
output_high(START_STOP_1); //start
// output_high(RUN_BREAk_1);//instant stop run
output_low(RUN_BREAk_1);//stop
set_pwm1_duty(0);
}
void mr_stop()
{
output_high(START_STOP_2); //start
output_low(RUN_BREAk_2);//run
set_pwm2_duty(0);
}
|
|
|
|
Ttelmah Guest
|
|
Posted: Sun Mar 22, 2009 10:20 am |
|
|
As a comment, you need either CCP2C1, or CCP2B3 in the fuses, to tell the compiler, whether you want CCP2 routed to the C1, or B3 pins. Without this, I'd not be at all surprised if the compiler got confused, and changed the TRIS on the wrong port....
Best Wishes |
|
|
v1r05 Guest
|
nice...some progress |
Posted: Sun Mar 22, 2009 10:45 am |
|
|
hi tTtelmah,
nice catch...now here is my output :
b1: 1 b0: 19072
b1: 1 b0: 36857
b1: 1 b0: 27169
b1: 1 b0: 29539
b1: 1 b0: 29539
b1: 1 b0: 29539
b1: 1 b0: 29539
b1: 8 b0: 8542
B0 is not behaving properly... INT0 is being triggered without stimulus,
when B0 is constant its being pulled to ground. when i touch B1 pin be a grounded wire it generates an interrupt as expected.
i ported the same code to MCC18 compiler and am stuck at this exact same place... i dont know why the interrupt is being generated
thank u guys for the support, please bear with me |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Sun Mar 22, 2009 10:56 am |
|
|
Post your compiler version. |
|
|
v1r05 Guest
|
|
Posted: Sun Mar 22, 2009 11:48 am |
|
|
4.57.18.15 |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Sun Mar 22, 2009 12:12 pm |
|
|
That's not the version. The version is a 4-digit number in this format:
x.xxx
It's given at the top of the .LST file, which is in your project directory.
Don't post any numbers that come after the version number. |
|
|
v1r05 Guest
|
|
Posted: Sun Mar 22, 2009 6:57 pm |
|
|
Version 4.057 |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Sun Mar 22, 2009 7:05 pm |
|
|
Quote: | B0 is not behaving properly... INT0 is being triggered without stimulus, |
1. What is the voltage level on pin B0 in the idle state ?
(Look at it with an oscilloscope).
2. What creates the idle state voltage on pin B0 ?
Is it a pull-up resistor, or the encoder ? |
|
|
v1r05 Guest
|
|
Posted: Mon Mar 23, 2009 12:06 am |
|
|
1. The 40Khz PWM signal is coming out of B0 and B2.......i dont know who this happened. i will look in the datasheet for more info
2. pull-up resistors, i have enable portb pull-ups. from the datasheet of the motor, the encoder output is not being pulled up high.. its the responsibility of the application board.. so i guess i am connecting it right...
please note that i am testing now without connecting the encoders. all these problems without even connecting the encoder. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Mon Mar 23, 2009 12:39 am |
|
|
Quote: |
1. The 40Khz PWM signal is coming out of B0 and B2.......i dont know who
this happened. i will look in the datasheet for more info |
Look for solder shorts on the board. Or look for incorrect connections.
This problem must be fixed before anything will work. |
|
|
v1r05 Guest
|
|
Posted: Mon Mar 23, 2009 1:05 am |
|
|
yep, problem solved, it seems that the pins are shorted together B0 with C2 and B2 with C1... i removed the short and everything is in order....
thanks for your help guys... |
|
|
|
|
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
|