Forum: Mikrocontroller und Digitale Elektronik PIC18F66 Konflikt zwischen RA0 und Init CAN-Modul


von Stefan S. (humus)


Lesenswert?

Hallo Zusammen,

wieder einmal das alte Leid, das einzelne Funktionen isoliert wunderbar 
funktionieren, aber zusammen nicht. Ich kommuniziere via CAN-Bus mit 
meinem PIC18F66K80, das funktionierte einwandfrei. Möchte jetzt vorab 
den analogen Eingang RA0 auslesen funktioniert das auch wunderbar, 
solange ich die Funktion "configureCAN()" auskommentiert lasse. Wenn ich 
die beiden Softwarefetzen zusammen bringe, schickt mir der AD-Wandler 
nur noch 4069 anstatt die erwartetet +-2000. Hier mein Code:
1
#include <stdint.h>
2
3
#define             IP_adress            PORTF
4
#define             ON                   1
5
#define             OFF                  0
6
#define             TLI4970              1
7
#define             LTC6804              0
8
#define             IDmaster             255
9
10
// LCD module connections
11
sbit LCD_RS at LATD4_bit;
12
sbit LCD_EN at LATD6_bit;
13
sbit LCD_D4 at LATD0_bit;
14
sbit LCD_D5 at LATD1_bit;
15
sbit LCD_D6 at LATD2_bit;
16
sbit LCD_D7 at LATD3_bit;
17
18
sbit LCD_RS_Direction at TRISD4_bit;
19
sbit LCD_EN_Direction at TRISD6_bit;
20
sbit LCD_D4_Direction at TRISD0_bit;
21
sbit LCD_D5_Direction at TRISD1_bit;
22
sbit LCD_D6_Direction at TRISD2_bit;
23
sbit LCD_D7_Direction at TRISD3_bit;
24
// End LCD module connections
25
26
// ECAN module connections
27
// End ECAN module connections
28
29
30
/*******************************************************************************
31
Variables
32
*******************************************************************************/
33
unsigned int IDmodule=0, IDmodule2 = 9;
34
short int lcd_line[4][20];
35
36
//-----------------    CAN    --------------------------------------------------
37
unsigned unsigned short Can_Init_Flags, Can_Send_Flags, Can_Rcv_Flags; // can flags
38
unsigned unsigned short Rx_Data_Len, dt, cell_count[2];                                   // received data length in bytes
39
unsigned short Rx_Data[8], Tx_Data[8], RxTx_Data[8];                                           // can rx/tx data 8-bytes buffer
40
unsigned short Msg_Rcvd = 0;
41
unsigned int Rx_ID, Tx_ID, i, j, h, k, adc_rd;
42
int pin_mux[13] = {0x0E, 0x0C, 0x0A, 0x08, 0x06, 0x04, 0x02, 0x00, 0x1C, 0x1E, 0x18, 0x16, 0x1A};
43
unsigned int temp_values[2][13];        //Line1 cell voltage & curren, line2 temperature
44
45
const unsigned short SJW = 1;
46
const unsigned short BRP = 1;
47
const unsigned short Propagation = 1;
48
const unsigned short Phase1 = 4;
49
const unsigned short Phase2 = 3;
50
51
52
void init() {
53
    ANCON0 = 0x01;                     // RA0 as analog input
54
    ANCON1 = 0x00;                     // No analog inputs
55
56
    TRISA = 0x01;                      // set PORTA as output except RA0
57
    LATA = 0x00;                       // clear PORTA
58
59
    TRISB = 0x00;                      // set PORTB as output
60
    LATB = 0x00;                       // clear PORTA
61
62
    TRISC = 0x08;                      // RC3(SCK) & RC4(SDI) as input, others as output
63
    PORTC = 0x00;                      // clear PORTC
64
65
    TRISD = 0x00;                      // set PORTD as output
66
    TRISE = 16;                        // RE4(CAN RX) as input, others as output (CAN TX)
67
    WPUB = 0x00;                       // Disable all PORTB pull-up resistors
68
    TRISF = 0xFF;                      // set PORTF as input
69
70
   Delay_ms(1000);
71
   IDmodule = (IP_adress & 0xff);
72
   Lcd_Cmd(_LCD_CLEAR);               // Clear display
73
   Lcd_Cmd(_LCD_CURSOR_OFF);          // Cursor off
74
   sprintf(lcd_line[0], "ID Module = %u v01", IDmodule);                                                                                                                        //The pec_error variable is simply set negative if any PEC errors
75
   Lcd_Out(1,1, lcd_line[0]);
76
   Delay_ms(4000);
77
}
78
//------------------------------------------------------------------------------
79
//                          CAN Configuration
80
//------------------------------------------------------------------------------
81
void configureCAN(void)
82
{
83
    Can_Init_Flags = 0;                                       //
84
    Can_Send_Flags = 0;                                       // clear flags
85
    Can_Rcv_Flags  = 0;                                       //
86
87
    Can_Send_Flags = _CAN_TX_PRIORITY_0 &                     // form value to be used
88
                     _CAN_TX_STD_FRAME &                      // with CANWrite
89
                     _CAN_TX_NO_RTR_FRAME;
90
91
    Can_Init_Flags = _CAN_CONFIG_SAMPLE_THRICE &              // form value to be used
92
                     _CAN_CONFIG_PHSEG2_PRG_ON &              // with CANInit
93
                     _CAN_CONFIG_STD_MSG &
94
                     _CAN_CONFIG_DBL_BUFFER_ON &
95
                     _CAN_CONFIG_VALID_STD_MSG &
96
                     _CAN_CONFIG_LINE_FILTER_ON;
97
98
    CANInitialize(SJW, BRP, Phase1, Phase2, Propagation, Can_Init_Flags);    // initialize external CAN module
99
100
    CANSetOperationMode(_CAN_MODE_CONFIG,0xFF);                    // set CONFIGURATION mode (blocking call)
101
102
    CANSetMask(_CAN_MASK_B1,0x0180,_CAN_CONFIG_STD_MSG);           // set all mask1 bits to ones
103
    CANSetMask(_CAN_MASK_B2,0xFFFF,_CAN_CONFIG_STD_MSG);           // set all bits to 1
104
105
    CANSetFilter(_CAN_FILTER_B1_F1, 0x0080,_CAN_CONFIG_STD_MSG);   // receive messages with bit 9 = 0 and 8 = 1
106
    CANSetFilter(_CAN_FILTER_B1_F2, 0x0180,_CAN_CONFIG_STD_MSG);   // receive messages with bit 9 = 1 and 8 = 1
107
108
//    CANSetFilter(_CAN_FILTER_B2_F1, 0x0000,_CAN_CONFIG_STD_MSG);   // receive messages with identifier = 0
109
//    CANSetFilter(_CAN_FILTER_B2_F2, 0x0001,_CAN_CONFIG_STD_MSG);   // receive messages with identifier = 1
110
    CANSetFilter(_CAN_FILTER_B2_F3, IDmodule2,_CAN_CONFIG_STD_MSG);   // receive messages with identifier = 2
111
    CANSetFilter(_CAN_FILTER_B2_F4, IDmodule,_CAN_CONFIG_STD_MSG);   // receive messages with identifier = IDmodule
112
113
    CANSetOperationMode(_CAN_MODE_NORMAL,0xFF);                // set NORMAL mode
114
}
115
116
117
void main()
118
{
119
init();                            // Perform main initialization
120
ADC_Init();                        // Initialize ADC module with default settings
121
configureCAN();                              // Configure CAN module
122
Lcd_Init();
123
124
while(1)
125
{
126
PORTC = 0x1;
127
Delay_ms(500);
128
PORTC = 0x0;
129
Delay_ms (500);
130
131
132
for(k=0;k<4;k++)
133
{
134
    PORTB = pin_mux[k];             // set MUX/I0
135
    Delay_ms(1);
136
    adc_rd = ADC_Read(0);    // get ADC value from 0st channel
137
    temp_values[1][k] = adc_rd;
138
    sprintf(lcd_line[k], "Voltage = %u V", temp_values[1][k]);                // Trim the string from leading spaces
139
    Lcd_Out(k+1,1, lcd_line[k]);
140
    PORTC = 0x2;
141
    Delay_ms(500);
142
    PORTC = 0x1;
143
}
144
}
145
}

Ich habe das Problem auf die Funktion "CANInitialize(SJW, BRP, Phase1, 
Phase2, Propagation, Can_Init_Flags);" isolieren können. Ich verwende 
den Compiler von MicroC. Die Librarybeschreibung hilft mir aber leider 
auch nicht weiter 
(http://download.mikroe.com/documents/compilers/mikroc/pic/help/can_library.htm#caninitialize). 
Kann mir jemand weiter helfen?

VG und DANKE!

: Bearbeitet durch User
von Frank K. (fchk)


Lesenswert?

Hast Du den Library-Quelltext, d.h. weißt Du, was bei CAN* passiert?

Wenn nein, dann benutze die MikroE Bibliotheken überhaupt nicht mehr, 
sondern mach alles selber. Dann weißt Du, wie es geht, was Du machst, 
und welche Bits Du anfasst.

Oder einfach mal den xc8 nehmen.

fchk

von Stefan S. (humus)


Lesenswert?

Nein den Quellcode habe ich natürlich nicht. Der xc8 mit der CAN-Library 
von Microchip hat bei mir und meinen Kollegen zu keinem Ergebnis 
geführt. Mit MicroC ging alles sauber, bis jetzt :/
Ich werde mal bei MicroC anfragen ob das Problem bekannt ist.

von Frank K. (fchk)


Lesenswert?

Stefan S. schrieb:
> Nein den Quellcode habe ich natürlich nicht. Der xc8 mit der CAN-Library
> von Microchip hat bei mir und meinen Kollegen zu keinem Ergebnis
> geführt. Mit MicroC ging alles sauber, bis jetzt :/
> Ich werde mal bei MicroC anfragen ob das Problem bekannt ist.

Ohne Bibliotheks-Quelltext kannst Du nicht wissen, was da passiert. Wenn 
MikroE Dir nicht helfen kann, kann es hier auch keiner.

fchk

von Witkatz :. (wit)


Lesenswert?

Lässt sich das Programm in MicroC debuggen, um die Werte der für PORTA 
und ADC zuständigen Register nach CANInitialize() zu prüfen?
Vielleicht würde eine veränderte Reihenfolge Abhilfe bringen: erst CAN 
Modul initialisieren, dann die restliche Peripherie?

witkatz

von Stefan S. (humus)


Lesenswert?

Ich habe die Reihenfolge verändert. Je nachdem was ich zuerst 
initialisiere funktioniert dann auch. Das kann doch nicht sein.

von Frank K. (fchk)


Lesenswert?

Stefan S. schrieb:
> Ich habe die Reihenfolge verändert. Je nachdem was ich zuerst
> initialisiere funktioniert dann auch. Das kann doch nicht sein.

Wenn Du grottige Bibliotheken verwendest, schon. Implementiere es eben 
selber.

von Stefan S. (humus)


Lesenswert?

Frank K. schrieb:
> Implementiere es eben
> selber.

Ok macht Sinn. Ich habe die Register für die CAN-Init wie folgt 
eingestellt (Ersatz für die Funktion "CANInitialize":
1
CANSetOperationMode(_CAN_MODE_CONFIG,0xFF);                    // set CONFIGURATION mode (blocking call)
2
3
//Set Bit rate values as per defines
4
5
BRGCON1 = ((SJW - 1) << 6) | (BRP-1);
6
BRGCON2 = (_CAN_CONFIG_PHSEG2_PRG_ON << 7) |  (_CAN_CONFIG_SAMPLE_THRICE << 6) | ((Phase1 - 1) << 4) | (Propagation -1);
7
BRGCON3 = (_CAN_CONFIG_LINE_FILTER_ON << 6) | (Phase2 -1);
8
9
10
//CANInitialize(SJW, BRP, Phase1, Phase2, Propagation, Can_Init_Flags);    // initialize external CAN module
11
    CANSetOperationMode(_CAN_MODE_NORMAL,0xFF);

Jetzt funktioniert zwar der AD-Wandler, aber der CAN-Bus noch nicht. 
Kann mir jemand einen Tipp geben was ich hier noch falsch mache?

VG und Danke

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.