View previous topic :: View next topic |
Author |
Message |
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
Little help, please |
Posted: Fri Jun 07, 2013 1:59 am |
|
|
Hi friends
It's surely a stupid issue but ...
Code: | #define E_MI !input(PIN_A0)
#define E_HI !input(PIN_A1)
#define E_Alarm !input(PIN_A4)
//#define E_Alarm !input(PIN_B4)
#define S_MI(x) output_bit(PIN_B3,x)
#define S_HI(x) output_bit(PIN_B2,x)
#define S_Alarm(x) output_bit(PIN_B5,x)
//variables-------------------------------------------------------------------
//Initialisation--------------------------------------------------------------
void initialisation()
{
setup_wdt(WDT_ON);
}
//--------------------------------------------------------------------------Main
void main()
{
initialisation();
while(true)
{
restart_wdt(); // resetter le watch dog !
S_MI(E_MI);
S_HI(E_HI);
S_Alarm(E_Alarm);
}
}
|
I use a PIC18F1230 to take advantage of pwm functions (not listed above)
In this code input(PIN_A0) does not work, nor other PIN_Ax
only PIN_B4 works
I mean that when I switch PIN_A0 to ground, or to 5V the Led connected at PIN_B3 always lit
Is there a reason ?
(the other pins are uses as follow :
A3 as RX
B0 as PWM0
A6 and A7 for the ceramic resonnator
B6 and B7 for the ICSP
)
Thanks for your suggestions |
|
|
ckielstra
Joined: 18 Mar 2004 Posts: 3680 Location: The Netherlands
|
|
Posted: Fri Jun 07, 2013 2:33 am |
|
|
First a few general notes:
1) As a regular visitor on this forum you should know we like to see programs posted that are complete, including all fuses, etc. This saves us time as we can copy/paste the program to our IDE, but even more important is that we than can be sure to have the exact situation you are using. Often a wrong fuse setting can cause many strange behaviours.
2) Always post your compiler version number! It can be an issue specific to your version.
3) Do you really need a watchdog? Watchdogs often cause more problems than they solve. For 95% of the situations where your device has a user sitting next to it who can power cycle the device when it hangs, no watchdog is needed. At least, during development disable the watchdog to make life a lot easier to yourself.
4) Without the watchdog your posted program will be shorter. We like short programs.
Then your problem at hand. I don't want to find the problem for you as I think there are a few more steps you can take yourself:
- Did you have a look at the generated assembly code? It might give you some clues. See the list file (*.lst)
- Have you tried writing the input and output commands as separate program lines instead of combining them in a macro?
- Just wondering, but I do hope you have a debugging tool? An In Circuit Debugger like ICD2 or PicKit3 is essential. Single stepping through your code you should be able to find the problem easily. |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
|
Posted: Fri Jun 07, 2013 3:12 am |
|
|
Like ckielstra says you should know the format by now. You're not being terribly helpful.
Maybe, since you've a problem with all the portA pins but not portB, it's something to do with portA pins defaulting to ANALOG inputs?
Mike |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Fri Jun 07, 2013 4:09 am |
|
|
My PCH is V 4.14
My .h is as follow
Code: | #include "18F1230.h"
//#device adc=8 //Where x is the number of bits read_adc() should return
#FUSES WDT32768 //Watch Dog Timer uses 1:32768 Postscale
#FUSES HS //High speed Osc (> 4mhz)
//#FUSES H4 //High speed Osc with PLL (> 4mhz)
//#FUSES NOFCMEN //Fail-safe clock monitor disabled
#FUSES NOBROWNOUT //No brownout reset
//#FUSES BORV20 //Brownout reset at 2.0V
#FUSES NOPUT //No Power Up Timer
#FUSES NOCPD //No EE protection
#FUSES NOSTVREN //Stack full/underflow will not cause reset
#FUSES NODEBUG //No Debug mode for ICD
//#FUSES LVP //Low Voltage Programming on B3(PIC16) or B5(PIC18)
//#FUSES NOLVP //No Low Voltage Programming on B3(PIC16) or B5(PIC18)
#FUSES NOWRT //Program memory not write protected
#FUSES NOWRTD //Data EEPROM not write protected
#FUSES NOWRTC //configuration registers not write protected
#FUSES NOIESO //Internal External Switch Over mode disabled
#FUSES NOEBTR //Memory not protected from table reads
#FUSES NOEBTRB //Boot block not protected from table reads
#FUSES NOMCLR //Master Clear pin used for I/O
#FUSES NOPROTECT //Code not protected from reading
#FUSES NOCPB //No Boot Block code protection
#FUSES NOWRTB //Boot block not write protected
#use delay(clock=20000000)
#use RS232(BAUD=75,BITS=8,PARITY=N,STOP=1,ERRORS) |
Which is nearly the same for each project
My code is
Code: | #include "CPL.h"
#define E_MI !input(PIN_A0)
#define E_HI !input(PIN_A1)
#define E_Alarm !input(PIN_A4)
//#define E_Alarm !input(PIN_B4)
#define S_MI(x) output_bit(PIN_B3,x)
#define S_HI(x) output_bit(PIN_B2,x)
#define S_Alarm(x) output_bit(PIN_B5,x)
#define PERIODE 0x31
//variables-------------------------------------------------------------------
long L_Periode;
boolean B_Isr1;
//Initialisation--------------------------------------------------------------
void initialisation()
{
//setup_wdt(WDT_ON);
L_Periode=2*PERIODE;
setup_timer_1(T1_INTERNAL | T1_DIV_BY_1); // 13ms pour T1_Div_BY_1 & 0xFFFF : 75Bdx
setup_power_pwm_pins(PWM_COMPLEMENTARY,PWM_OFF,PWM_OFF,PWM_OFF);
//PPWM channels 0 and 1 are both on and always opposite values
setup_power_pwm(PWM_CLOCK_DIV_4|PWM_FREE_RUN,1,0,PERIODE,0,1,0);
set_power_pwm0_duty(L_Periode);
enable_interrupts(INT_TIMER1);
enable_interrupts(GLOBAL);
}
//génération des pulses ---------------------------------------
#int_TIMER1
void BF()
{
B_Isr1=TRUE;
}
//--------------------------------------------------------------------------Main
void main()
{
Boolean B_BF;
initialisation();
while(true)
{
//restart_wdt(); // resetter le watch dog !
S_MI(E_MI);
S_HI(E_HI);
S_Alarm(E_Alarm);
if(B_Isr1)
{
B_BF=!B_BF;
B_Isr1=FALSE;
set_power_pwm0_duty(L_Periode * (int)B_BF);
output_bit(PIN_B6,B_BF);
}
}
} |
It seems there is no reason why thes 3 pins are not read |
|
|
z3ngew
Joined: 20 Apr 2013 Posts: 50
|
|
Posted: Fri Jun 07, 2013 4:41 am |
|
|
I think the problem might be in wdt and infinite loop but i'm not sure
Code: | while(true)
{
restart_wdt(); // resetter le watch dog !
} |
try to change this code structure,
Good Luck,
z3ngew |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Fri Jun 07, 2013 7:14 am |
|
|
z3ngew wrote: | I think the problem might be in wdt and infinite loop but i'm not sure
Code: | while(true)
{
restart_wdt(); // resetter le watch dog !
} |
try to change this code structure,
Good Luck,
z3ngew |
Sorry it doesn't work independantly of watch dog. I always include a watchdog in my application, and it is the first time I cannot read a port.
Thanks |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Fri Jun 07, 2013 7:37 am |
|
|
I exchange the PICF1230 with a PIC18F1220 and ... PIN_A4 is read but still PIN_A0 nor PIN_A1 is not read.
What special could have these pins ? |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19538
|
|
Posted: Fri Jun 07, 2013 7:37 am |
|
|
I think Mike has given you the key. The rule always is that you need to turn off peripherals that are on pins, before you can be sure of using them. Port A on this chip, has both the normal analog inputs, and the comparator on it. Then the serial on A2/A3. Remember also A5 is _input only_.
Best Wishes |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Fri Jun 07, 2013 8:04 am |
|
|
OK
You're right.
I add setup_adc_ports(NO_ANALOGS); in the init and it works.
It is the first time I have to do that, maybe a coincidence ?
Thanks a lot. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9243 Location: Greensville,Ontario
|
|
Posted: Fri Jun 07, 2013 8:44 am |
|
|
It has a lot to do with PIC type and compiler version.
Seems a single pin can have 1,2,5 different uses these days!
CCS will change the default use of I/O pins to digital,though only on some versions(newer) of some compilers.
Since it isn't consistent,you should ALWAYS 'hardcode' the pins uses.NEVER take anything for granted.
From an 'old guy' perspective, I'm 'miffed' that the default use of pins isn't set to digital I/O instead of any number of fancy peripheral uses !
Guess some guys at microchip figure nobody uses I/O that way anymore ?
cheers
jay |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Tue Jun 11, 2013 7:16 am |
|
|
temtronic wrote: | From an 'old guy' perspective, I'm 'miffed' that the default use of pins isn't set to digital I/O instead of any number of fancy peripheral uses !
Guess some guys at microchip figure nobody uses I/O that way anymore ?
cheers
jay |
I agree so much ! |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Tue Jun 11, 2013 7:27 am |
|
|
And now, in the same project, a new issue appears !
Code: | #use RS232(BAUD=75,BITS=8,PARITY=N,STOP=1,UART1) |
Code: | #include "CPL.h"
#define E_MI !input(PIN_A0)
#define E_HI !input(PIN_A1)
#define E_Alarm !input(PIN_A4)
#define S_MI(x) output_bit(PIN_B3,x)
#define S_HI(x) output_bit(PIN_B2,x)
#define S_Alarm(x) output_bit(PIN_B5,x)
#define PERIODE 0x31
//variables-------------------------------------------------------------------
Boolean B_Emetteur=FALSE;
long L_Periode;
boolean B_Isr1;
char I_buffer;
//Initialisation--------------------------------------------------------------
void initialisation()
{
setup_wdt(WDT_ON);
L_Periode=2*PERIODE;
setup_adc_ports(NO_ANALOGS); // pas d'analog. au reste les pin A0 A1 et A4 sont analogiques par défaut !
setup_timer_0(T0_INTERNAL | T0_DIV_64); // XXms pour T3_Div_BY_16
setup_power_pwm_pins(PWM_COMPLEMENTARY,PWM_OFF,PWM_OFF,PWM_OFF);
//PPWM channels 0 and 1 are both on and always opposite values
setup_power_pwm(PWM_CLOCK_DIV_4|PWM_FREE_RUN,1,0,PERIODE,0,1,0);
set_power_pwm0_duty(L_Periode);
enable_interrupts(INT_TIMER0);
enable_interrupts(GLOBAL);
}
//génération des pulses ---------------------------------------
#int_TIMER0
void Sec()
{
output_toggle(PIN_B3);
if (B_Emetteur)
{
putc(I_buffer);
putc(I_buffer);
}
}
#int_RDA
void Receive()
{
char I_Caract1;
char I_Caract2;
I_Caract1=getc();
I_Caract2=getc();
//S_Alarm(I_Caract1==I_Caract1);
S_Alarm(TRUE);
}
//--------------------------------------------------------------------------Main
void main()
{
boolean B_MI;
boolean B_HI;
Boolean B_Alarm;
initialisation();
while(true)
{
restart_wdt(); // resetter le watch dog !
B_MI=E_MI;
S_MI(B_MI);
B_HI=E_HI;
S_HI(B_HI);
B_Alarm=E_Alarm;
//S_Alarm(B_Alarm);
// bit 0 a chaque fois
// bit 1 MA
// bit 2 MI
// bit 3 HI
// bit 5 Alarm
I_Buffer=0x01 + (int)B_MI*0x04 + (int)B_HI*0x08 + (int)B_Alarm *0x20;
set_power_pwm0_duty(L_Periode *(int)(!input_state(PIN_A2))); //le PWM marche quand TX est au niveau bas
}
} |
I have 2 panel with this code.
Panel 1 send a message of 2 bytes to panel 2
It really send it, I see it on the oscilloscope !
I expect Panel 2 receives it. But #int_RDA does not fire !
The Led of S_Alarm does not lit as it should !
But I see the signal on PIN_A3/RX of my PIC18F1230
(I precise my compiler version is PCH V 4.14)
Where could be my error ?
Thanks to all |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19538
|
|
Posted: Tue Jun 11, 2013 8:28 am |
|
|
First, what is the compiler version!.....
Version numbers are always 4.xxx. Are you actually on 4.014 or 4.140?. If the former, give up!. The earliest reasonably working V4 compilers were around 4.06x ish.
Then realise that INT_RDA, implies _one_ character is waiting to be read only. Not two.
Code: |
#int_RDA
void Receive()
{
char temp;
static int8 old;
static int1 state=FALSE;
temp=getc();
switch (state) {
case FALSE:
old=temp;
state=TRUE;
break;
case TRUE:
state=FALSE;
if (old==temp)
S_Alarm(FALSE);
else
S_alarm(TRUE);
break;
}
}
|
Then study your code. Where do you enable INT_RDA?.....
This is the 'biggy'.....
Best Wishes |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Wed Jun 12, 2013 1:07 am |
|
|
Ttelmah wrote: | First, what is the compiler version!..... |
V 4.140
Ttelmah wrote: |
Then study your code. Where do you enable INT_RDA?.....
This is the 'biggy'.....
Best Wishes |
Dear, what distrait am I !
Is it a sign of early Alzheimer ?
Thanks for all |
|
|
Jean FOUGERON
Joined: 30 Nov 2012 Posts: 110 Location: France
|
|
Posted: Wed Jun 12, 2013 7:49 am |
|
|
In another way :
My receive routine is as follow :
Code: | #int_RDA
void Receive()
{
I_Receive[I_Receive_Counter]=getc();
I_Receive_Counter++;
if(I_Receive_Counter==2) // reçu 2 caractères
{
I_Receive_Counter=0;
if(I_Receive[0]!=I_Receive[1]) //problème
{
I_Send=0x81; // bit 7 = demande de renvoyer
B_Reponse=TRUE;
S_Alarm(FALSE);
}
else
{
B_MI=(I_Receive[0]&0x04);
B_HI=(I_Receive[0]&0x08);
B_Reponse=FALSE;
S_Alarm(TRUE);
}
}
} |
Where I expect that B_MI goes TRUE when I_Receive[0] has its bit 2 set, and FALSE in the other cases.
But, when I apply 0x05, 0x0D 0x25 or 0x2D on the pin RX of my PIC, B_MI stays FALSE
Now, when I use this routine :
Code: | switch (I_Receive[0])
{
case 0x05:
B_MI=TRUE;
break;
case 0x0D:
B_MI=TRUE;
break;
case 0x25:
B_MI=TRUE;
break;
case 0x2D:
B_MI=TRUE;
break;
default:
B_MI=FALSE;
break;
} |
B_MI goes TRUE when I_Receive[0] has its bit 2 set !!
I look at .lst and observe :
Code: | .................... B_HI=(I_Receive[0]&0x08);
0136: MOVF 1D,W --> W=I_Receive[0]
0138: ANDLW 08 --> W=W & 0x08 Flag Z is actioned if bit 2 not set
013A: BCF 19.4 --> B_HI=False
013C: BTFSC FE8.0 --> test bit 0 of FE8 (what is FE8 ?) and branch to 013E if not set
013E: BSF 19.4 -->B_HI=true => FE8.0 is set |
I understand that we proceed to as Bitwise AND between I_Receive[0] and bit 2, if the result is 1 then B_HI=True else B_HI=false
But in reality B_HI stays FALSE !
When I use the switch procedure, I have :
Code: | .................... switch (I_Receive[0])
.................... {
0110: MOVF 1D,W
0112: XORLW 05
0114: BZ 0124
0116: XORLW 08
0118: BZ 0128
011A: XORLW 28
011C: BZ 012C
011E: XORLW 08
0120: BZ 0130
0122: BRA 0134
.................... case 0x05:
.................... B_MI=TRUE;
0124: BSF 19.3
.................... break;
0126: BRA 0136
.................... case 0x0D:
.................... B_MI=TRUE;
0128: BSF 19.3
.................... break;
012A: BRA 0136
.................... case 0x25:
.................... B_MI=TRUE;
012C: BSF 19.3
.................... break;
012E: BRA 0136
.................... case 0x2D:
.................... B_MI=TRUE;
0130: BSF 19.3
.................... break;
0132: BRA 0136
.................... default:
.................... B_MI=FALSE;
0134: BCF 19.3
.................... break;
.................... } |
Wich is more complicated but which does what I expect : B_MI=TRUE when bit 2 of I_Receive[0] is set !
Code: | .................... switch (I_Receive[0])
.................... {
0110: MOVF 1D,W --> W=I_Receive[0]
0112: XORLW 05 --> W=W XOR 05 ==0 only if bit 2=1 (which means B_MI has to be TRUE) and other bits are equals each other ! which generally is not the case !
0114: BZ 0124 --> branch if equals zero
.../...
.................... case 0x05:
.................... B_MI=TRUE;
0124: BSF 19.3 --> set B_MI to True
.................... break;
.../...
.................... } |
So ... I'm lost and do nor see why my simple routine using a & does not work and a complicated one does !
Thanks to all |
|
|
|