Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Ardupilot
GitHub Repository: Ardupilot/ardupilot
Path: blob/master/libraries/AP_CANManager/AP_SLCANIface.h
9692 views
1
/*
2
* This file is free software: you can redistribute it and/or modify it
3
* under the terms of the GNU General Public License as published by the
4
* Free Software Foundation, either version 3 of the License, or
5
* (at your option) any later version.
6
*
7
* This file is distributed in the hope that it will be useful, but
8
* WITHOUT ANY WARRANTY; without even the implied warranty of
9
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10
* See the GNU General Public License for more details.
11
*
12
* You should have received a copy of the GNU General Public License along
13
* with this program. If not, see <http://www.gnu.org/licenses/>.
14
*
15
* Code by Siddharth Bharat Purohit
16
*/
17
18
#pragma once
19
20
#include "AP_CANManager_config.h"
21
22
#if AP_CAN_SLCAN_ENABLED
23
24
#include <AP_HAL/AP_HAL.h>
25
#include "AP_HAL/utility/RingBuffer.h"
26
#include <AP_Param/AP_Param.h>
27
28
#define SLCAN_BUFFER_SIZE 200
29
#define SLCAN_RX_QUEUE_SIZE 64
30
31
#ifndef HAL_CAN_RX_QUEUE_SIZE
32
#define HAL_CAN_RX_QUEUE_SIZE 128
33
#endif
34
35
static_assert(HAL_CAN_RX_QUEUE_SIZE <= 254, "Invalid CAN Rx queue size");
36
37
namespace SLCAN
38
{
39
40
class CANIface: public AP_HAL::CANIface
41
{
42
43
int16_t reportFrame(const AP_HAL::CANFrame& frame, uint64_t timestamp_usec);
44
45
const char* processCommand(char* cmd);
46
47
// pushes received frame into queue, false if failed
48
bool push_Frame(AP_HAL::CANFrame &frame);
49
50
// Methods to handle different types of frames,
51
// return true if successfully received frame type
52
bool handle_FrameRTRStd(const char* cmd);
53
bool handle_FrameRTRExt(const char* cmd);
54
bool handle_FrameDataStd(const char* cmd);
55
bool handle_FrameDataExt(const char* cmd, bool canfd);
56
57
bool handle_FDFrameDataExt(const char* cmd);
58
59
// Parsing bytes received on the serial port
60
inline void addByte(const uint8_t byte);
61
62
// track changes to slcan serial port
63
void update_slcan_port();
64
65
bool initialized_;
66
67
char buf_[SLCAN_BUFFER_SIZE + 1]; // buffer to record raw frame nibbles before parsing
68
int16_t pos_ = 0; // position in the buffer recording nibble frames before parsing
69
AP_HAL::UARTDriver* _port; // UART interface port reference to be used for SLCAN iface
70
bool _enabled; // Flag to check whether we are allowed to use _port
71
72
ObjectBuffer<AP_HAL::CANIface::CanRxItem> rx_queue_; // Parsed Rx Frame queue
73
74
const uint32_t _serial_lock_key = 0x53494442; // Key used to lock UART port for use by slcan
75
76
AP_Int8 _slcan_can_port;
77
AP_Int8 _slcan_ser_port;
78
AP_Int8 _slcan_timeout;
79
AP_Int8 _slcan_start_delay;
80
81
bool _slcan_start_req;
82
uint32_t _slcan_start_req_time;
83
int8_t _prev_ser_port;
84
int8_t _iface_num = -1;
85
uint32_t _last_had_activity;
86
uint8_t num_tries;
87
AP_HAL::CANIface* _can_iface; // Can interface to be used for interaction by SLCAN interface
88
HAL_Semaphore port_sem;
89
bool _set_by_sermgr;
90
public:
91
CANIface():
92
rx_queue_(HAL_CAN_RX_QUEUE_SIZE)
93
{
94
AP_Param::setup_object_defaults(this, var_info);
95
}
96
97
static const struct AP_Param::GroupInfo var_info[];
98
99
bool init(const uint32_t bitrate) override
100
{
101
return false;
102
}
103
104
// Initialisation of SLCAN Passthrough method of operation
105
bool init_passthrough(uint8_t i);
106
107
void set_can_iface(AP_HAL::CANIface* can_iface)
108
{
109
_can_iface = can_iface;
110
}
111
112
void reset_params();
113
114
// Overriden methods
115
bool set_event_handle(AP_HAL::BinarySemaphore *sem_handle) override;
116
uint32_t getErrorCount() const override;
117
void get_stats(ExpandingString &) override;
118
bool is_busoff() const override;
119
void flush_tx() override;
120
void clear_rx() override;
121
bool is_initialized() const override;
122
bool select(bool &read, bool &write,
123
const AP_HAL::CANFrame* const pending_tx,
124
uint64_t blocking_deadline) override;
125
int16_t send(const AP_HAL::CANFrame& frame, uint64_t tx_deadline,
126
AP_HAL::CANIface::CanIOFlags flags) override;
127
128
int16_t receive(AP_HAL::CANFrame& out_frame, uint64_t& rx_time,
129
AP_HAL::CANIface::CanIOFlags& out_flags) override;
130
131
protected:
132
int8_t get_iface_num() const override {
133
return _iface_num;
134
}
135
136
bool add_to_rx_queue(const AP_HAL::CANIface::CanRxItem &frm) override {
137
return rx_queue_.push(frm);
138
}
139
bool is_enabled() const {
140
return (_port != nullptr) && _enabled;
141
}
142
};
143
144
}
145
146
#endif // AP_CAN_SLCAN_ENABLED
147
148