Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependents: test-lpc1768 oldheating gps motorhome ... more
can/can.c@71:2f8af23950de, 2022-06-03 (annotated)
- Committer:
- andrewboyson
- Date:
- Fri Jun 03 11:51:13 2022 +0000
- Revision:
- 71:2f8af23950de
Added can module
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
andrewboyson | 71:2f8af23950de | 1 | |
andrewboyson | 71:2f8af23950de | 2 | #include "log.h" |
andrewboyson | 71:2f8af23950de | 3 | #include "mstimer.h" |
andrewboyson | 71:2f8af23950de | 4 | |
andrewboyson | 71:2f8af23950de | 5 | #define AFMR *((volatile unsigned *)0x4003C000) // Acceptance Filter Mode Register |
andrewboyson | 71:2f8af23950de | 6 | |
andrewboyson | 71:2f8af23950de | 7 | #define CAN2MOD *((volatile unsigned *)0x40048000) // CAN Mode register |
andrewboyson | 71:2f8af23950de | 8 | #define CAN2CMR *((volatile unsigned *)0x40048004) // CAN Command register |
andrewboyson | 71:2f8af23950de | 9 | #define CAN2GSR *((volatile unsigned *)0x40048008) // CAN Global Status register |
andrewboyson | 71:2f8af23950de | 10 | #define CAN2ICR *((volatile unsigned *)0x4004800C) // CAN Interrupt and Capture Register |
andrewboyson | 71:2f8af23950de | 11 | #define CAN2IER *((volatile unsigned *)0x40048010) // CAN Interrupt Enable Register |
andrewboyson | 71:2f8af23950de | 12 | #define CAN2BTR *((volatile unsigned *)0x40048014) // CAN Bus Timing Register |
andrewboyson | 71:2f8af23950de | 13 | #define CAN2TFI1 *((volatile unsigned *)0x40048030) // CAN Transmit Frame Information register |
andrewboyson | 71:2f8af23950de | 14 | #define CAN2TID1 *((volatile unsigned *)0x40048034) // CAN Transmit Identifier Register |
andrewboyson | 71:2f8af23950de | 15 | #define CAN2TDA1 *((volatile unsigned *)0x40048038) // CAN Transmit Data Register A |
andrewboyson | 71:2f8af23950de | 16 | #define CAN2TDB1 *((volatile unsigned *)0x4004803C) // CAN Transmit Data Register B |
andrewboyson | 71:2f8af23950de | 17 | #define CAN2RFS *((volatile unsigned *)0x40048020) // CAN Receive Frame Status register |
andrewboyson | 71:2f8af23950de | 18 | #define CAN2RID *((volatile unsigned *)0x40048024) // CAN Receive Identifier register |
andrewboyson | 71:2f8af23950de | 19 | #define CAN2RDA *((volatile unsigned *)0x40048028) // CAN Receive Data register A |
andrewboyson | 71:2f8af23950de | 20 | #define CAN2RDB *((volatile unsigned *)0x4004802C) // CAN Receive Data register B |
andrewboyson | 71:2f8af23950de | 21 | |
andrewboyson | 71:2f8af23950de | 22 | void (*CanReceive)(uint16_t id, int length, uint32_t dataA, uint32_t dataB); |
andrewboyson | 71:2f8af23950de | 23 | void CanInit() |
andrewboyson | 71:2f8af23950de | 24 | { |
andrewboyson | 71:2f8af23950de | 25 | LogTime("Can init started\r\n"); |
andrewboyson | 71:2f8af23950de | 26 | /* |
andrewboyson | 71:2f8af23950de | 27 | 00: BRP = 95 : Clock is 96 / 4 = 24MHz and we want 1.000MHz so prescale by BRP+1 = 24: BRP = 23. |
andrewboyson | 71:2f8af23950de | 28 | 14: SJW = 3 : 4 can clocks |
andrewboyson | 71:2f8af23950de | 29 | 16: TESG1 = 4 : 5 can clocks |
andrewboyson | 71:2f8af23950de | 30 | 20: TESG2 = 3 : 4 can clocks |
andrewboyson | 71:2f8af23950de | 31 | */ |
andrewboyson | 71:2f8af23950de | 32 | CAN2BTR = 0; |
andrewboyson | 71:2f8af23950de | 33 | CAN2BTR |= 23 << 00; |
andrewboyson | 71:2f8af23950de | 34 | CAN2BTR |= 3 << 14; |
andrewboyson | 71:2f8af23950de | 35 | CAN2BTR |= 4 << 16; |
andrewboyson | 71:2f8af23950de | 36 | CAN2BTR |= 3 << 20; |
andrewboyson | 71:2f8af23950de | 37 | |
andrewboyson | 71:2f8af23950de | 38 | AFMR |= 1 << 1; //Accept all messages |
andrewboyson | 71:2f8af23950de | 39 | |
andrewboyson | 71:2f8af23950de | 40 | CAN2MOD = 0; //Controller to operating mode |
andrewboyson | 71:2f8af23950de | 41 | } |
andrewboyson | 71:2f8af23950de | 42 | void CanSend(uint16_t id, int length, uint32_t dataA, uint32_t dataB) |
andrewboyson | 71:2f8af23950de | 43 | { |
andrewboyson | 71:2f8af23950de | 44 | if (length > 8) length = 8; |
andrewboyson | 71:2f8af23950de | 45 | CAN2CMR |= 1 << 5; //STB1 Select Tx Buffer 1 |
andrewboyson | 71:2f8af23950de | 46 | CAN2TFI1 = 0; |
andrewboyson | 71:2f8af23950de | 47 | CAN2TFI1 |= length << 16; //DLC Data Length Code |
andrewboyson | 71:2f8af23950de | 48 | CAN2TFI1 |= 0 << 30; //RTR Remote TRansmission |
andrewboyson | 71:2f8af23950de | 49 | CAN2TFI1 |= 0 << 31; // FF Extended frame (0 = 11 bit id; 1 = 29 bit id) |
andrewboyson | 71:2f8af23950de | 50 | CAN2TID1 = id; |
andrewboyson | 71:2f8af23950de | 51 | CAN2TDA1 = dataA; |
andrewboyson | 71:2f8af23950de | 52 | CAN2TDB1 = dataB; |
andrewboyson | 71:2f8af23950de | 53 | CAN2CMR |= 1 << 0; //TR Transmission Request |
andrewboyson | 71:2f8af23950de | 54 | } |
andrewboyson | 71:2f8af23950de | 55 | void CanMain() |
andrewboyson | 71:2f8af23950de | 56 | { |
andrewboyson | 71:2f8af23950de | 57 | if (CAN2GSR & 0x01) //RBS Receive Buffer Status - At least one complete message is available in CANxRFS CANxRID CANxRDA CANxRDB |
andrewboyson | 71:2f8af23950de | 58 | { |
andrewboyson | 71:2f8af23950de | 59 | uint16_t id = CAN2RID & 0x3FF; |
andrewboyson | 71:2f8af23950de | 60 | int length = (CAN2RFS >> 16) & 0xF; |
andrewboyson | 71:2f8af23950de | 61 | CanReceive(id, length, CAN2RDA, CAN2RDB); |
andrewboyson | 71:2f8af23950de | 62 | CAN2CMR |= 1 << 2; //RRB Release Receive Buffer |
andrewboyson | 71:2f8af23950de | 63 | } |
andrewboyson | 71:2f8af23950de | 64 | } |