OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [freertos-6.1.1/] [Demo/] [Common/] [drivers/] [Atmel/] [at91lib/] [peripherals/] [can/] [can.c] - Blame information for rev 608

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 608 jeremybenn
/* ----------------------------------------------------------------------------
2
 *         ATMEL Microcontroller Software Support
3
 * ----------------------------------------------------------------------------
4
 * Copyright (c) 2008, Atmel Corporation
5
 *
6
 * All rights reserved.
7
 *
8
 * Redistribution and use in source and binary forms, with or without
9
 * modification, are permitted provided that the following conditions are met:
10
 *
11
 * - Redistributions of source code must retain the above copyright notice,
12
 * this list of conditions and the disclaimer below.
13
 *
14
 * Atmel's name may not be used to endorse or promote products derived from
15
 * this software without specific prior written permission.
16
 *
17
 * DISCLAIMER: THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR
18
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
19
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE
20
 * DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT,
21
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
23
 * OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
24
 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
25
 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
26
 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27
 * ----------------------------------------------------------------------------
28
 */
29
 
30
//------------------------------------------------------------------------------
31
//         Headers
32
//------------------------------------------------------------------------------
33
 
34
#include <board.h>
35
#include <pio/pio.h>
36
#include <utility/trace.h>
37
#include <aic/aic.h>
38
#include "can.h"
39
 
40
//------------------------------------------------------------------------------
41
//         Local definitions
42
//------------------------------------------------------------------------------
43
// CAN state
44
#define CAN_DISABLED       0
45
#define CAN_HALTED         1
46
#define CAN_IDLE           2
47
#define CAN_SENDING        3
48
#define CAN_RECEIVING      4
49
 
50
// MOT: Mailbox Object Type
51
#define CAN_MOT_DISABLE    0 // Mailbox is disabled
52
#define CAN_MOT_RECEPT     1 // Reception Mailbox
53
#define CAN_MOT_RECEPT_OW  2 // Reception mailbox with overwrite
54
#define CAN_MOT_TRANSMIT   3 // Transmit mailbox
55
#define CAN_MOT_CONSUMER   4 // Consumer mailbox
56
#define CAN_MOT_PRODUCER   5 // Producer mailbox
57
 
58
//------------------------------------------------------------------------------
59
//         Local variables
60
//------------------------------------------------------------------------------
61
#if defined (PINS_CAN_TRANSCEIVER_TXD)
62
static const Pin pins_can_transceiver_txd[] = {PINS_CAN_TRANSCEIVER_TXD};
63
#endif
64
#if defined (PINS_CAN_TRANSCEIVER_RXD)
65
static const Pin pins_can_transceiver_rxd[] = {PINS_CAN_TRANSCEIVER_RXD};
66
#endif
67
static const Pin pin_can_transceiver_rs   = PIN_CAN_TRANSCEIVER_RS;
68
#if defined (PIN_CAN_TRANSCEIVER_RXEN)
69
static const Pin pin_can_transceiver_rxen = PIN_CAN_TRANSCEIVER_RXEN;
70
#endif
71
 
72
static CanTransfer *pCAN0Transfer=NULL;
73
#ifdef AT91C_BASE_CAN1
74
static CanTransfer *pCAN1Transfer=NULL;
75
#endif
76
 
77
//------------------------------------------------------------------------------
78
//         Local functions
79
//------------------------------------------------------------------------------
80
 
81
//------------------------------------------------------------------------------
82
/// CAN Error Detection
83
/// \param status     error type
84
/// \param can_number can nulber
85
//------------------------------------------------------------------------------
86
static void CAN_ErrorHandling( unsigned int status, unsigned char can_number)
87
{
88
    if( (status&AT91C_CAN_ERRA) ==  AT91C_CAN_ERRA) {
89
        trace_LOG( trace_ERROR, "-E- (CAN) CAN is in active Error Active mode\n\r");
90
    }
91
    else if( (status&AT91C_CAN_ERRP) ==  AT91C_CAN_ERRP) {
92
        trace_LOG( trace_ERROR, "-E- (CAN) CAN is in Error Passive mode\n\r");
93
    }
94
    else if( (status&AT91C_CAN_BOFF) ==  AT91C_CAN_BOFF) {
95
        trace_LOG( trace_ERROR, "-E- (CAN) CAN is in Buff Off mode\n\r");
96
        // CAN reset
97
        trace_LOG( trace_ERROR, "-E- (CAN) CAN%d reset\n\r", can_number);
98
        // CAN Controller Disable
99
        if (can_number == 0) {
100
            AT91C_BASE_CAN0->CAN_MR &= ~AT91C_CAN_CANEN;
101
            // CAN Controller Enable
102
            AT91C_BASE_CAN0->CAN_MR |= AT91C_CAN_CANEN;
103
        }
104
#ifdef AT91C_BASE_CAN1
105
        else if (can_number == 1) {
106
            AT91C_BASE_CAN1->CAN_MR &= ~AT91C_CAN_CANEN;
107
            // CAN Controller Enable
108
            AT91C_BASE_CAN1->CAN_MR |= AT91C_CAN_CANEN;
109
        }
110
#endif
111
    }
112
 
113
    // Error for Frame dataframe
114
    // CRC error
115
    if( (status&AT91C_CAN_CERR) ==  AT91C_CAN_CERR) {
116
        trace_LOG( trace_ERROR, "-E- (CAN) CRC Error\n\r");
117
    }
118
    // Bit-stuffing error
119
    else if( (status&AT91C_CAN_SERR) ==  AT91C_CAN_SERR) {
120
        trace_LOG( trace_ERROR, "-E- (CAN) Stuffing Error\n\r");
121
    }
122
    // Bit error
123
    else if( (status&AT91C_CAN_BERR) ==  AT91C_CAN_BERR) {
124
        trace_LOG( trace_ERROR, "-E- (CAN) Bit Error\n\r");
125
    }
126
    // Form error
127
    else if( (status&AT91C_CAN_FERR) ==  AT91C_CAN_FERR) {
128
        trace_LOG( trace_ERROR, "-E- (CAN) Form Error\n\r");
129
    }
130
    // Acknowledgment error
131
    else if( (status&AT91C_CAN_AERR) ==  AT91C_CAN_AERR) {
132
        trace_LOG( trace_ERROR, "-E- (CAN) Acknowledgment Error\n\r");
133
    }
134
 
135
    // Error interrupt handler
136
    // Represent the current status of the CAN bus and are not latched.
137
    // See CAN, par. Error Interrupt Handler
138
    // AT91C_CAN_WARN
139
    // AT91C_CAN_ERRA
140
}
141
 
142
//------------------------------------------------------------------------------
143
// Generic CAN Interrupt handler
144
/// \param can_number can nulber
145
//------------------------------------------------------------------------------
146
static void CAN_Handler( unsigned char can_number )
147
{
148
    AT91PS_CAN base_can;
149
    AT91PS_CAN_MB CAN_Mailbox;
150
 
151
    unsigned int status;
152
    unsigned int can_msr;
153
    unsigned int* pCan_mcr;
154
    unsigned int message_mode;
155
    unsigned char numMailbox;
156
    unsigned char state0;
157
    unsigned char state1;
158
 
159
    if( can_number == 0 ) {
160
        base_can = AT91C_BASE_CAN0;
161
        CAN_Mailbox = AT91C_BASE_CAN0_MB0;
162
        state0 = pCAN0Transfer->state;
163
    }
164
#ifdef AT91C_BASE_CAN1
165
    else {
166
        base_can = AT91C_BASE_CAN1;
167
        CAN_Mailbox = AT91C_BASE_CAN1_MB0;
168
        state1 = pCAN1Transfer->state;
169
    }
170
#endif
171
    status = (base_can->CAN_SR) & (base_can->CAN_IMR);
172
    base_can->CAN_IDR = status;
173
 
174
    trace_LOG( trace_DEBUG, "CAN0 status=0x%X\n\r", status);
175
    if(status & AT91C_CAN_WAKEUP) {
176
        if( can_number == 0 ) {
177
            pCAN0Transfer->test_can = AT91C_TEST_OK;
178
            pCAN0Transfer->state = CAN_IDLE;
179
        }
180
#ifdef AT91C_BASE_CAN1
181
        else {
182
            pCAN1Transfer->test_can = AT91C_TEST_OK;
183
            pCAN1Transfer->state = CAN_IDLE;
184
        }
185
#endif
186
    }
187
    // Mailbox event ?
188
    else if ((status&0x0000FFFF) != 0) {
189
        trace_LOG( trace_DEBUG, "Mailbox event\n\r");
190
 
191
        // Handle Mailbox interrupts
192
        for (numMailbox = 0; numMailbox < NUM_MAILBOX_MAX; numMailbox++) {
193
 
194
            can_msr = *(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x10+(0x20*numMailbox)));
195
            if ((AT91C_CAN_MRDY & can_msr) == AT91C_CAN_MRDY) {
196
                // Mailbox object type
197
                message_mode =  ((*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x00+(0x20*numMailbox))))>>24)&0x7;
198
                trace_LOG( trace_DEBUG, "message_mode 0x%X\n\r", message_mode);
199
                trace_LOG( trace_DEBUG, "numMailbox 0x%X\n\r", numMailbox);
200
 
201
                if( message_mode == 0 ) {
202
                    trace_LOG( trace_ERROR, "-E-Error in MOT\n\r");
203
                }
204
                else if( ( message_mode == CAN_MOT_RECEPT )
205
                      || ( message_mode == CAN_MOT_RECEPT_OW )
206
                      || ( message_mode == CAN_MOT_PRODUCER ) ) {
207
                    trace_LOG( trace_DEBUG, "Mailbox is in RECEPTION\n\r");
208
                    trace_LOG( trace_DEBUG, "Length 0x%X\n\r", (can_msr>>16)&0xF);
209
                    trace_LOG( trace_DEBUG, "CAN_MB_MID 0x%X\n\r", ((*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x08+(0x20*numMailbox)))&AT91C_CAN_MIDvA)>>18));
210
 
211
                    trace_LOG( trace_DEBUG, "can_number %d\n\r", can_number);
212
                    if( can_number == 0 ) {
213
                        //CAN_MB_MDLx
214
                        pCAN0Transfer->data_low_reg =
215
                           (*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x14+(0x20*numMailbox))));
216
                        //CAN_MB_MDHx
217
                        pCAN0Transfer->data_high_reg =
218
                           (*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x18+(0x20*numMailbox))));
219
                        pCAN0Transfer->size = (can_msr>>16)&0xF;
220
                        pCAN0Transfer->mailbox_number = numMailbox;
221
                        state0 = CAN_IDLE;
222
                    }
223
#ifdef AT91C_BASE_CAN1
224
                    else {
225
                        //CAN_MB_MDLx
226
                        pCAN1Transfer->data_low_reg =
227
                           (*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x14+(0x20*numMailbox))));
228
                        //CAN_MB_MDHx
229
                        pCAN1Transfer->data_high_reg =
230
                           (*(unsigned int*)((unsigned int)CAN_Mailbox+(unsigned int)(0x18+(0x20*numMailbox))));
231
                        pCAN1Transfer->size = (can_msr>>16)&0xF;
232
                        pCAN1Transfer->mailbox_number = numMailbox;
233
                        state1 = CAN_IDLE;
234
                    }
235
#endif
236
                    // Message Data has been received
237
                    pCan_mcr = (unsigned int*)((unsigned int)CAN_Mailbox+0x1C+(0x20*numMailbox));
238
                    *pCan_mcr = AT91C_CAN_MTCR;
239
 
240
                }
241
                else {
242
                    trace_LOG( trace_DEBUG, "Mailbox is in TRANSMIT\n\r");
243
                    trace_LOG( trace_DEBUG, "Length 0x%X\n\r", (can_msr>>16)&0xF);
244
                    trace_LOG( trace_DEBUG, "can_number %d\n\r", can_number);
245
                    if( can_number == 0 ) {
246
                        state0 = CAN_IDLE;
247
                    }
248
                    else {
249
                        state1 = CAN_IDLE;
250
                    }
251
                }
252
            }
253
        }
254
        if( can_number == 0 ) {
255
            pCAN0Transfer->state = state0;
256
        }
257
#ifdef AT91C_BASE_CAN1
258
        else {
259
            pCAN1Transfer->state = state1;
260
        }
261
#endif
262
    }
263
    if ((status&0xFFCF0000) != 0) {
264
        CAN_ErrorHandling(status, 0);
265
    }
266
}
267
 
268
//------------------------------------------------------------------------------
269
/// CAN 0 Interrupt handler
270
//------------------------------------------------------------------------------
271
static void CAN0_Handler(void)
272
{
273
    CAN_Handler( 0 );
274
}
275
 
276
//------------------------------------------------------------------------------
277
/// CAN 1 Interrupt handler
278
//------------------------------------------------------------------------------
279
#if defined AT91C_BASE_CAN1
280
static void CAN1_Handler(void)
281
{
282
    CAN_Handler( 1 );
283
}
284
#endif
285
 
286
//------------------------------------------------------------------------------
287
//         Global functions
288
//------------------------------------------------------------------------------
289
 
290
//------------------------------------------------------------------------------
291
/// Configure the corresponding mailbox
292
/// \param pTransfer can transfer structure
293
//------------------------------------------------------------------------------
294
void CAN_InitMailboxRegisters( CanTransfer *pTransfer )
295
{
296
    AT91PS_CAN    base_can;
297
    AT91PS_CAN_MB CAN_Mailbox;
298
 
299
    if( pTransfer->can_number == 0 ) {
300
        base_can = AT91C_BASE_CAN0;
301
        CAN_Mailbox = AT91C_BASE_CAN0_MB0;
302
    }
303
#ifdef AT91C_BASE_CAN1
304
    else {
305
        base_can = AT91C_BASE_CAN1;
306
        CAN_Mailbox = AT91C_BASE_CAN1_MB0;
307
    }
308
#endif
309
    CAN_Mailbox = (AT91PS_CAN_MB)((unsigned int)CAN_Mailbox+(unsigned int)(0x20*pTransfer->mailbox_number));
310
 
311
    pTransfer->mailbox_in_use |= 1<<(pTransfer->mailbox_number);
312
    // MailBox Control Register
313
    CAN_Mailbox->CAN_MB_MCR = 0x0;
314
    // MailBox Mode Register
315
    CAN_Mailbox->CAN_MB_MMR = 0x00;
316
    // CAN Message Acceptance Mask Register
317
    CAN_Mailbox->CAN_MB_MAM = pTransfer->acceptance_mask_reg;
318
    // MailBox ID Register
319
    // Disable the mailbox before writing to CAN_MIDx registers
320
    if( pTransfer->identifier != 0 ) {
321
        CAN_Mailbox->CAN_MB_MAM |= AT91C_CAN_MIDE;
322
        CAN_Mailbox->CAN_MB_MID = pTransfer->identifier;
323
    }
324
    else {
325
        CAN_Mailbox->CAN_MB_MAM &= ~AT91C_CAN_MIDE;
326
    }
327
    // MailBox Mode Register
328
    CAN_Mailbox->CAN_MB_MMR = pTransfer->mode_reg;
329
    // MailBox Data Low Register
330
    CAN_Mailbox->CAN_MB_MDL = pTransfer->data_low_reg;
331
    // MailBox Data High Register
332
    CAN_Mailbox->CAN_MB_MDH = pTransfer->data_high_reg;
333
    // MailBox Control Register
334
    CAN_Mailbox->CAN_MB_MCR = pTransfer->control_reg;
335
}
336
 
337
//------------------------------------------------------------------------------
338
/// Reset the MBx
339
//------------------------------------------------------------------------------
340
void CAN_ResetAllMailbox( void )
341
{
342
    unsigned char i;
343
 
344
#if defined (AT91C_BASE_CAN0_MB0)
345
    CAN_ResetTransfer( pCAN0Transfer );
346
    for( i=0; i<8; i++ ) {
347
        pCAN0Transfer->can_number = 0;
348
        pCAN0Transfer->mailbox_number = i;
349
        pCAN0Transfer->mode_reg = AT91C_CAN_MOT_DIS;
350
        pCAN0Transfer->acceptance_mask_reg = 0;
351
        pCAN0Transfer->identifier = 0;
352
        pCAN0Transfer->data_low_reg = 0x00000000;
353
        pCAN0Transfer->data_high_reg = 0x00000000;
354
        pCAN0Transfer->control_reg = 0x00000000;
355
        CAN_InitMailboxRegisters( pCAN0Transfer );
356
    }
357
#endif
358
#if defined (AT91C_BASE_CAN0_MB8)
359
    for( i=0; i<8; i++ ) {
360
        pCAN0Transfer->can_number = 0;
361
        pCAN0Transfer->mailbox_number = i+8;
362
        pCAN0Transfer->mode_reg = AT91C_CAN_MOT_DIS;
363
        pCAN0Transfer->acceptance_mask_reg = 0;
364
        pCAN0Transfer->identifier = 0;
365
        pCAN0Transfer->data_low_reg = 0x00000000;
366
        pCAN0Transfer->data_high_reg = 0x00000000;
367
        pCAN0Transfer->control_reg = 0x00000000;
368
        CAN_InitMailboxRegisters( pCAN0Transfer );
369
    }
370
#endif
371
 
372
#if defined (AT91C_BASE_CAN1_MB0)
373
    if( pCAN1Transfer != NULL ) {
374
        CAN_ResetTransfer( pCAN1Transfer );
375
        for( i=0; i<8; i++ ) {
376
            pCAN1Transfer->can_number = 1;
377
            pCAN1Transfer->mailbox_number = i;
378
            pCAN1Transfer->mode_reg = AT91C_CAN_MOT_DIS;
379
            pCAN1Transfer->acceptance_mask_reg = 0;
380
            pCAN1Transfer->identifier = 0;
381
            pCAN1Transfer->data_low_reg = 0x00000000;
382
            pCAN1Transfer->data_high_reg = 0x00000000;
383
            pCAN1Transfer->control_reg = 0x00000000;
384
            CAN_InitMailboxRegisters( pCAN1Transfer );
385
        }
386
    }
387
#endif
388
#if defined (AT91C_BASE_CAN1_MB8)
389
    if( pCAN1Transfer != NULL ) {
390
        for( i=0; i<8; i++ ) {
391
            pCAN1Transfer->can_number = 1;
392
            pCAN1Transfer->mailbox_number = i+8;
393
            pCAN1Transfer->mode_reg = AT91C_CAN_MOT_DIS;
394
            pCAN1Transfer->acceptance_mask_reg = 0;
395
            pCAN1Transfer->identifier = 0;
396
            pCAN1Transfer->data_low_reg = 0x00000000;
397
            pCAN1Transfer->data_high_reg = 0x00000000;
398
            pCAN1Transfer->control_reg = 0x00000000;
399
            CAN_InitMailboxRegisters( pCAN1Transfer );
400
        }
401
    }
402
#endif
403
 
404
}
405
 
406
//------------------------------------------------------------------------------
407
/// CAN reset Transfer descriptor
408
/// \param pTransfer can transfer structure
409
//------------------------------------------------------------------------------
410
void CAN_ResetTransfer( CanTransfer *pTransfer )
411
{
412
    pTransfer->state = CAN_IDLE;
413
    pTransfer->can_number = 0;
414
    pTransfer->mailbox_number = 0;
415
    pTransfer->test_can = 0;
416
    pTransfer->mode_reg = 0;
417
    pTransfer->acceptance_mask_reg = 0;
418
    pTransfer->identifier = 0;
419
    pTransfer->data_low_reg = 0;
420
    pTransfer->data_high_reg = 0;
421
    pTransfer->control_reg = 0;
422
    pTransfer->mailbox_in_use = 0;
423
    pTransfer->size = 0;
424
}
425
 
426
//------------------------------------------------------------------------------
427
/// Wait for CAN synchronisation
428
/// \return return 1 for good initialisation, otherwise return 0
429
//------------------------------------------------------------------------------
430
static unsigned char CAN_Synchronisation( void )
431
{
432
    unsigned int tick=0;
433
 
434
    trace_LOG( trace_INFO, "CAN_Synchronisation\n\r");
435
 
436
    pCAN0Transfer->test_can = AT91C_TEST_NOK;
437
#ifdef AT91C_BASE_CAN1
438
    if( pCAN1Transfer != NULL ) {
439
        pCAN1Transfer->test_can = AT91C_TEST_NOK;
440
    }
441
#endif
442
    // Enable CAN and Wait for WakeUp Interrupt
443
    AT91C_BASE_CAN0->CAN_IER = AT91C_CAN_WAKEUP;
444
    // CAN Controller Enable
445
    AT91C_BASE_CAN0->CAN_MR = AT91C_CAN_CANEN;
446
    // Enable Autobaud/Listen mode
447
    // dangerous, CAN not answer in this mode
448
 
449
     while( (pCAN0Transfer->test_can != AT91C_TEST_OK)
450
         && (tick < AT91C_CAN_TIMEOUT) ) {
451
        tick++;
452
    }
453
    if (tick == AT91C_CAN_TIMEOUT) {
454
        trace_LOG( trace_ERROR, "-E- CAN0 Initialisations FAILED\n\r");
455
        return 0;
456
    } else {
457
        trace_LOG( trace_INFO, "-I- CAN0 Initialisations Completed\n\r");
458
    }
459
 
460
#if defined AT91C_BASE_CAN1
461
    if( pCAN1Transfer != NULL ) {
462
        AT91C_BASE_CAN1->CAN_IER = AT91C_CAN_WAKEUP;
463
        // CAN Controller Enable
464
        AT91C_BASE_CAN1->CAN_MR = AT91C_CAN_CANEN;
465
 
466
        tick = 0;
467
        // Wait for WAKEUP flag raising <=> 11-recessive-bit were scanned by the transceiver
468
        while( ((pCAN1Transfer->test_can != AT91C_TEST_OK))
469
            && (tick < AT91C_CAN_TIMEOUT) ) {
470
            tick++;
471
        }
472
 
473
        if (tick == AT91C_CAN_TIMEOUT) {
474
            trace_LOG( trace_ERROR, "-E- CAN1 Initialisations FAILED\n\r");
475
            return 0;
476
        } else {
477
            trace_LOG( trace_INFO, "-I- CAN1 Initialisations Completed\n\r");
478
        }
479
    }
480
#endif
481
    return 1;
482
}
483
 
484
//------------------------------------------------------------------------------
485
/// Write a CAN transfer
486
/// \param pTransfer can transfer structure
487
/// \return return CAN_STATUS_SUCCESS if command passed, otherwise 
488
///         return CAN_STATUS_LOCKED
489
//------------------------------------------------------------------------------
490
unsigned char CAN_Write( CanTransfer *pTransfer )
491
{
492
    AT91PS_CAN base_can;
493
 
494
    if (pTransfer->state == CAN_RECEIVING)  {
495
        pTransfer->state = CAN_IDLE;
496
    }
497
 
498
    if (pTransfer->state != CAN_IDLE)  {
499
        return CAN_STATUS_LOCKED;
500
    }
501
 
502
    trace_LOG( trace_DEBUG, "CAN_Write\n\r");
503
    pTransfer->state = CAN_SENDING;
504
    if( pTransfer->can_number == 0 ) {
505
        base_can = AT91C_BASE_CAN0;
506
    }
507
#ifdef AT91C_BASE_CAN1
508
    else {
509
        base_can = AT91C_BASE_CAN1;
510
    }
511
#endif
512
    base_can->CAN_TCR = pTransfer->mailbox_in_use;
513
    base_can->CAN_IER = pTransfer->mailbox_in_use;
514
 
515
    return CAN_STATUS_SUCCESS;
516
 
517
}
518
 
519
 
520
//------------------------------------------------------------------------------
521
/// Read a CAN transfer
522
/// \param pTransfer can transfer structure
523
/// \return return CAN_STATUS_SUCCESS if command passed, otherwise 
524
///         return CAN_STATUS_LOCKED
525
//------------------------------------------------------------------------------
526
unsigned char CAN_Read( CanTransfer *pTransfer )
527
{
528
    AT91PS_CAN base_can;
529
 
530
    if (pTransfer->state != CAN_IDLE)  {
531
        return CAN_STATUS_LOCKED;
532
    }
533
 
534
    trace_LOG( trace_DEBUG, "CAN_Read\n\r");
535
    pTransfer->state = CAN_RECEIVING;
536
 
537
 
538
    if( pTransfer->can_number == 0 ) {
539
        base_can = AT91C_BASE_CAN0;
540
    }
541
#ifdef AT91C_BASE_CAN1
542
    else {
543
        base_can = AT91C_BASE_CAN1;
544
    }
545
#endif
546
    // enable interrupt
547
    base_can->CAN_IER = pTransfer->mailbox_in_use;
548
 
549
    return CAN_STATUS_SUCCESS;
550
}
551
 
552
//------------------------------------------------------------------------------
553
/// Test if CAN is in IDLE state
554
/// \param pTransfer can transfer structure
555
/// \return return 0 if CAN is in IDLE, otherwise return 1
556
//------------------------------------------------------------------------------
557
unsigned char CAN_IsInIdle( CanTransfer *pTransfer )
558
{
559
  return( pTransfer->state != CAN_IDLE );
560
}
561
 
562
//------------------------------------------------------------------------------
563
/// Basic CAN test without Interrupt
564
//------------------------------------------------------------------------------
565
void CAN_BasicTestSuiteWithoutInterrupt(void)
566
{
567
#if defined AT91C_BASE_CAN1
568
    unsigned int status;
569
    unsigned int tick=0;
570
 
571
    trace_LOG( trace_INFO, "Without Interrupt ");
572
    trace_LOG( trace_INFO, "CAN0 Mailbox 0 transmitting to CAN1 Mailbox 0\n\r");
573
    // Init CAN0 Mailbox 0, transmit
574
    CAN_ResetTransfer( pCAN0Transfer );
575
    pCAN0Transfer->can_number = 0;
576
    pCAN0Transfer->mailbox_number = 0;
577
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_TX | AT91C_CAN_PRIOR;
578
    pCAN0Transfer->acceptance_mask_reg = 0x00000000;
579
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x07<<18);
580
    pCAN0Transfer->data_low_reg = 0x11223344;
581
    pCAN0Transfer->data_high_reg = 0x01234567;
582
    pCAN0Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16));
583
    CAN_InitMailboxRegisters( pCAN0Transfer );
584
 
585
    // Init CAN1 Mailbox 0, receive, 
586
    CAN_ResetTransfer( pCAN1Transfer );
587
    pCAN1Transfer->can_number = 1;
588
    pCAN1Transfer->mailbox_number = 0;
589
    pCAN1Transfer->mode_reg = AT91C_CAN_MOT_RX;
590
    pCAN1Transfer->acceptance_mask_reg = AT91C_CAN_MIDvA | AT91C_CAN_MIDvB;
591
    pCAN1Transfer->identifier = AT91C_CAN_MIDvA & (0x07<<18);
592
    pCAN1Transfer->data_low_reg = 0x00000000;
593
    pCAN1Transfer->data_high_reg = 0x00000000;
594
    pCAN1Transfer->control_reg = 0x00000000;
595
    CAN_InitMailboxRegisters( pCAN1Transfer );
596
 
597
    // Transfer Request for Mailbox 0
598
    AT91C_BASE_CAN0->CAN_TCR = AT91C_CAN_MB0;
599
 
600
    tick = 0;
601
    do {
602
        // CAN Message Status Register
603
        status = AT91C_BASE_CAN0_MB0->CAN_MB_MSR;
604
    }
605
    while( !(status & AT91C_CAN_MRDY) && (++tick < AT91C_CAN_TIMEOUT) );
606
 
607
    if (tick == AT91C_CAN_TIMEOUT) {
608
        trace_LOG( trace_ERROR, "-E- Test FAILED\n\r");
609
    }
610
    else {
611
        trace_LOG( trace_DEBUG, "-I- Transfer completed: CAN1 Mailbox 0 MRDY flag has raised\n\r");
612
        if( AT91C_BASE_CAN0_MB0->CAN_MB_MDL != AT91C_BASE_CAN1_MB0->CAN_MB_MDL ) {
613
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
614
        }
615
        else if( AT91C_BASE_CAN0_MB0->CAN_MB_MDH != AT91C_BASE_CAN1_MB0->CAN_MB_MDH ) {
616
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
617
        }
618
        else {
619
            trace_LOG( trace_INFO, "Test passed\n\r");
620
        }
621
    }
622
 
623
    CAN_ResetAllMailbox();
624
 
625
    trace_LOG( trace_INFO, "Without Interrupt ");
626
    trace_LOG( trace_INFO, "CAN0 Mailboxes 1 & 2 transmitting to CAN1 Mailbox 15\n\r");
627
    // Init CAN0 Mailbox 1, transmit
628
    CAN_ResetTransfer( pCAN0Transfer );
629
    pCAN0Transfer->can_number = 0;
630
    pCAN0Transfer->mailbox_number = 1;
631
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_TX | AT91C_CAN_PRIOR;
632
    pCAN0Transfer->acceptance_mask_reg = 0x00000000;
633
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x09<<18);      // ID 9
634
    pCAN0Transfer->data_low_reg = 0xAABBCCDD;
635
    pCAN0Transfer->data_high_reg = 0xCAFEDECA;
636
    pCAN0Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16)); // Mailbox Data Length Code
637
    CAN_InitMailboxRegisters( pCAN0Transfer );
638
 
639
    // Init CAN0 Mailbox 2, transmit
640
    pCAN0Transfer->can_number = 0;
641
    pCAN0Transfer->mailbox_number = 2;
642
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_TX | (AT91C_CAN_PRIOR-(1<<16));
643
    pCAN0Transfer->acceptance_mask_reg = 0x00000000;
644
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x0A<<18);      // ID 10
645
    pCAN0Transfer->data_low_reg = 0x55667788;
646
    pCAN0Transfer->data_high_reg = 0x99AABBCC;
647
    pCAN0Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16)); // Mailbox Data Length Code
648
    CAN_InitMailboxRegisters( pCAN0Transfer );
649
 
650
    // Init CAN1 Mailbox 15, reception with overwrite
651
    CAN_ResetTransfer( pCAN1Transfer );
652
    pCAN1Transfer->can_number = 1;
653
    pCAN1Transfer->mailbox_number = 15;
654
    pCAN1Transfer->mode_reg = AT91C_CAN_MOT_RXOVERWRITE;
655
    pCAN1Transfer->acceptance_mask_reg = 0;
656
    pCAN1Transfer->identifier = 0x0;
657
    pCAN1Transfer->data_low_reg = 0x00000000;
658
    pCAN1Transfer->data_high_reg = 0x00000000;
659
    pCAN1Transfer->control_reg = 0x00000000;
660
    CAN_InitMailboxRegisters( pCAN1Transfer );
661
 
662
    // Ask Transmissions on Mailbox 1 & 2 --> AT91C_CAN_MRDY & AT91C_CAN_MMI raises for Mailbox 15 CAN_MB_SR
663
    AT91C_BASE_CAN0->CAN_TCR = AT91C_CAN_MB1 | AT91C_CAN_MB2;
664
 
665
    // Wait for Last Transmit Mailbox
666
    tick = 0;
667
    do  {
668
        status = AT91C_BASE_CAN1_MB15->CAN_MB_MSR;
669
    }
670
    while( !(status & AT91C_CAN_MMI) && (++tick < AT91C_CAN_TIMEOUT) );
671
 
672
    if (tick == AT91C_CAN_TIMEOUT) {
673
    }
674
    else {
675
        trace_LOG( trace_DEBUG, "-I- Transfer completed: CAN1 Mailbox 15 MRDY and MMI flags have raised\n\r");
676
        if( AT91C_BASE_CAN0_MB1->CAN_MB_MDL != AT91C_BASE_CAN1_MB15->CAN_MB_MDL ) {
677
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
678
        }
679
        else if( AT91C_BASE_CAN0_MB1->CAN_MB_MDH != AT91C_BASE_CAN1_MB15->CAN_MB_MDH ) {
680
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
681
        }
682
        else {
683
            trace_LOG( trace_INFO, "Test passed\n\r");
684
        }
685
    }
686
 
687
    CAN_ResetAllMailbox();
688
    trace_LOG( trace_INFO, "Without Interrupt ");
689
    trace_LOG( trace_INFO, "CAN0 Mailboxes 1 & 2 transmitting to CAN1 Mailbox 15\n\r");
690
    // Init CAN0 Mailbox 1, transmit
691
    CAN_ResetTransfer( pCAN0Transfer );
692
    pCAN0Transfer->can_number = 0;
693
    pCAN0Transfer->mailbox_number = 1;
694
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_TX | AT91C_CAN_PRIOR;
695
    pCAN0Transfer->acceptance_mask_reg = 0x00000000;
696
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x09<<18);      // ID 9
697
    pCAN0Transfer->data_low_reg = 0xAABBCCDD;
698
    pCAN0Transfer->data_high_reg = 0xCAFEDECA;
699
    pCAN0Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16)); // Mailbox Data Length Code
700
    CAN_InitMailboxRegisters( pCAN0Transfer );
701
 
702
    // Init CAN0 Mailbox 2, transmit
703
    pCAN0Transfer->can_number = 0;
704
    pCAN0Transfer->mailbox_number = 2;
705
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_TX | (AT91C_CAN_PRIOR-(1<<16));
706
    pCAN0Transfer->acceptance_mask_reg = 0x00000000;
707
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x0A<<18);      // ID 10
708
    pCAN0Transfer->data_low_reg = 0x55667788;
709
    pCAN0Transfer->data_high_reg = 0x99AABBCC;
710
    pCAN0Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16)); // Mailbox Data Length Code
711
    CAN_InitMailboxRegisters( pCAN0Transfer );
712
 
713
    // Init CAN1 Mailbox 15, reception with overwrite
714
    CAN_ResetTransfer( pCAN1Transfer );
715
    pCAN1Transfer->can_number = 1;
716
    pCAN1Transfer->mailbox_number = 15;
717
    pCAN1Transfer->mode_reg = AT91C_CAN_MOT_RX;
718
    pCAN1Transfer->acceptance_mask_reg = 0;
719
    pCAN1Transfer->identifier = 0x0;
720
    pCAN1Transfer->data_low_reg = 0x00000000;
721
    pCAN1Transfer->data_high_reg = 0x00000000;
722
    pCAN1Transfer->control_reg = 0x00000000;
723
    CAN_InitMailboxRegisters( pCAN1Transfer );
724
 
725
    // Ask Transmissions on Mailbox 1 & 2 --> AT91C_CAN_MRDY & AT91C_CAN_MMI raises for Mailbox 15 CAN_MB_SR
726
    AT91C_BASE_CAN0->CAN_TCR = AT91C_CAN_MB1 | AT91C_CAN_MB2;
727
 
728
    // Wait for Last Transmit Mailbox
729
    tick = 0;
730
    do  {
731
        status = AT91C_BASE_CAN1_MB15->CAN_MB_MSR;
732
    }
733
    while( !(status & AT91C_CAN_MMI) && (++tick < AT91C_CAN_TIMEOUT) );
734
 
735
    if (tick == AT91C_CAN_TIMEOUT) {
736
    trace_LOG( trace_ERROR, "-E- Test FAILED\n\r");
737
    }
738
    else {
739
        trace_LOG( trace_DEBUG, "Transfer completed: CAN1 Mailbox 15 MRDY and MMI flags have raised\n\r");
740
        trace_LOG( trace_DEBUG, "MB_MDL: 0x%X\n\r", AT91C_BASE_CAN1_MB15->CAN_MB_MDL);
741
        trace_LOG( trace_DEBUG, "MB_MDLH: 0x%X\n\r", AT91C_BASE_CAN1_MB15->CAN_MB_MDH);
742
        if( AT91C_BASE_CAN0_MB2->CAN_MB_MDL != AT91C_BASE_CAN1_MB15->CAN_MB_MDL ) {
743
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
744
        }
745
        else if( AT91C_BASE_CAN0_MB2->CAN_MB_MDH != AT91C_BASE_CAN1_MB15->CAN_MB_MDH ) {
746
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
747
        }
748
        else {
749
            trace_LOG( trace_INFO, "Test passed\n\r");
750
        }
751
    }
752
 
753
    CAN_ResetAllMailbox();
754
    trace_LOG( trace_INFO, "Without Interrupt ");
755
    trace_LOG( trace_INFO, "CAN0 Mailbox 3 asking for CAN1 Mailbox 3 transmission\n\r");
756
    // Init CAN0 Mailbox 3, consumer mailbox
757
    // Sends a remote frame and waits for an answer
758
    CAN_ResetTransfer( pCAN0Transfer );
759
    pCAN0Transfer->can_number = 0;
760
    pCAN0Transfer->mailbox_number = 3;
761
    pCAN0Transfer->mode_reg = AT91C_CAN_MOT_CONSUMER | AT91C_CAN_PRIOR;
762
    pCAN0Transfer->acceptance_mask_reg = AT91C_CAN_MIDvA | AT91C_CAN_MIDvB;
763
    pCAN0Transfer->identifier = AT91C_CAN_MIDvA & (0x0B<<18);     // ID 11
764
    pCAN0Transfer->data_low_reg = 0x00000000;
765
    pCAN0Transfer->data_high_reg = 0x00000000;
766
    pCAN0Transfer->control_reg = 0x00000000;
767
    CAN_InitMailboxRegisters( pCAN0Transfer );
768
 
769
    // Init CAN1 Mailbox 3, porducer mailbox
770
    // Waits to receive a Remote Frame before sending its contents
771
    CAN_ResetTransfer( pCAN1Transfer );
772
    pCAN1Transfer->can_number = 1;
773
    pCAN1Transfer->mailbox_number = 3;
774
    pCAN1Transfer->mode_reg = AT91C_CAN_MOT_PRODUCER | AT91C_CAN_PRIOR;
775
    pCAN1Transfer->acceptance_mask_reg = 0;
776
    pCAN1Transfer->identifier = AT91C_CAN_MIDvA & (0x0B<<18);     // ID 11
777
    pCAN1Transfer->data_low_reg = 0xEEDDFF00;
778
    pCAN1Transfer->data_high_reg = 0x34560022;
779
    pCAN1Transfer->control_reg = (AT91C_CAN_MDLC & (0x8<<16));
780
    CAN_InitMailboxRegisters( pCAN1Transfer );
781
 
782
    // Ask Transmissions on Mailbox 3 --> AT91C_CAN_MRDY raises for Mailbox 3 CAN_MB_SR
783
    AT91C_BASE_CAN1->CAN_TCR = AT91C_CAN_MB3;
784
    AT91C_BASE_CAN0->CAN_TCR = AT91C_CAN_MB3;
785
 
786
    // Wait for Last Transmit Mailbox
787
    tick = 0;
788
    do  {
789
        status = AT91C_BASE_CAN0_MB3->CAN_MB_MSR;
790
    }
791
    while( !(status & AT91C_CAN_MRDY) && (++tick < AT91C_CAN_TIMEOUT) );
792
 
793
    if (tick == AT91C_CAN_TIMEOUT) {
794
        trace_LOG( trace_ERROR, "-E- Test FAILED\n\r");
795
    }
796
    else {
797
        trace_LOG( trace_DEBUG, "-I- Transfer Completed: CAN0 & CAN1 Mailboxes 3 MRDY flags have raised\n\r");
798
        if( AT91C_BASE_CAN0_MB3->CAN_MB_MDL != AT91C_BASE_CAN1_MB3->CAN_MB_MDL ) {
799
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
800
        }
801
        else if( AT91C_BASE_CAN0_MB3->CAN_MB_MDH != AT91C_BASE_CAN1_MB3->CAN_MB_MDH ) {
802
            trace_LOG( trace_ERROR, "-E- Data Corrupted\n\r");
803
        }
804
        else {
805
            trace_LOG( trace_INFO, "Test passed\n\r");
806
        }
807
    }
808
#endif // AT91C_BASE_CAN1
809
 
810
  return;
811
}
812
 
813
 
814
//------------------------------------------------------------------------------
815
/// Disable CAN and enter in low power
816
//------------------------------------------------------------------------------
817
void CAN_disable( void )
818
{
819
    // Disable the interrupt on the interrupt controller
820
    AIC_DisableIT(AT91C_ID_CAN0);
821
    // disable all IT
822
    AT91C_BASE_CAN0->CAN_IDR = 0x1FFFFFFF;
823
#if defined AT91C_BASE_CAN1
824
    AIC_DisableIT(AT91C_ID_CAN1);
825
    // disable all IT
826
    AT91C_BASE_CAN1->CAN_IDR = 0x1FFFFFFF;
827
#endif
828
 
829
    // Enable Low Power mode
830
    AT91C_BASE_CAN0->CAN_MR |= AT91C_CAN_LPM;
831
 
832
    // Disable CANs Transceivers
833
    // Enter standby mode
834
    PIO_Set(&pin_can_transceiver_rs);
835
#if defined (PIN_CAN_TRANSCEIVER_RXEN)
836
    // Enable ultra Low Power mode
837
    PIO_Clear(&pin_can_transceiver_rxen);
838
#endif
839
 
840
    // Disable clock for CAN PIO
841
    AT91C_BASE_PMC->PMC_PCDR = (1 << AT91C_ID_PIOA);
842
 
843
    // Disable the CAN0 controller peripheral clock
844
    AT91C_BASE_PMC->PMC_PCDR = (1 << AT91C_ID_CAN0);
845
 
846
}
847
 
848
//------------------------------------------------------------------------------
849
/// baudrate calcul
850
/// \param base_CAN CAN base address
851
/// \param baudrate Baudrate value
852
///                 allowed values: 1000, 800, 500, 250, 125, 50, 25, 10
853
/// \return return 1 in success, otherwise return 0
854
//------------------------------------------------------------------------------
855
unsigned char CAN_BaudRateCalculate( AT91PS_CAN   base_CAN,
856
                                     unsigned int baudrate )
857
{
858
    unsigned int BRP;
859
    unsigned int PROPAG;
860
    unsigned int PHASE1;
861
    unsigned int PHASE2;
862
    unsigned int SJW;
863
    unsigned int t1t2;
864
 
865
    base_CAN->CAN_BR = 0;
866
 
867
    BRP = (BOARD_MCK / (baudrate*1000*16))-1;
868
    //trace_LOG( trace_DEBUG, "BRP = 0x%X\n\r", BRP);
869
    // timing Delay:
870
    // Delay Bus Driver: 50 ns
871
    // Delay Receiver:   30 ns
872
    // Delay Bus Line:  110 ns
873
    if( (16*baudrate*2*(50+30+110)/1000000) >= 1) {
874
        PROPAG = (16*baudrate*2*(50+30+110)/1000000)-1;
875
    }
876
    else {
877
        PROPAG = 0;
878
    }
879
    //trace_LOG( trace_DEBUG, "PROPAG = 0x%X\n\r", PROPAG);
880
 
881
    t1t2 = 15-(PROPAG+1);
882
    //trace_LOG( trace_DEBUG, "t1t2 = 0x%X\n\r", t1t2);
883
 
884
    if( (t1t2 & 0x01) == 0x01 ) {
885
        // ODD
886
        //trace_LOG( trace_DEBUG, "ODD\n\r");
887
        PHASE1 = ((t1t2-1)/2)-1;
888
        PHASE2 = PHASE1+1;
889
    }
890
    else {
891
        // EVEN
892
        //trace_LOG( trace_DEBUG, "EVEN\n\r");
893
        PHASE1 = (t1t2/2)-1;
894
        PHASE2 = PHASE1;
895
    }
896
    //trace_LOG( trace_DEBUG, "PHASE1 = 0x%X\n\r", PHASE1);
897
    //trace_LOG( trace_DEBUG, "PHASE2 = 0x%X\n\r", PHASE2);
898
 
899
    if( 1 > (4/(PHASE1+1)) ) {
900
        //trace_LOG( trace_DEBUG, "4*Tcsc\n\r");
901
        SJW = 3;
902
    }
903
    else {
904
        //trace_LOG( trace_DEBUG, "Tphs1\n\r");
905
        SJW = PHASE1;
906
    }
907
    //trace_LOG( trace_DEBUG, "SJW = 0x%X\n\r", SJW);
908
    // Verif
909
    if( BRP == 0 ) {
910
        trace_LOG( trace_DEBUG, "BRP = 0 is not authorized\n\r");
911
        return 0;
912
    }
913
    if( (PROPAG + PHASE1 + PHASE2) != 12 ) {
914
        trace_LOG( trace_DEBUG, "(PROPAG + PHASE1 + PHASE2) != 12\n\r");
915
        return 0;
916
    }
917
    base_CAN->CAN_BR = (AT91C_CAN_PHASE2 & (PHASE2 <<  0))
918
                     + (AT91C_CAN_PHASE1 & (PHASE1 <<  4))
919
                     + (AT91C_CAN_PROPAG & (PROPAG <<  8))
920
                     + (AT91C_CAN_SYNC   & (SJW << 12))
921
                     + (AT91C_CAN_BRP    & (BRP << 16))
922
                     + (AT91C_CAN_SMP    & (0 << 24));
923
    return 1;
924
 
925
}
926
 
927
//------------------------------------------------------------------------------
928
//------------------------------------------------------------------------------
929
//------------------------------------------------------------------------------
930
/// Init of the CAN peripheral
931
/// \param baudrate Baudrate value
932
///                 allowed values: 1000, 800, 500, 250, 125, 50, 25, 10
933
/// \param canTransfer0 CAN0 structure transfer
934
/// \param canTransfer1 CAN1 structure transfer
935
/// \return return 1 if CAN has good baudrate and CAN is synchronized, 
936
///         otherwise return 0
937
//------------------------------------------------------------------------------
938
unsigned char CAN_Init( unsigned int baudrate,
939
                        CanTransfer *canTransfer0,
940
                        CanTransfer *canTransfer1 )
941
{
942
    unsigned char ret;
943
 
944
    // CAN Transmit Serial Data
945
#if defined (PINS_CAN_TRANSCEIVER_TXD)
946
    PIO_Configure(pins_can_transceiver_txd, PIO_LISTSIZE(pins_can_transceiver_txd));
947
#endif
948
#if defined (PINS_CAN_TRANSCEIVER_RXD)
949
    // CAN Receive Serial Data
950
    PIO_Configure(pins_can_transceiver_rxd, PIO_LISTSIZE(pins_can_transceiver_rxd));
951
#endif
952
    // CAN RS
953
    PIO_Configure(&pin_can_transceiver_rs, PIO_LISTSIZE(pin_can_transceiver_rs));
954
#if defined (PIN_CAN_TRANSCEIVER_RXEN)
955
    // CAN RXEN
956
    PIO_Configure(&pin_can_transceiver_rxen, PIO_LISTSIZE(pin_can_transceiver_rxen));
957
#endif
958
 
959
    // Enable clock for CAN PIO
960
    AT91C_BASE_PMC->PMC_PCER = (1 << AT91C_ID_PIOA);
961
 
962
    // Enable the CAN0 controller peripheral clock
963
    AT91C_BASE_PMC->PMC_PCER = (1 << AT91C_ID_CAN0);
964
 
965
    // disable all IT
966
    AT91C_BASE_CAN0->CAN_IDR = 0x1FFFFFFF;
967
 
968
    // Enable CANs Transceivers
969
#if defined (PIN_CAN_TRANSCEIVER_RXEN)
970
    // Disable ultra Low Power mode
971
    PIO_Set(&pin_can_transceiver_rxen);
972
#endif
973
    // Normal Mode (versus Standby mode)
974
    PIO_Clear(&pin_can_transceiver_rs);
975
 
976
    // Configure the AIC for CAN interrupts
977
    AIC_ConfigureIT(AT91C_ID_CAN0, AT91C_AIC_PRIOR_HIGHEST, CAN0_Handler);
978
 
979
    // Enable the interrupt on the interrupt controller
980
    AIC_EnableIT(AT91C_ID_CAN0);
981
 
982
    if( CAN_BaudRateCalculate(AT91C_BASE_CAN0, baudrate) == 0 ) {
983
        // Baudrate problem
984
        trace_LOG( trace_DEBUG, "Baudrate CAN0 problem\n\r");
985
        return 0;
986
    }
987
 
988
    pCAN0Transfer = canTransfer0;
989
 
990
#if defined AT91C_BASE_CAN1
991
    if( canTransfer1 != NULL ) {
992
        pCAN1Transfer = canTransfer1;
993
        // Enable CAN1 Clocks
994
        AT91C_BASE_PMC->PMC_PCER = (1 << AT91C_ID_CAN1);
995
 
996
        // disable all IT
997
        AT91C_BASE_CAN1->CAN_IDR = 0x1FFFFFFF;
998
 
999
        // Configure the AIC for CAN interrupts
1000
        AIC_ConfigureIT(AT91C_ID_CAN1, AT91C_AIC_PRIOR_HIGHEST, CAN1_Handler);
1001
 
1002
        // Enable the interrupt on the interrupt controller
1003
        AIC_EnableIT(AT91C_ID_CAN1);
1004
 
1005
        if( CAN_BaudRateCalculate(AT91C_BASE_CAN1, baudrate) == 0 ) {
1006
            // Baudrate problem
1007
            trace_LOG( trace_DEBUG, "Baudrate CAN1 problem\n\r");
1008
            return 0;
1009
        }
1010
    }
1011
#endif
1012
    // Reset all mailbox
1013
    CAN_ResetAllMailbox();
1014
 
1015
    // Enable the interrupt with all error cases
1016
    AT91C_BASE_CAN0->CAN_IER =  AT91C_CAN_CERR  // (CAN) CRC Error
1017
                             |  AT91C_CAN_SERR  // (CAN) Stuffing Error
1018
                             |  AT91C_CAN_BERR  // (CAN) Bit Error
1019
                             |  AT91C_CAN_FERR  // (CAN) Form Error
1020
                             |  AT91C_CAN_AERR; // (CAN) Acknowledgment Error
1021
 
1022
#if defined AT91C_BASE_CAN1
1023
    if( canTransfer1 != NULL ) {
1024
        AT91C_BASE_CAN1->CAN_IER =  AT91C_CAN_CERR  // (CAN) CRC Error
1025
                                 |  AT91C_CAN_SERR  // (CAN) Stuffing Error
1026
                                 |  AT91C_CAN_BERR  // (CAN) Bit Error
1027
                                 |  AT91C_CAN_FERR  // (CAN) Form Error
1028
                                 |  AT91C_CAN_AERR; // (CAN) Acknowledgment Error
1029
    }
1030
#endif
1031
 
1032
    // Wait for CAN synchronisation
1033
    if( CAN_Synchronisation( ) == 1 ) {
1034
        ret = 1;
1035
    }
1036
    else {
1037
        ret = 0;
1038
    }
1039
 
1040
    return ret;
1041
}
1042
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.