Skyward boardcore
Loading...
Searching...
No Matches
CanProtocol.h
Go to the documentation of this file.
1/* Copyright (c) 2022 Skyward Experimental Rocketry
2 * Author: Federico Mandelli
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20 * THE SOFTWARE.
21 */
22
23#pragma once
24
27#include <utils/Debug.h>
29
30#include "CanProtocolData.h"
31#include "CanProtocolTypes.h"
32
33namespace Boardcore
34{
35
36namespace Canbus
37{
38
49{
50 using MsgHandler = std::function<void(const CanMessage& data)>;
51
52public:
58 CanProtocol(CanbusDriver* can, MsgHandler onReceive,
59 miosix::Priority threadPriority);
60
66 bool start();
67
71 bool isStarted();
72
76 void stop();
77
86 bool addFilter(uint8_t src, uint64_t dst);
87
95 bool enqueueMsg(const CanMessage& msg);
96
101 bool enqueueEvent(uint8_t priority, uint8_t primaryType, uint8_t source,
102 uint8_t destination, uint8_t secondaryType);
103
109 bool enqueueSimplePacket(uint8_t priority, uint8_t primaryType,
110 uint8_t source, uint8_t destination,
111 uint8_t secondaryType, uint64_t payload);
112
121 template <typename T>
122 bool enqueueData(uint8_t priority, uint8_t primaryType, uint8_t source,
123 uint8_t destination, uint8_t secondaryType, const T& t);
124
125private:
134 void sendMessage(const CanMessage& msg);
135
147 void runReceiver();
148
153 void runSender();
154
160 static void rcvLauncher(void* arg);
161
167 static void sndLauncher(void* arg);
168
172 uint8_t byteForUint64(uint64_t number);
173
174 CanbusDriver* can;
175 MsgHandler onReceive;
176
177 // Threads
178 bool stopFlag = false;
179 bool sndStarted = false;
180 bool rcvStarted = false;
181
182 miosix::Thread* sndThread = nullptr;
183 miosix::Thread* rcvThread = nullptr;
184 miosix::Priority threadPriority;
185
186 SyncCircularBuffer<CanMessage, 10> outQueue;
187
188 PrintLogger logger = Logging::getLogger("canprotocol");
189};
190
191template <typename T>
192bool CanProtocol::enqueueData(uint8_t priority, uint8_t primaryType,
193 uint8_t source, uint8_t destination,
194 uint8_t secondaryType, const T& t)
195{
196 if (priority > 0xF || primaryType > 0x3F || source > 0xF ||
197 destination > 0xF || secondaryType > 0xF)
198 {
199 return false;
200 }
201
202 CanMessage msg = toCanMessage(t);
203
204 // clang-format off
205 msg.id = priority << static_cast<uint32_t>(CanProtocolShiftInformation::PRIORITY);
206 msg.id |= primaryType << static_cast<uint32_t>(CanProtocolShiftInformation::PRIMARY_TYPE);
207 msg.id |= source << static_cast<uint32_t>(CanProtocolShiftInformation::SOURCE);
208 msg.id |= destination << static_cast<uint32_t>(CanProtocolShiftInformation::DESTINATION);
209 msg.id |= secondaryType << static_cast<uint32_t>(CanProtocolShiftInformation::SECONDARY_TYPE);
210 // clang-format off
211
212 return enqueueMsg(msg);
213}
214
215} // namespace Canbus
216
217} // namespace Boardcore
Canbus protocol implementation.
Definition CanProtocol.h:49
CanProtocol(CanbusDriver *can, MsgHandler onReceive, miosix::Priority threadPriority)
Construct a new CanProtocol object.
bool enqueueMsg(const CanMessage &msg)
Non-blocking send function, puts the messages in a queue. Message is discarded if the queue is full.
bool start()
Start the receiving and sending threads.
bool enqueueData(uint8_t priority, uint8_t primaryType, uint8_t source, uint8_t destination, uint8_t secondaryType, const T &t)
Non-blocking send function for a generic data type.
bool isStarted()
Tells whether the driver was started.
bool enqueueSimplePacket(uint8_t priority, uint8_t primaryType, uint8_t source, uint8_t destination, uint8_t secondaryType, uint64_t payload)
Non-blocking send function for a simple packet with a payload of 1 can packet, useful to send generic...
bool addFilter(uint8_t src, uint64_t dst)
Adds a filter to the can peripheral to receive only messages from the given source and targeted to th...
void stop()
Stops sender and receiver threads.
bool enqueueEvent(uint8_t priority, uint8_t primaryType, uint8_t source, uint8_t destination, uint8_t secondaryType)
Non-blocking send function for an event (a message without payload).
Low level CanBus driver, with support for both peripherals (CAN1 and CAN2) on stm32f4 microcontroller...
Definition CanDriver.h:45
static PrintLogger getLogger(const string &name)
This file includes all the types the logdecoder script will decode.
Canbus::CanMessage toCanMessage(const PitotData &data)
Generic struct that contains a can protocol message.