Open FFBoard
Open source force feedback firmware
Loading...
Searching...
No Matches
CAN.h
Go to the documentation of this file.
1/*
2 * CAN.h
3 *
4 * Created on: 21.06.2021
5 * Author: Yannick
6 */
7
8#ifndef SRC_CAN_H_
9#define SRC_CAN_H_
10#include "target_constants.h"
11#ifdef CANBUS
12//#include "CanHandler.h"
13#include "main.h"
14#include <algorithm>
15#include <vector>
16#include "semaphore.hpp"
17#include <GPIOPin.h>
18#include "PersistentStorage.h"
19#include "CommandHandler.h"
20#include <span>
21
22
23class CANPort;
24
25#if defined(CAN1)
26#define CANTYPE_2B
27#define CAN_INITTYPE uint32_t
28#define CAN_MSGBUFSIZE 8
29#elif defined(FDCAN1)
30#define CANTYPE_FDCAN
31#define CAN_INITTYPE FDCAN_InitTypeDef&
32#define CAN_MSGBUFSIZE 64
33const uint8_t DLCtoBytes[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 12, 16, 20, 24, 32, 48, 64};
34#endif
35
36//class CANPort;
37
38
40public:
41 struct PresetEntry{// Helper for preset entries
42 const CAN_INITTYPE init;
43 const uint32_t speed;
44 const char* name;
45 constexpr PresetEntry(const CAN_INITTYPE init,const uint32_t speed,const char* name):init(init),speed(speed),name(name){}
46 };
47 constexpr CANPortHardwareConfig(const bool canChangeSpeed,std::span<const PresetEntry> presets_list)
48 : canChangeSpeed(canChangeSpeed),presets(presets_list){}
49
50 // Values
51 const bool canChangeSpeed;
52 constexpr PresetEntry getPreset(uint8_t idx) const {return PresetEntry(presets[std::min<uint8_t>(idx,presets.size())]);}
53 constexpr uint32_t speedToPreset(uint32_t speed) const {
54 auto it = std::find_if( presets.begin(), presets.end(), [&speed](const PresetEntry &e){return e.speed == speed;});
55 return it == presets.end() ? 255 : std::distance(presets.begin(),it);
56 }
57 constexpr uint32_t presetToSpeed(uint8_t preset) const {return presets[preset].speed;}
58 const std::span<const PresetEntry> presets; // Name for listing and init types for setup
59};
60
61typedef struct {
62 uint32_t id = 0;
63 uint32_t length = 0;
64 bool extId = false;
65 bool rtr = false;
66 bool fdcan = false; // Placeholder
67// bool fdcan_rateswitch = false;
69
71public:
72 uint32_t id = 0;
73 uint32_t length = 0;
74 bool extId = false;
75 bool rtr = false;
76 uint32_t filter = 0;
77 uint32_t timestamp = 0;
78 bool fdcan = false;
79// bool fdcan_rateswitch = false;
81#if defined(CANTYPE_2B)
82#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
83 CAN_msg_header_rx(CAN_RxHeaderTypeDef* hdr) : id(hdr->IDE==CAN_ID_STD ? hdr->StdId : hdr->ExtId),length(hdr->DLC),extId(hdr->IDE==CAN_ID_EXT),rtr(hdr->RTR == CAN_RTR_REMOTE),filter(hdr->FilterMatchIndex),timestamp(hdr->Timestamp),fdcan(false) {};
84#elif defined(CANTYPE_FDCAN)
85#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
86 CAN_msg_header_rx(FDCAN_RxHeaderTypeDef* hdr) : id(hdr->Identifier),length(DLCtoBytes[hdr->DataLength >> 16]),extId(hdr->FDFormat),rtr(hdr->RxFrameType == FDCAN_REMOTE_FRAME),filter(hdr->FilterIndex),timestamp(hdr->RxTimestamp),fdcan(hdr->FDFormat == FDCAN_FD_CAN) {};
87#endif
88 virtual ~CAN_msg_header_rx(){};
89};
90
91typedef struct{
92 uint8_t data[CAN_MSGBUFSIZE] = {0};
93 //CAN_TxHeaderTypeDef header = {0,0,0,CAN_RTR_DATA,8,(FunctionalState)0};
96
97// Unused?
98typedef struct{
99 uint8_t data[CAN_MSGBUFSIZE] = {0};
100 //CAN_RxHeaderTypeDef header = {0,0,0,0,0,0};
102 uint8_t fifo = 0;
103 uint32_t size(){return header.length;}
104} CAN_rx_msg;
105
109typedef struct {
110 uint32_t filter_id = 0;
111 uint32_t filter_mask = 0;
112 uint32_t buffer = 0; // FIFO index or fdcan buffer mode
113 bool active = true;
114 bool extid = false;
115// bool dedicated_buffer = false; // Not yet supported
116} CAN_filter;
117
118
119
120//template<class INIT>
121class CANPort : public PersistentStorage { // : public CanHandler if interrupt callbacks needed
122 static std::vector<CANPort*> canPorts;
123public:
124
125 CANPort(const CANPortHardwareConfig& presets,uint8_t instance = 0);
126 virtual ~CANPort();
127
128 // ---- Implement these in the CAN port ---
132 virtual bool start() = 0;
133
137 virtual bool stop() = 0;
138
139 virtual bool sendMessage(CAN_tx_msg& msg) = 0;
140 virtual bool sendMessage(CAN_msg_header_tx *pHeader, uint8_t aData[],uint32_t *pTxMailbox = nullptr) = 0;
144 virtual void abortTxRequests() = 0;
145
146 virtual int32_t addCanFilter(CAN_filter filter) = 0;
147 virtual void removeCanFilter(uint8_t filterId) = 0;
148
149 virtual void setSpeed(uint32_t speed) = 0;
150 virtual void setSpeedPreset(uint8_t preset) = 0;
151 virtual uint32_t getSpeed() = 0;
152 virtual uint8_t getSpeedPreset() = 0;
153
154 virtual void setSilentMode(bool silent) = 0;
155
156 virtual bool isWaiting();
157
158
159 // ---------------------------------------------
160
161 // Common implementations
162 virtual int32_t getPortUsers(){return portUsers;}
163 virtual void takePort(){
164 if(portUsers++ == 0){
165 start();
166 }
167 }
168 virtual void freePort(){
169 if(portUsers>0){
170 portUsers--;
171 }
172
173 if(portUsers == 0){
174 stop();
175 }
176 }
177 virtual void giveSemaphore(){
178 bool isIsr = inIsr();
179 BaseType_t taskWoken = 0;
180 if(isIsr)
181 this->semaphore.GiveFromISR(&taskWoken);
182 else
183 this->semaphore.Give();
184 isWaitingFlag = false;
185 portYIELD_FROM_ISR(taskWoken);
186 }
187 virtual bool takeSemaphore(uint32_t delay = portMAX_DELAY){
188 bool isIsr = inIsr();
189 BaseType_t taskWoken = 0;
190 bool success;
191 if(isIsr)
192 success = this->semaphore.TakeFromISR(&taskWoken);
193 else{
194 success = this->semaphore.Take(delay);
195 }
196 //isTakenFlag = true;
197 portYIELD_FROM_ISR(taskWoken);
198 return success;
199 }
200 static CANPort* handleToPort(void* handle);
201 virtual uint8_t speedToPreset(uint32_t speed){return presets.speedToPreset(speed);}
202 virtual uint32_t presetToSpeed(uint8_t preset){return presets.presetToSpeed(preset);}
203
204protected:
208 bool isWaitingFlag = false;
209 int32_t portUsers = 0;
210 virtual void* getHandle() = 0;
211};
212
213
214
215
216#endif /* SRC_CAN_H_ */
217#endif
const uint8_t DLCtoBytes[]
Definition CAN.h:33
CAN_msg_header_rx(CAN_RxHeaderTypeDef *hdr)
Definition CAN.h:83
CAN_msg_header_rx()
Definition CAN.h:80
uint32_t timestamp
Definition CAN.h:77
uint32_t filter
Definition CAN.h:76
virtual ~CAN_msg_header_rx()
Definition CAN.h:88
uint32_t id
Definition CAN.h:72
CAN_msg_header_rx(FDCAN_RxHeaderTypeDef *hdr)
Definition CAN.h:86
uint32_t length
Definition CAN.h:73
constexpr CANPortHardwareConfig(const bool canChangeSpeed, std::span< const PresetEntry > presets_list)
Definition CAN.h:47
const bool canChangeSpeed
Definition CAN.h:51
constexpr uint32_t presetToSpeed(uint8_t preset) const
Definition CAN.h:57
constexpr uint32_t speedToPreset(uint32_t speed) const
Definition CAN.h:53
constexpr PresetEntry getPreset(uint8_t idx) const
Definition CAN.h:52
const std::span< const PresetEntry > presets
Definition CAN.h:58
Definition CAN.h:121
virtual void * getHandle()=0
virtual void giveSemaphore()
Definition CAN.h:177
virtual uint8_t speedToPreset(uint32_t speed)
Gets preset index for a speed.
Definition CAN.h:201
virtual ~CANPort()
Definition CAN.cpp:19
virtual void freePort()
Definition CAN.h:168
virtual uint8_t getSpeedPreset()=0
cpp_freertos::BinarySemaphore configSem
Definition CAN.h:206
static CANPort * handleToPort(void *handle)
Definition CAN.cpp:23
virtual bool takeSemaphore(uint32_t delay=portMAX_DELAY)
Definition CAN.h:187
virtual void takePort()
Definition CAN.h:163
virtual bool start()=0
virtual bool isWaiting()
Definition CAN.cpp:33
virtual void setSpeedPreset(uint8_t preset)=0
virtual int32_t getPortUsers()
Definition CAN.h:162
cpp_freertos::BinarySemaphore semaphore
Definition CAN.h:205
const CANPortHardwareConfig & presets
CAN port presets for different speeds. Hardware dependent.
Definition CAN.h:207
virtual uint32_t getSpeed()=0
CANPort(const CANPortHardwareConfig &presets, uint8_t instance=0)
Definition CAN.cpp:16
bool isWaitingFlag
Definition CAN.h:208
virtual int32_t addCanFilter(CAN_filter filter)=0
virtual bool sendMessage(CAN_tx_msg &msg)=0
virtual void setSpeed(uint32_t speed)=0
int32_t portUsers
Definition CAN.h:209
virtual bool stop()=0
static std::vector< CANPort * > canPorts
Definition CAN.h:122
virtual void abortTxRequests()=0
virtual uint32_t presetToSpeed(uint8_t preset)
Gets speed for a preset index.
Definition CAN.h:202
virtual void removeCanFilter(uint8_t filterId)=0
virtual bool sendMessage(CAN_msg_header_tx *pHeader, uint8_t aData[], uint32_t *pTxMailbox=nullptr)=0
virtual void setSilentMode(bool silent)=0
static bool inIsr()
Definition cppmain.h:41
bool extid
Definition CAN.h:114
bool active
Definition CAN.h:113
uint32_t buffer
Definition CAN.h:112
uint32_t filter_mask
Definition CAN.h:111
uint32_t filter_id
Definition CAN.h:110
uint32_t length
Definition CAN.h:63
uint8_t fifo
Definition CAN.h:102
uint32_t size()
Definition CAN.h:103
uint8_t data[CAN_MSGBUFSIZE]
Definition CAN.h:99
CAN_msg_header_rx header
Definition CAN.h:101
CAN_msg_header_tx header
Definition CAN.h:94
uint8_t data[CAN_MSGBUFSIZE]
Definition CAN.h:92
Definition CAN.h:41
const char * name
Definition CAN.h:44
const uint32_t speed
Definition CAN.h:43
const CAN_INITTYPE init
Definition CAN.h:42
constexpr PresetEntry(const CAN_INITTYPE init, const uint32_t speed, const char *name)
Definition CAN.h:45