Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add MCP2515 12MHz xtal support #5089

Merged
merged 3 commits into from
Jul 12, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions esphome/components/mcp2515/canbus.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

CAN_CLOCK = {
"8MHZ": CanClock.MCP_8MHZ,
"12MHZ": CanClock.MCP_12MHZ,
"16MHZ": CanClock.MCP_16MHZ,
"20MHZ": CanClock.MCP_20MHZ,
}
Expand Down
98 changes: 85 additions & 13 deletions esphome/components/mcp2515/mcp2515.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,14 @@ const struct MCP2515::RxBnRegs MCP2515::RXB[N_RXBUFFERS] = {{MCP_RXB0CTRL, MCP_R
bool MCP2515::setup_internal() {
this->spi_setup();

if (this->reset_() == canbus::ERROR_FAIL)
if (this->reset_() != canbus::ERROR_OK)
return false;
this->set_bitrate_(this->bit_rate_, this->mcp_clock_);
this->set_mode_(this->mcp_mode_);
ESP_LOGV(TAG, "setup done");
if (this->set_bitrate_(this->bit_rate_, this->mcp_clock_) != canbus::ERROR_OK)
return false;
if (this->set_mode_(this->mcp_mode_) != canbus::ERROR_OK)
return false;
uint8_t err_flags = this->get_error_flags_();
ESP_LOGD(TAG, "mcp2515 setup done, error_flags = %02X", err_flags);
return true;
}

Expand All @@ -38,7 +41,7 @@ canbus::Error MCP2515::reset_() {
set_registers_(MCP_TXB0CTRL, zeros, 14);
set_registers_(MCP_TXB1CTRL, zeros, 14);
set_registers_(MCP_TXB2CTRL, zeros, 14);
ESP_LOGD(TAG, "reset() CLEARED TXB registers");
ESP_LOGV(TAG, "reset() CLEARED TXB registers");

set_register_(MCP_RXB0CTRL, 0);
set_register_(MCP_RXB1CTRL, 0);
Expand Down Expand Up @@ -114,16 +117,12 @@ canbus::Error MCP2515::set_mode_(const CanctrlReqopMode mode) {
modify_register_(MCP_CANCTRL, CANCTRL_REQOP, mode);

uint32_t end_time = millis() + 10;
bool mode_match = false;
while (millis() < end_time) {
uint8_t new_mode = read_register_(MCP_CANSTAT);
new_mode &= CANSTAT_OPMOD;
mode_match = new_mode == mode;
if (mode_match) {
break;
}
if ((read_register_(MCP_CANSTAT) & CANSTAT_OPMOD) == mode)
return canbus::ERROR_OK;
}
return mode_match ? canbus::ERROR_OK : canbus::ERROR_FAIL;
ESP_LOGE(TAG, "Failed to set mode");
return canbus::ERROR_FAIL;
}

canbus::Error MCP2515::set_clk_out_(const CanClkOut divisor) {
Expand Down Expand Up @@ -451,6 +450,78 @@ canbus::Error MCP2515::set_bitrate_(canbus::CanSpeed can_speed, CanClock can_clo
}
break;

case (MCP_12MHZ):
switch (can_speed) {
case (canbus::CAN_5KBPS): // 5Kbps
cfg1 = MCP_12MHZ_5KBPS_CFG1;
cfg2 = MCP_12MHZ_5KBPS_CFG2;
cfg3 = MCP_12MHZ_5KBPS_CFG3;
break;
case (canbus::CAN_10KBPS): // 10Kbps
cfg1 = MCP_12MHZ_10KBPS_CFG1;
cfg2 = MCP_12MHZ_10KBPS_CFG2;
cfg3 = MCP_12MHZ_10KBPS_CFG3;
break;
case (canbus::CAN_20KBPS): // 20Kbps
cfg1 = MCP_12MHZ_20KBPS_CFG1;
cfg2 = MCP_12MHZ_20KBPS_CFG2;
cfg3 = MCP_12MHZ_20KBPS_CFG3;
break;
case (canbus::CAN_33KBPS): // 33.333Kbps
cfg1 = MCP_12MHZ_33K3BPS_CFG1;
cfg2 = MCP_12MHZ_33K3BPS_CFG2;
cfg3 = MCP_12MHZ_33K3BPS_CFG3;
break;
case (canbus::CAN_40KBPS): // 40Kbps
cfg1 = MCP_12MHZ_40KBPS_CFG1;
cfg2 = MCP_12MHZ_40KBPS_CFG2;
cfg3 = MCP_12MHZ_40KBPS_CFG3;
break;
case (canbus::CAN_50KBPS): // 50Kbps
cfg2 = MCP_12MHZ_50KBPS_CFG2;
cfg3 = MCP_12MHZ_50KBPS_CFG3;
break;
case (canbus::CAN_80KBPS): // 80Kbps
cfg1 = MCP_12MHZ_80KBPS_CFG1;
cfg2 = MCP_12MHZ_80KBPS_CFG2;
cfg3 = MCP_12MHZ_80KBPS_CFG3;
break;
case (canbus::CAN_100KBPS): // 100Kbps
cfg1 = MCP_12MHZ_100KBPS_CFG1;
cfg2 = MCP_12MHZ_100KBPS_CFG2;
cfg3 = MCP_12MHZ_100KBPS_CFG3;
break;
case (canbus::CAN_125KBPS): // 125Kbps
cfg1 = MCP_12MHZ_125KBPS_CFG1;
cfg2 = MCP_12MHZ_125KBPS_CFG2;
cfg3 = MCP_12MHZ_125KBPS_CFG3;
break;
case (canbus::CAN_200KBPS): // 200Kbps
cfg1 = MCP_12MHZ_200KBPS_CFG1;
cfg2 = MCP_12MHZ_200KBPS_CFG2;
cfg3 = MCP_12MHZ_200KBPS_CFG3;
break;
case (canbus::CAN_250KBPS): // 250Kbps
cfg1 = MCP_12MHZ_250KBPS_CFG1;
cfg2 = MCP_12MHZ_250KBPS_CFG2;
cfg3 = MCP_12MHZ_250KBPS_CFG3;
break;
case (canbus::CAN_500KBPS): // 500Kbps
cfg1 = MCP_12MHZ_500KBPS_CFG1;
cfg2 = MCP_12MHZ_500KBPS_CFG2;
cfg3 = MCP_12MHZ_500KBPS_CFG3;
break;
case (canbus::CAN_1000KBPS): // 1Mbps
cfg1 = MCP_12MHZ_1000KBPS_CFG1;
cfg2 = MCP_12MHZ_1000KBPS_CFG2;
cfg3 = MCP_12MHZ_1000KBPS_CFG3;
break;
default:
set = 0;
break;
}
break;

case (MCP_16MHZ):
switch (can_speed) {
case (canbus::CAN_5KBPS): // 5Kbps
Expand Down Expand Up @@ -602,6 +673,7 @@ canbus::Error MCP2515::set_bitrate_(canbus::CanSpeed can_speed, CanClock can_clo
set_register_(MCP_CNF3, cfg3); // NOLINT
return canbus::ERROR_OK;
} else {
ESP_LOGE(TAG, "Invalid frequency/bitrate combination: %d/%d", can_clock, can_speed);
return canbus::ERROR_FAIL;
}
}
Expand Down
2 changes: 1 addition & 1 deletion esphome/components/mcp2515/mcp2515.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ static const uint32_t SPI_CLOCK = 10000000; // 10MHz

static const int N_TXBUFFERS = 3;
static const int N_RXBUFFERS = 2;
enum CanClock { MCP_20MHZ, MCP_16MHZ, MCP_8MHZ };
enum CanClock { MCP_20MHZ, MCP_16MHZ, MCP_12MHZ, MCP_8MHZ };
enum MASK { MASK0, MASK1 };
enum RXF { RXF0 = 0, RXF1 = 1, RXF2 = 2, RXF3 = 3, RXF4 = 4, RXF5 = 5 };
enum RXBn { RXB0 = 0, RXB1 = 1 };
Expand Down
56 changes: 56 additions & 0 deletions esphome/components/mcp2515/mcp2515_defs.h
Original file line number Diff line number Diff line change
Expand Up @@ -207,6 +207,62 @@ static const uint8_t MCP_8MHZ_5KBPS_CFG1 = 0x1F;
static const uint8_t MCP_8MHZ_5KBPS_CFG2 = 0xBF;
static const uint8_t MCP_8MHZ_5KBPS_CFG3 = 0x87;

/*
* Speed 12M
*/

static const uint8_t MCP_12MHZ_1000KBPS_CFG1 = 0x00;
static const uint8_t MCP_12MHZ_1000KBPS_CFG2 = 0x88;
static const uint8_t MCP_12MHZ_1000KBPS_CFG3 = 0x81;

static const uint8_t MCP_12MHZ_500KBPS_CFG1 = 0x00;
static const uint8_t MCP_12MHZ_500KBPS_CFG2 = 0x9B;
static const uint8_t MCP_12MHZ_500KBPS_CFG3 = 0x82;

static const uint8_t MCP_12MHZ_250KBPS_CFG1 = 0x01;
static const uint8_t MCP_12MHZ_250KBPS_CFG2 = 0x9B;
static const uint8_t MCP_12MHZ_250KBPS_CFG3 = 0x82;

static const uint8_t MCP_12MHZ_200KBPS_CFG1 = 0x01;
static const uint8_t MCP_12MHZ_200KBPS_CFG2 = 0xA4;
static const uint8_t MCP_12MHZ_200KBPS_CFG3 = 0x83;

static const uint8_t MCP_12MHZ_125KBPS_CFG1 = 0x03;
static const uint8_t MCP_12MHZ_125KBPS_CFG2 = 0x9B;
static const uint8_t MCP_12MHZ_125KBPS_CFG3 = 0x82;

static const uint8_t MCP_12MHZ_100KBPS_CFG1 = 0x03;
static const uint8_t MCP_12MHZ_100KBPS_CFG2 = 0xA4;
static const uint8_t MCP_12MHZ_100KBPS_CFG3 = 0x83;

static const uint8_t MCP_12MHZ_80KBPS_CFG1 = 0x04;
static const uint8_t MCP_12MHZ_80KBPS_CFG2 = 0xA4;
static const uint8_t MCP_12MHZ_80KBPS_CFG3 = 0x83;

static const uint8_t MCP_12MHZ_50KBPS_CFG1 = 0x07;
static const uint8_t MCP_12MHZ_50KBPS_CFG2 = 0xA4;
static const uint8_t MCP_12MHZ_50KBPS_CFG3 = 0x83;

static const uint8_t MCP_12MHZ_40KBPS_CFG1 = 0x09;
static const uint8_t MCP_12MHZ_40KBPS_CFG2 = 0xA4;
static const uint8_t MCP_12MHZ_40KBPS_CFG3 = 0x83;

static const uint8_t MCP_12MHZ_33K3BPS_CFG1 = 0x08;
static const uint8_t MCP_12MHZ_33K3BPS_CFG2 = 0xB6;
static const uint8_t MCP_12MHZ_33K3BPS_CFG3 = 0x84;

static const uint8_t MCP_12MHZ_20KBPS_CFG1 = 0x0E;
static const uint8_t MCP_12MHZ_20KBPS_CFG2 = 0xB6;
static const uint8_t MCP_12MHZ_20KBPS_CFG3 = 0x84;

static const uint8_t MCP_12MHZ_10KBPS_CFG1 = 0x31;
static const uint8_t MCP_12MHZ_10KBPS_CFG2 = 0x9B;
static const uint8_t MCP_12MHZ_10KBPS_CFG3 = 0x82;

static const uint8_t MCP_12MHZ_5KBPS_CFG1 = 0x3B;
static const uint8_t MCP_12MHZ_5KBPS_CFG2 = 0xB6;
static const uint8_t MCP_12MHZ_5KBPS_CFG3 = 0x84;

/*
* speed 16M
*/
Expand Down