mirror of
https://github.com/Evolution-X/hardware_interfaces
synced 2026-02-01 11:36:00 +00:00
Add support for registering existing interfaces
This adds support for native and slcan interfaces which are already configured up to be registered in the CAN bus HAL. Bug: 142655647 Test: manual Change-Id: Ifd129db14dbf473bb627ebc9b9d13f5cb945b611
This commit is contained in:
@@ -31,6 +31,11 @@ ICanController::Result CanBusNative::preUp() {
|
||||
return ICanController::Result::BAD_ADDRESS;
|
||||
}
|
||||
|
||||
if (mBaudrate == 0) {
|
||||
// interface is already up and we just want to register it
|
||||
return ICanController::Result::OK;
|
||||
}
|
||||
|
||||
if (!netdevice::down(mIfname)) {
|
||||
LOG(ERROR) << "Can't bring " << mIfname << " down (to configure it)";
|
||||
return ICanController::Result::UNKNOWN_ERROR;
|
||||
|
||||
@@ -47,13 +47,34 @@ static const std::map<uint32_t, std::string> kBitrateCommands = {
|
||||
CanBusSlcan::CanBusSlcan(const std::string& uartName, uint32_t bitrate)
|
||||
: CanBus(), mUartName(uartName), kBitrate(bitrate) {}
|
||||
|
||||
/** helper function to update CanBusSlcan object's iface name */
|
||||
ICanController::Result CanBusSlcan::updateIfaceName(base::unique_fd& uartFd) {
|
||||
struct ifreq ifrequest = {};
|
||||
/*
|
||||
* Fetching the iface name with an ioctl won't interfere with an open socketCAN iface attached
|
||||
* to this tty. This is important in the event we are trying to register a SLCAN based iface
|
||||
* that has already been configured and brought up.
|
||||
*/
|
||||
if (ioctl(uartFd.get(), SIOCGIFNAME, ifrequest.ifr_name) < 0) {
|
||||
LOG(ERROR) << "Failed to get the name of the created device: " << strerror(errno);
|
||||
return ICanController::Result::UNKNOWN_ERROR;
|
||||
}
|
||||
|
||||
// Update the CanBus object with name that was assigned to it
|
||||
mIfname = ifrequest.ifr_name;
|
||||
return ICanController::Result::OK;
|
||||
}
|
||||
|
||||
ICanController::Result CanBusSlcan::preUp() {
|
||||
// verify valid bitrate and translate to serial command format
|
||||
const auto lookupIt = slcanprotocol::kBitrateCommands.find(kBitrate);
|
||||
if (lookupIt == slcanprotocol::kBitrateCommands.end()) {
|
||||
return ICanController::Result::BAD_BAUDRATE;
|
||||
std::optional<std::string> canBitrateCommand = std::nullopt;
|
||||
if (kBitrate != 0) {
|
||||
const auto lookupIt = slcanprotocol::kBitrateCommands.find(kBitrate);
|
||||
if (lookupIt == slcanprotocol::kBitrateCommands.end()) {
|
||||
return ICanController::Result::BAD_BAUDRATE;
|
||||
}
|
||||
canBitrateCommand = lookupIt->second;
|
||||
}
|
||||
const auto canBitrateCommand = lookupIt->second;
|
||||
|
||||
/* Attempt to open the uart in r/w without blocking or becoming the
|
||||
* controlling terminal */
|
||||
@@ -63,6 +84,11 @@ ICanController::Result CanBusSlcan::preUp() {
|
||||
return ICanController::Result::BAD_ADDRESS;
|
||||
}
|
||||
|
||||
// If the device is already up, update the iface name in our CanBusSlcan object
|
||||
if (kBitrate == 0) {
|
||||
return updateIfaceName(mFd);
|
||||
}
|
||||
|
||||
// blank terminal settings and pull them from the device
|
||||
struct termios terminalSettings = {};
|
||||
if (tcgetattr(mFd.get(), &terminalSettings) < 0) {
|
||||
@@ -102,7 +128,7 @@ ICanController::Result CanBusSlcan::preUp() {
|
||||
}
|
||||
|
||||
// apply speed setting for CAN
|
||||
if (write(mFd.get(), canBitrateCommand.c_str(), canBitrateCommand.length()) <= 0) {
|
||||
if (write(mFd.get(), canBitrateCommand->c_str(), canBitrateCommand->length()) <= 0) {
|
||||
LOG(ERROR) << "Failed to apply CAN bitrate: " << strerror(errno);
|
||||
return ICanController::Result::UNKNOWN_ERROR;
|
||||
}
|
||||
@@ -120,17 +146,8 @@ ICanController::Result CanBusSlcan::preUp() {
|
||||
return ICanController::Result::UNKNOWN_ERROR;
|
||||
}
|
||||
|
||||
// get the name of the device we created
|
||||
struct ifreq ifrequest = {};
|
||||
if (ioctl(mFd.get(), SIOCGIFNAME, ifrequest.ifr_name) < 0) {
|
||||
LOG(ERROR) << "Failed to get the name of the created device: " << strerror(errno);
|
||||
return ICanController::Result::UNKNOWN_ERROR;
|
||||
}
|
||||
|
||||
// Update the CanBus object with name that was assigned to it
|
||||
mIfname = ifrequest.ifr_name;
|
||||
|
||||
return ICanController::Result::OK;
|
||||
return updateIfaceName(mFd);
|
||||
}
|
||||
|
||||
bool CanBusSlcan::postDown() {
|
||||
|
||||
@@ -32,6 +32,8 @@ struct CanBusSlcan : public CanBus {
|
||||
virtual bool postDown() override;
|
||||
|
||||
private:
|
||||
ICanController::Result updateIfaceName(base::unique_fd& uartFd);
|
||||
|
||||
const std::string mUartName;
|
||||
const uint32_t kBitrate;
|
||||
base::unique_fd mFd;
|
||||
|
||||
Reference in New Issue
Block a user