strat: use m_ for member variables

This commit is contained in:
Michael Scire 2021-10-10 00:14:06 -07:00
parent ce28591ab2
commit a595c232b9
425 changed files with 8531 additions and 8484 deletions

View file

@ -55,56 +55,56 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
void I2cBusAccessor::Initialize(dd::PhysicalAddress reg_paddr, size_t reg_size, os::InterruptName intr, bool pb, SpeedMode sm) {
AMS_ASSERT(this->state == State::NotInitialized);
AMS_ASSERT(m_state == State::NotInitialized);
this->is_power_bus = pb;
this->speed_mode = sm;
this->interrupt_name = intr;
this->registers_phys_addr = reg_paddr;
this->registers_size = reg_size;
this->state = State::Initializing;
m_is_power_bus = pb;
m_speed_mode = sm;
m_interrupt_name = intr;
m_registers_phys_addr = reg_paddr;
m_registers_size = reg_size;
m_state = State::Initializing;
}
void I2cBusAccessor::RegisterDeviceCode(DeviceCode dc) {
AMS_ASSERT(this->state == State::Initializing);
AMS_ASSERT(m_state == State::Initializing);
this->device_code = dc;
m_device_code = dc;
}
void I2cBusAccessor::InitializeDriver() {
AMS_ASSERT(this->state == State::Initializing);
AMS_ASSERT(m_state == State::Initializing);
this->registers = reinterpret_cast<volatile I2cRegisters *>(dd::QueryIoMapping(this->registers_phys_addr, this->registers_size));
AMS_ABORT_UNLESS(this->registers != nullptr);
m_registers = reinterpret_cast<volatile I2cRegisters *>(dd::QueryIoMapping(m_registers_phys_addr, m_registers_size));
AMS_ABORT_UNLESS(m_registers != nullptr);
this->state = State::Initialized;
m_state = State::Initialized;
}
void I2cBusAccessor::FinalizeDriver() {
AMS_ASSERT(this->state == State::Initialized);
this->state = State::Initializing;
AMS_ASSERT(m_state == State::Initialized);
m_state = State::Initializing;
}
Result I2cBusAccessor::InitializeDevice(I2cDeviceProperty *device) {
/* Check that the device is valid. */
AMS_ASSERT(device != nullptr);
AMS_ASSERT(this->state == State::Initialized);
AMS_ASSERT(m_state == State::Initialized);
AMS_UNUSED(device);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* Increment our user count -- if we're already open, we're done. */
AMS_ASSERT(this->user_count >= 0);
++this->user_count;
R_SUCCEED_IF(this->user_count > 1);
AMS_ASSERT(m_user_count >= 0);
++m_user_count;
R_SUCCEED_IF(m_user_count > 1);
/* Initialize our interrupt event. */
os::InitializeInterruptEvent(std::addressof(this->interrupt_event), this->interrupt_name, os::EventClearMode_ManualClear);
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
os::InitializeInterruptEvent(std::addressof(m_interrupt_event), m_interrupt_name, os::EventClearMode_ManualClear);
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
/* If we're not power bus, perform power management init. */
if (!this->is_power_bus) {
if (!m_is_power_bus) {
/* Initialize regulator library. */
regulator::Initialize();
@ -112,9 +112,9 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
R_TRY(this->TryOpenRegulatorSession());
/* If we have a regulator session, set voltage to 2.9V. */
if (this->has_regulator_session) {
if (m_has_regulator_session) {
/* NOTE: Nintendo does not check the result, here. */
regulator::SetVoltageValue(std::addressof(this->regulator_session), 2'900'000u);
regulator::SetVoltageValue(std::addressof(m_regulator_session), 2'900'000u);
}
/* Initialize clock/reset library. */
@ -125,12 +125,12 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
this->ExecuteInitialConfig();
/* If we have a regulator session, enable voltage. */
if (!this->is_power_bus && this->has_regulator_session) {
if (!m_is_power_bus && m_has_regulator_session) {
/* Check whether voltage was already enabled. */
const bool was_enabled = regulator::GetVoltageEnabled(std::addressof(this->regulator_session));
const bool was_enabled = regulator::GetVoltageEnabled(std::addressof(m_regulator_session));
/* NOTE: Nintendo does not check the result of this call. */
regulator::SetVoltageEnabled(std::addressof(this->regulator_session), true);
regulator::SetVoltageEnabled(std::addressof(m_regulator_session), true);
/* If we enabled voltage, delay to give our enable time to take. */
if (!was_enabled) {
@ -144,35 +144,35 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void I2cBusAccessor::FinalizeDevice(I2cDeviceProperty *device) {
/* Check that the device is valid. */
AMS_ASSERT(device != nullptr);
AMS_ASSERT(this->state == State::Initialized);
AMS_ASSERT(m_state == State::Initialized);
AMS_UNUSED(device);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* Increment our user count -- if we're not the last user, we're done. */
AMS_ASSERT(this->user_count > 0);
--this->user_count;
if (this->user_count > 0) {
AMS_ASSERT(m_user_count > 0);
--m_user_count;
if (m_user_count > 0) {
return;
}
/* Finalize our interrupt event. */
os::FinalizeInterruptEvent(std::addressof(this->interrupt_event));
os::FinalizeInterruptEvent(std::addressof(m_interrupt_event));
/* If we have a regulator session, disable voltage. */
if (this->has_regulator_session) {
if (m_has_regulator_session) {
/* NOTE: Nintendo does not check the result of this call. */
regulator::SetVoltageEnabled(std::addressof(this->regulator_session), false);
regulator::SetVoltageEnabled(std::addressof(m_regulator_session), false);
}
/* Finalize the clock/reset library. */
clkrst::Finalize();
/* If we have a regulator session, close it. */
if (this->has_regulator_session) {
regulator::CloseSession(std::addressof(this->regulator_session));
this->has_regulator_session = false;
if (m_has_regulator_session) {
regulator::CloseSession(std::addressof(m_regulator_session));
m_has_regulator_session = false;
}
/* Finalize the regulator library. */
@ -185,10 +185,10 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
AMS_ASSERT(src != nullptr);
AMS_ASSERT(src_size > 0);
if (this->is_power_bus) {
AMS_ASSERT(this->state == State::Initialized || this->state == State::Suspended);
if (m_is_power_bus) {
AMS_ASSERT(m_state == State::Initialized || m_state == State::Suspended);
} else {
AMS_ASSERT(this->state == State::Initialized);
AMS_ASSERT(m_state == State::Initialized);
}
/* Send the data. */
@ -201,10 +201,10 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
AMS_ASSERT(dst != nullptr);
AMS_ASSERT(dst_size > 0);
if (this->is_power_bus) {
AMS_ASSERT(this->state == State::Initialized || this->state == State::Suspended);
if (m_is_power_bus) {
AMS_ASSERT(m_state == State::Initialized || m_state == State::Suspended);
} else {
AMS_ASSERT(this->state == State::Initialized);
AMS_ASSERT(m_state == State::Initialized);
}
/* Send the data. */
@ -213,18 +213,18 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void I2cBusAccessor::SuspendBus() {
/* Check that state is valid. */
AMS_ASSERT(this->state == State::Initialized);
AMS_ASSERT(m_state == State::Initialized);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* If we need to, disable clock/voltage appropriately. */
if (!this->is_power_bus && this->user_count > 0) {
if (!m_is_power_bus && m_user_count > 0) {
/* Disable clock. */
{
/* Open a clkrst session. */
clkrst::ClkRstSession clkrst_session;
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), this->device_code));
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), m_device_code));
ON_SCOPE_EXIT { clkrst::CloseSession(std::addressof(clkrst_session)); };
/* Set clock disabled for the session. */
@ -232,47 +232,47 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Disable voltage. */
if (this->has_regulator_session) {
regulator::SetVoltageEnabled(std::addressof(this->regulator_session), false);
if (m_has_regulator_session) {
regulator::SetVoltageEnabled(std::addressof(m_regulator_session), false);
}
}
/* Update state. */
this->state = State::Suspended;
m_state = State::Suspended;
}
void I2cBusAccessor::SuspendPowerBus() {
/* Check that state is valid. */
AMS_ASSERT(this->state == State::Suspended);
AMS_ASSERT(m_state == State::Suspended);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* If we need to, disable clock/voltage appropriately. */
if (this->is_power_bus && this->user_count > 0) {
if (m_is_power_bus && m_user_count > 0) {
/* Nothing should actually be done here. */
}
/* Update state. */
this->state = State::PowerBusSuspended;
m_state = State::PowerBusSuspended;
}
void I2cBusAccessor::ResumeBus() {
/* Check that state is valid. */
AMS_ASSERT(this->state == State::Suspended);
AMS_ASSERT(m_state == State::Suspended);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* If we need to, enable clock/voltage appropriately. */
if (!this->is_power_bus && this->user_count > 0) {
if (!m_is_power_bus && m_user_count > 0) {
/* Enable voltage. */
if (this->has_regulator_session) {
if (m_has_regulator_session) {
/* Check whether voltage was already enabled. */
const bool was_enabled = regulator::GetVoltageEnabled(std::addressof(this->regulator_session));
const bool was_enabled = regulator::GetVoltageEnabled(std::addressof(m_regulator_session));
/* NOTE: Nintendo does not check the result of this call. */
regulator::SetVoltageEnabled(std::addressof(this->regulator_session), true);
regulator::SetVoltageEnabled(std::addressof(m_regulator_session), true);
/* If we enabled voltage, delay to give our enable time to take. */
if (!was_enabled) {
@ -285,36 +285,36 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Update state. */
this->state = State::Initialized;
m_state = State::Initialized;
}
void I2cBusAccessor::ResumePowerBus() {
/* Check that state is valid. */
AMS_ASSERT(this->state == State::PowerBusSuspended);
AMS_ASSERT(m_state == State::PowerBusSuspended);
/* Acquire exclusive access. */
std::scoped_lock lk(this->user_count_mutex);
std::scoped_lock lk(m_user_count_mutex);
/* If we need to, enable clock/voltage appropriately. */
if (this->is_power_bus && this->user_count > 0) {
if (m_is_power_bus && m_user_count > 0) {
/* Execute initial config, which will enable clock as relevant. */
this->ExecuteInitialConfig();
}
/* Update state. */
this->state = State::Suspended;
m_state = State::Suspended;
}
Result I2cBusAccessor::TryOpenRegulatorSession() {
/* Ensure we track the session. */
this->has_regulator_session = true;
auto s_guard = SCOPE_GUARD { this->has_regulator_session = false; };
m_has_regulator_session = true;
auto s_guard = SCOPE_GUARD { m_has_regulator_session = false; };
/* Try to open the session. */
R_TRY_CATCH(regulator::OpenSession(std::addressof(this->regulator_session), this->device_code)) {
R_TRY_CATCH(regulator::OpenSession(std::addressof(m_regulator_session), m_device_code)) {
R_CATCH(ddsf::ResultDeviceCodeNotFound) {
/* It's okay if the device isn't found, but we don't have a session if so. */
this->has_regulator_session = false;
m_has_regulator_session = false;
}
} R_END_TRY_CATCH;
@ -325,13 +325,13 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void I2cBusAccessor::ExecuteInitialConfig() {
/* Lock exclusive access to registers. */
std::scoped_lock lk(this->register_mutex);
std::scoped_lock lk(m_register_mutex);
/* Reset the controller. */
this->ResetController();
/* Set clock registers. */
this->SetClockRegisters(this->speed_mode);
this->SetClockRegisters(m_speed_mode);
/* Set packet mode registers. */
this->SetPacketModeRegisters();
@ -342,20 +342,20 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
Result I2cBusAccessor::Send(const u8 *src, size_t src_size, TransactionOption option, u16 slave_address, AddressingMode addressing_mode) {
/* Acquire exclusive access to the registers. */
std::scoped_lock lk(this->register_mutex);
std::scoped_lock lk(m_register_mutex);
/* Configure interrupt mask, clear interrupt status. */
reg::Write(this->registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_TFIFO_DATA_REQ_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
reg::Write(m_registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_TFIFO_DATA_REQ_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
reg::Write(this->registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ARB_LOST, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_NOACK, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_RFIFO_UNF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_TFIFO_OVF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ALL_PACKETS_XFER_COMPLETE, SET));
reg::Write(m_registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ARB_LOST, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_NOACK, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_RFIFO_UNF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_TFIFO_OVF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ALL_PACKETS_XFER_COMPLETE, SET));
/* Write the header. */
this->WriteHeader(Xfer_Write, src_size, option, slave_address, addressing_mode);
@ -366,7 +366,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
while (true) {
/* Get the number of empty bytes in the fifo status. */
const u32 empty = reg::GetValue(this->registers->fifo_status, I2C_REG_BITS_MASK(FIFO_STATUS_TX_FIFO_EMPTY_CNT));
const u32 empty = reg::GetValue(m_registers->fifo_status, I2C_REG_BITS_MASK(FIFO_STATUS_TX_FIFO_EMPTY_CNT));
/* Write up to (empty) bytes to the fifo. */
for (u32 i = 0; remaining > 0 && i < empty; ++i) {
@ -379,7 +379,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Write the data word. */
reg::Write(this->registers->tx_packet_fifo, word);
reg::Write(m_registers->tx_packet_fifo, word);
/* Advance. */
cur += cur_bytes;
@ -392,13 +392,13 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Wait for our current data to send. */
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(this->interrupt_event), Timeout)) {
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(m_interrupt_event), Timeout)) {
/* We timed out. */
this->HandleTransactionError(i2c::ResultBusBusy());
this->DisableInterruptMask();
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
return i2c::ResultTimeout();
}
@ -407,9 +407,9 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Configure interrupt mask to not care about tfifo data req. */
reg::Write(this->registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
reg::Write(m_registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
/* Wait for the packet transfer to complete. */
while (true) {
@ -417,18 +417,18 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
R_TRY(this->CheckAndHandleError());
/* Check if packet transfer is done. */
if (reg::HasValue(this->registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET))) {
if (reg::HasValue(m_registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET))) {
break;
}
/* Wait for our the packet to transfer. */
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(this->interrupt_event), Timeout)) {
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(m_interrupt_event), Timeout)) {
/* We timed out. */
this->HandleTransactionError(i2c::ResultBusBusy());
this->DisableInterruptMask();
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
return i2c::ResultTimeout();
}
}
@ -443,20 +443,20 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
Result I2cBusAccessor::Receive(u8 *dst, size_t dst_size, TransactionOption option, u16 slave_address, AddressingMode addressing_mode) {
/* Acquire exclusive access to the registers. */
std::scoped_lock lk(this->register_mutex);
std::scoped_lock lk(m_register_mutex);
/* Configure interrupt mask, clear interrupt status. */
reg::Write(this->registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_RFIFO_DATA_REQ_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
reg::Write(m_registers->interrupt_mask_register, I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_RFIFO_DATA_REQ_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_ARB_LOST_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_NOACK_INT_EN, ENABLE),
I2C_REG_BITS_ENUM(INTERRUPT_MASK_REGISTER_PACKET_XFER_COMPLETE_INT_EN, ENABLE));
reg::Write(this->registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ARB_LOST, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_NOACK, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_RFIFO_UNF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_TFIFO_OVF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ALL_PACKETS_XFER_COMPLETE, SET));
reg::Write(m_registers->interrupt_status_register, I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ARB_LOST, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_NOACK, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_RFIFO_UNF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_TFIFO_OVF, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_PACKET_XFER_COMPLETE, SET),
I2C_REG_BITS_ENUM(INTERRUPT_STATUS_REGISTER_ALL_PACKETS_XFER_COMPLETE, SET));
/* Write the header. */
this->WriteHeader(Xfer_Read, dst_size, option, slave_address, addressing_mode);
@ -467,13 +467,13 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
while (remaining > 0) {
/* Wait for data to come in. */
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(this->interrupt_event), Timeout)) {
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
if (!os::TimedWaitInterruptEvent(std::addressof(m_interrupt_event), Timeout)) {
/* We timed out. */
this->HandleTransactionError(i2c::ResultBusBusy());
this->DisableInterruptMask();
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
return i2c::ResultTimeout();
}
@ -481,7 +481,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
R_TRY(this->CheckAndHandleError());
/* Get the number of full bytes in the fifo status. */
const u32 full = reg::GetValue(this->registers->fifo_status, I2C_REG_BITS_MASK(FIFO_STATUS_RX_FIFO_FULL_CNT));
const u32 full = reg::GetValue(m_registers->fifo_status, I2C_REG_BITS_MASK(FIFO_STATUS_RX_FIFO_FULL_CNT));
/* Determine how many words we can read. */
const size_t cur_words = std::min(util::DivideUp(remaining, sizeof(u32)), static_cast<size_t>(full));
@ -489,7 +489,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
/* Read the correct number of words from the fifo. */
for (size_t i = 0; i < cur_words; ++i) {
/* Read the word from the fifo. */
const u32 word = reg::Read(this->registers->rx_fifo);
const u32 word = reg::Read(m_registers->rx_fifo);
/* Copy bytes from the word. */
const size_t cur_bytes = std::min(remaining, sizeof(u32));
@ -512,41 +512,41 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
const bool is_read = xfer == Xfer_Read;
const bool is_7_bit = addressing_mode == AddressingMode_SevenBit;
const bool is_stop = (option & TransactionOption_StopCondition) != 0;
const bool is_hs = this->speed_mode == SpeedMode_HighSpeed;
const bool is_hs = m_speed_mode == SpeedMode_HighSpeed;
const u32 slave_addr = ((static_cast<u32>(slave_address) & 0x7F) << 1) | (is_read ? 1 : 0);
/* Flush fifos. */
this->FlushFifos();
/* Enqueue the first header word. */
reg::Write(this->registers->tx_packet_fifo, IO_PACKET_BITS_ENUM (HEADER_WORD0_PROT_HDR_SZ, 1_WORD),
IO_PACKET_BITS_VALUE(HEADER_WORD0_PKT_ID, 0),
IO_PACKET_BITS_VALUE(HEADER_WORD0_CONTROLLER_ID, 0),
IO_PACKET_BITS_ENUM (HEADER_WORD0_PROTOCOL, I2C),
IO_PACKET_BITS_ENUM (HEADER_WORD0_PKT_TYPE, REQUEST));
reg::Write(m_registers->tx_packet_fifo, IO_PACKET_BITS_ENUM (HEADER_WORD0_PROT_HDR_SZ, 1_WORD),
IO_PACKET_BITS_VALUE(HEADER_WORD0_PKT_ID, 0),
IO_PACKET_BITS_VALUE(HEADER_WORD0_CONTROLLER_ID, 0),
IO_PACKET_BITS_ENUM (HEADER_WORD0_PROTOCOL, I2C),
IO_PACKET_BITS_ENUM (HEADER_WORD0_PKT_TYPE, REQUEST));
/* Enqueue the second header word. */
reg::Write(this->registers->tx_packet_fifo, IO_PACKET_BITS_VALUE(HEADER_WORD1_PAYLOAD_SIZE, static_cast<u32>(size - 1)));
reg::Write(m_registers->tx_packet_fifo, IO_PACKET_BITS_VALUE(HEADER_WORD1_PAYLOAD_SIZE, static_cast<u32>(size - 1)));
/* Enqueue the protocol header word. */
reg::Write(this->registers->tx_packet_fifo, IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_HS_MODE, is_hs, ENABLE, DISABLE),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_CONTINUE_ON_NACK, DISABLE),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_SEND_START_BYTE, DISABLE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_READ_WRITE, is_read, READ, WRITE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_ADDRESS_MODE, is_7_bit, SEVEN_BIT, TEN_BIT),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_IE, ENABLE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_REPEAT_START_STOP, is_stop, STOP_CONDITION, REPEAT_START_CONDITION),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_CONTINUE_XFER, USE_REPEAT_START_TOP),
IO_PACKET_BITS_VALUE (PROTOCOL_HEADER_HS_MASTER_ADDR, 0),
IO_PACKET_BITS_VALUE (PROTOCOL_HEADER_SLAVE_ADDR, slave_addr));
reg::Write(m_registers->tx_packet_fifo, IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_HS_MODE, is_hs, ENABLE, DISABLE),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_CONTINUE_ON_NACK, DISABLE),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_SEND_START_BYTE, DISABLE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_READ_WRITE, is_read, READ, WRITE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_ADDRESS_MODE, is_7_bit, SEVEN_BIT, TEN_BIT),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_IE, ENABLE),
IO_PACKET_BITS_ENUM_SEL(PROTOCOL_HEADER_REPEAT_START_STOP, is_stop, STOP_CONDITION, REPEAT_START_CONDITION),
IO_PACKET_BITS_ENUM (PROTOCOL_HEADER_CONTINUE_XFER, USE_REPEAT_START_TOP),
IO_PACKET_BITS_VALUE (PROTOCOL_HEADER_HS_MASTER_ADDR, 0),
IO_PACKET_BITS_VALUE (PROTOCOL_HEADER_SLAVE_ADDR, slave_addr));
}
void I2cBusAccessor::ResetController() const {
/* Reset the controller. */
if (!this->is_power_bus) {
if (!m_is_power_bus) {
/* Open a clkrst session. */
clkrst::ClkRstSession clkrst_session;
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), this->device_code));
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), m_device_code));
ON_SCOPE_EXIT { clkrst::CloseSession(std::addressof(clkrst_session)); };
/* Reset the controller, setting clock rate to 408 MHz / 5 (to account for clock divisor). */
@ -573,17 +573,17 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
this->ResetController();
/* Configure the sclk threshold for bus clear config. */
reg::Write(this->registers->bus_clear_config, I2C_REG_BITS_VALUE(BUS_CLEAR_CONFIG_BC_SCLK_THRESHOLD, 9));
reg::Write(m_registers->bus_clear_config, I2C_REG_BITS_VALUE(BUS_CLEAR_CONFIG_BC_SCLK_THRESHOLD, 9));
/* Set stop cond and terminate in bus clear config. */
reg::ReadWrite(this->registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_STOP_COND, STOP));
reg::ReadWrite(this->registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_TERMINATE, IMMEDIATE));
reg::ReadWrite(m_registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_STOP_COND, STOP));
reg::ReadWrite(m_registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_TERMINATE, IMMEDIATE));
/* Set master config load, busy loop up to 1ms for it to take. */
reg::ReadWrite(this->registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE));
reg::ReadWrite(m_registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE));
const os::Tick start_tick_a = os::GetSystemTick();
while (reg::HasValue(this->registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE))) {
while (reg::HasValue(m_registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE))) {
if ((os::GetSystemTick() - start_tick_a).ToTimeSpan().GetMicroSeconds() > BusyLoopMicroSeconds) {
need_retry = true;
break;
@ -595,10 +595,10 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
}
/* Set bus clear enable, wait up to 1ms for it to take. */
reg::ReadWrite(this->registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_ENABLE, ENABLE));
reg::ReadWrite(m_registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_ENABLE, ENABLE));
const os::Tick start_tick_b = os::GetSystemTick();
while (reg::HasValue(this->registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_ENABLE, ENABLE))) {
while (reg::HasValue(m_registers->bus_clear_config, I2C_REG_BITS_ENUM(BUS_CLEAR_CONFIG_BC_ENABLE, ENABLE))) {
if ((os::GetSystemTick() - start_tick_b).ToTimeSpan().GetMicroSeconds() > BusyLoopMicroSeconds) {
need_retry = true;
break;
@ -611,7 +611,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
/* Wait up to 1ms for the bus clear to complete. */
const os::Tick start_tick_c = os::GetSystemTick();
while (reg::HasValue(this->registers->bus_clear_status, I2C_REG_BITS_ENUM(BUS_CLEAR_STATUS_BC_STATUS, NOT_CLEARED))) {
while (reg::HasValue(m_registers->bus_clear_status, I2C_REG_BITS_ENUM(BUS_CLEAR_STATUS_BC_STATUS, NOT_CLEARED))) {
if ((os::GetSystemTick() - start_tick_c).ToTimeSpan().GetMicroSeconds() > BusyLoopMicroSeconds) {
need_retry = true;
break;
@ -629,7 +629,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
u32 t_high, t_low, clk_div, debounce, src_div;
bool high_speed = false;
if (this->is_power_bus) {
if (m_is_power_bus) {
t_high = 0x02;
t_low = 0x04;
clk_div = 0x05;
@ -672,26 +672,26 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
/* Write the clock divisors. */
if (high_speed) {
reg::Write(this->registers->hs_interface_timing_0, I2C_REG_BITS_VALUE(HS_INTERFACE_TIMING_0_HS_THIGH, t_high),
I2C_REG_BITS_VALUE(HS_INTERFACE_TIMING_0_HS_TLOW, t_low));
reg::Write(m_registers->hs_interface_timing_0, I2C_REG_BITS_VALUE(HS_INTERFACE_TIMING_0_HS_THIGH, t_high),
I2C_REG_BITS_VALUE(HS_INTERFACE_TIMING_0_HS_TLOW, t_low));
reg::Write(this->registers->clk_divisor_register, I2C_REG_BITS_VALUE(CLK_DIVISOR_REGISTER_HSMODE, clk_div));
reg::Write(m_registers->clk_divisor_register, I2C_REG_BITS_VALUE(CLK_DIVISOR_REGISTER_HSMODE, clk_div));
} else {
reg::Write(this->registers->interface_timing_0, I2C_REG_BITS_VALUE(INTERFACE_TIMING_0_THIGH, t_high),
I2C_REG_BITS_VALUE(INTERFACE_TIMING_0_TLOW, t_low));
reg::Write(m_registers->interface_timing_0, I2C_REG_BITS_VALUE(INTERFACE_TIMING_0_THIGH, t_high),
I2C_REG_BITS_VALUE(INTERFACE_TIMING_0_TLOW, t_low));
reg::Write(this->registers->clk_divisor_register, I2C_REG_BITS_VALUE(CLK_DIVISOR_REGISTER_STD_FAST_MODE, clk_div));
reg::Write(m_registers->clk_divisor_register, I2C_REG_BITS_VALUE(CLK_DIVISOR_REGISTER_STD_FAST_MODE, clk_div));
}
/* Configure debounce. */
reg::Write(this->registers->cnfg, I2C_REG_BITS_VALUE(I2C_CNFG_DEBOUNCE_CNT, debounce));
reg::Read(this->registers->cnfg);
reg::Write(m_registers->cnfg, I2C_REG_BITS_VALUE(I2C_CNFG_DEBOUNCE_CNT, debounce));
reg::Read(m_registers->cnfg);
/* Set the clock rate, if we should. */
if (!this->is_power_bus) {
if (!m_is_power_bus) {
/* Open a clkrst session. */
clkrst::ClkRstSession clkrst_session;
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), this->device_code));
R_ABORT_UNLESS(clkrst::OpenSession(std::addressof(clkrst_session), m_device_code));
ON_SCOPE_EXIT { clkrst::CloseSession(std::addressof(clkrst_session)); };
/* Reset the controller, setting clock rate to 408 MHz / (src_div + 1). */
@ -704,26 +704,26 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void I2cBusAccessor::SetPacketModeRegisters() {
/* Set packet mode enable. */
reg::ReadWrite(this->registers->cnfg, I2C_REG_BITS_ENUM(I2C_CNFG_PACKET_MODE_EN, GO));
reg::ReadWrite(m_registers->cnfg, I2C_REG_BITS_ENUM(I2C_CNFG_PACKET_MODE_EN, GO));
/* Set master config load. */
reg::ReadWrite(this->registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE));
reg::ReadWrite(m_registers->config_load, I2C_REG_BITS_ENUM(CONFIG_LOAD_MSTR_CONFIG_LOAD, ENABLE));
/* Set tx/fifo triggers to default (maximum values). */
reg::Write(this->registers->fifo_control, I2C_REG_BITS_VALUE(FIFO_CONTROL_RX_FIFO_TRIG, 7),
I2C_REG_BITS_VALUE(FIFO_CONTROL_TX_FIFO_TRIG, 7));
reg::Write(m_registers->fifo_control, I2C_REG_BITS_VALUE(FIFO_CONTROL_RX_FIFO_TRIG, 7),
I2C_REG_BITS_VALUE(FIFO_CONTROL_TX_FIFO_TRIG, 7));
}
Result I2cBusAccessor::FlushFifos() {
/* Flush the fifo. */
reg::Write(this->registers->fifo_control, I2C_REG_BITS_VALUE(FIFO_CONTROL_RX_FIFO_TRIG, 7),
I2C_REG_BITS_VALUE(FIFO_CONTROL_TX_FIFO_TRIG, 7),
I2C_REG_BITS_ENUM (FIFO_CONTROL_RX_FIFO_FLUSH, SET),
I2C_REG_BITS_ENUM (FIFO_CONTROL_TX_FIFO_FLUSH, SET));
reg::Write(m_registers->fifo_control, I2C_REG_BITS_VALUE(FIFO_CONTROL_RX_FIFO_TRIG, 7),
I2C_REG_BITS_VALUE(FIFO_CONTROL_TX_FIFO_TRIG, 7),
I2C_REG_BITS_ENUM (FIFO_CONTROL_RX_FIFO_FLUSH, SET),
I2C_REG_BITS_ENUM (FIFO_CONTROL_TX_FIFO_FLUSH, SET));
/* Wait up to 5 ms for the flush to complete. */
int count = 0;
while (!reg::HasValue(this->registers->fifo_control, I2C_REG_BITS_ENUM(FIFO_CONTROL_FIFO_FLUSH, RX_UNSET_TX_UNSET))) {
while (!reg::HasValue(m_registers->fifo_control, I2C_REG_BITS_ENUM(FIFO_CONTROL_FIFO_FLUSH, RX_UNSET_TX_UNSET))) {
R_UNLESS((++count < 5), i2c::ResultBusBusy());
os::SleepThread(TimeSpan::FromMilliSeconds(1));
}
@ -733,8 +733,8 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
Result I2cBusAccessor::GetTransactionResult() const {
/* Get packet status/interrupt status. */
volatile u32 packet_status = reg::Read(this->registers->packet_transfer_status);
volatile u32 interrupt_status = reg::Read(this->registers->interrupt_status_register);
volatile u32 packet_status = reg::Read(m_registers->packet_transfer_status);
volatile u32 interrupt_status = reg::Read(m_registers->interrupt_status_register);
/* Check for ack. */
R_UNLESS(reg::HasValue(packet_status, I2C_REG_BITS_ENUM(PACKET_TRANSFER_STATUS_NOACK_FOR_DATA, UNSET)), i2c::ResultNoAck());
@ -759,7 +759,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
this->ResetController();
/* Set clock registers. */
this->SetClockRegisters(this->speed_mode);
this->SetClockRegisters(m_speed_mode);
/* Set packet mode registers. */
this->SetPacketModeRegisters();

View file

@ -37,31 +37,31 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
Xfer_Read = 1,
};
private:
volatile I2cRegisters *registers;
SpeedMode speed_mode;
os::InterruptEventType interrupt_event;
int user_count;
os::SdkMutex user_count_mutex;
os::SdkMutex register_mutex;
regulator::RegulatorSession regulator_session;
bool has_regulator_session;
State state;
os::SdkMutex transaction_order_mutex;
bool is_power_bus;
dd::PhysicalAddress registers_phys_addr;
size_t registers_size;
os::InterruptName interrupt_name;
DeviceCode device_code;
util::IntrusiveListNode bus_accessor_list_node;
volatile I2cRegisters *m_registers;
SpeedMode m_speed_mode;
os::InterruptEventType m_interrupt_event;
int m_user_count;
os::SdkMutex m_user_count_mutex;
os::SdkMutex m_register_mutex;
regulator::RegulatorSession m_regulator_session;
bool m_has_regulator_session;
State m_state;
os::SdkMutex m_transaction_order_mutex;
bool m_is_power_bus;
dd::PhysicalAddress m_registers_phys_addr;
size_t m_registers_size;
os::InterruptName m_interrupt_name;
DeviceCode m_device_code;
util::IntrusiveListNode m_bus_accessor_list_node;
public:
using BusAccessorListTraits = util::IntrusiveListMemberTraitsDeferredAssert<&I2cBusAccessor::bus_accessor_list_node>;
using BusAccessorListTraits = util::IntrusiveListMemberTraitsDeferredAssert<&I2cBusAccessor::m_bus_accessor_list_node>;
using BusAccessorList = typename BusAccessorListTraits::ListType;
friend class util::IntrusiveList<I2cBusAccessor, util::IntrusiveListMemberTraitsDeferredAssert<&I2cBusAccessor::bus_accessor_list_node>>;
friend class util::IntrusiveList<I2cBusAccessor, util::IntrusiveListMemberTraitsDeferredAssert<&I2cBusAccessor::m_bus_accessor_list_node>>;
public:
I2cBusAccessor()
: registers(nullptr), speed_mode(SpeedMode_Fast), user_count(0), user_count_mutex(),
register_mutex(), has_regulator_session(false), state(State::NotInitialized), transaction_order_mutex(),
is_power_bus(false), registers_phys_addr(0), registers_size(0), interrupt_name(), device_code(-1), bus_accessor_list_node()
: m_registers(nullptr), m_speed_mode(SpeedMode_Fast), m_user_count(0), m_user_count_mutex(),
m_register_mutex(), m_has_regulator_session(false), m_state(State::NotInitialized), m_transaction_order_mutex(),
m_is_power_bus(false), m_registers_phys_addr(0), m_registers_size(0), m_interrupt_name(), m_device_code(-1), m_bus_accessor_list_node()
{
/* ... */
}
@ -69,10 +69,10 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void Initialize(dd::PhysicalAddress reg_paddr, size_t reg_size, os::InterruptName intr, bool pb, SpeedMode sm);
void RegisterDeviceCode(DeviceCode device_code);
SpeedMode GetSpeedMode() const { return this->speed_mode; }
dd::PhysicalAddress GetRegistersPhysicalAddress() const { return this->registers_phys_addr; }
size_t GetRegistersSize() const { return this->registers_size; }
os::InterruptName GetInterruptName() const { return this->interrupt_name; }
SpeedMode GetSpeedMode() const { return m_speed_mode; }
dd::PhysicalAddress GetRegistersPhysicalAddress() const { return m_registers_phys_addr; }
size_t GetRegistersSize() const { return m_registers_size; }
os::InterruptName GetInterruptName() const { return m_interrupt_name; }
private:
Result TryOpenRegulatorSession();
@ -94,8 +94,8 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
void HandleTransactionError(Result result);
void DisableInterruptMask() {
reg::Write(this->registers->interrupt_mask_register, 0);
reg::Read(this->registers->interrupt_mask_register);
reg::Write(m_registers->interrupt_mask_register, 0);
reg::Read(m_registers->interrupt_mask_register);
}
Result CheckAndHandleError() {
@ -103,7 +103,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
this->HandleTransactionError(result);
if (R_FAILED(result)) {
this->DisableInterruptMask();
os::ClearInterruptEvent(std::addressof(this->interrupt_event));
os::ClearInterruptEvent(std::addressof(m_interrupt_event));
return result;
}
@ -120,7 +120,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
virtual Result Receive(void *dst, size_t dst_size, I2cDeviceProperty *device, TransactionOption option) override;
virtual os::SdkMutex &GetTransactionOrderMutex() override {
return this->transaction_order_mutex;
return m_transaction_order_mutex;
}
virtual void SuspendBus() override;
@ -130,7 +130,7 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
virtual void ResumePowerBus() override;
virtual const DeviceCode &GetDeviceCode() const override {
return this->device_code;
return m_device_code;
}
};

View file

@ -25,48 +25,48 @@ namespace ams::i2c::driver::board::nintendo::nx::impl {
private:
using T = typename ListType::value_type;
private:
ams::MemoryResource *memory_resource;
ListType list;
mutable os::SdkMutex list_lock;
ams::MemoryResource *m_memory_resource;
ListType m_list;
mutable os::SdkMutex m_list_lock;
public:
IAllocator(ams::MemoryResource *mr) : memory_resource(mr), list(), list_lock() { /* ... */ }
IAllocator(ams::MemoryResource *mr) : m_memory_resource(mr), m_list(), m_list_lock() { /* ... */ }
~IAllocator() {
std::scoped_lock lk(this->list_lock);
std::scoped_lock lk(m_list_lock);
/* Remove all entries. */
auto it = this->list.begin();
while (it != this->list.end()) {
auto it = m_list.begin();
while (it != m_list.end()) {
T *obj = std::addressof(*it);
it = this->list.erase(it);
it = m_list.erase(it);
std::destroy_at(obj);
this->memory_resource->Deallocate(obj, sizeof(T));
m_memory_resource->Deallocate(obj, sizeof(T));
}
}
template<typename ...Args>
T *Allocate(Args &&...args) {
std::scoped_lock lk(this->list_lock);
std::scoped_lock lk(m_list_lock);
/* Allocate space for the object. */
void *storage = this->memory_resource->Allocate(sizeof(T), alignof(T));
void *storage = m_memory_resource->Allocate(sizeof(T), alignof(T));
AMS_ABORT_UNLESS(storage != nullptr);
/* Construct the object. */
T *t = std::construct_at(static_cast<T *>(storage), std::forward<Args>(args)...);
/* Link the object into our list. */
this->list.push_back(*t);
m_list.push_back(*t);
return t;
}
template<typename F>
T *Find(F f) {
std::scoped_lock lk(this->list_lock);
std::scoped_lock lk(m_list_lock);
for (T &it : this->list) {
for (T &it : m_list) {
if (f(static_cast<const T &>(it))) {
return std::addressof(it);
}