mirror of
https://github.com/RGBCube/serenity
synced 2025-07-26 08:37:45 +00:00
Kernel/AHCI: Simplify wait and timeout pattern significantly
Instead of repeating ourselves with the pattern of waiting for some condition to be met, we can have a general method for this task, and then we can provide the retry count, the required delay and a lambda function for the checked condition.
This commit is contained in:
parent
557351724a
commit
0e5983e603
2 changed files with 26 additions and 22 deletions
|
@ -405,14 +405,11 @@ void AHCIPort::rebase()
|
||||||
stop_command_list_processing();
|
stop_command_list_processing();
|
||||||
stop_fis_receiving();
|
stop_fis_receiving();
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
size_t retry = 0;
|
|
||||||
// Try to wait 1 second for HBA to clear Command List Running and FIS Receive Running
|
// Try to wait 1 second for HBA to clear Command List Running and FIS Receive Running
|
||||||
while (retry < 1000) {
|
wait_until_condition_met_or_timeout(1000, 1000, [this]() -> bool {
|
||||||
if (!(m_port_registers.cmd & (1 << 15)) && !(m_port_registers.cmd & (1 << 14)))
|
return !(m_port_registers.cmd & (1 << 15)) && !(m_port_registers.cmd & (1 << 14));
|
||||||
break;
|
});
|
||||||
IO::delay(1000);
|
|
||||||
retry++;
|
|
||||||
}
|
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
m_port_registers.clbu = 0;
|
m_port_registers.clbu = 0;
|
||||||
m_port_registers.clb = m_command_list_page->paddr().get();
|
m_port_registers.clb = m_command_list_page->paddr().get();
|
||||||
|
@ -690,6 +687,17 @@ bool AHCIPort::identify_device()
|
||||||
return success;
|
return success;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void AHCIPort::wait_until_condition_met_or_timeout(size_t delay_in_microseconds, size_t retries, Function<bool(void)> condition_being_met) const
|
||||||
|
{
|
||||||
|
size_t retry = 0;
|
||||||
|
while (retry < retries) {
|
||||||
|
if (condition_being_met())
|
||||||
|
break;
|
||||||
|
IO::delay(delay_in_microseconds);
|
||||||
|
retry++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool AHCIPort::shutdown()
|
bool AHCIPort::shutdown()
|
||||||
{
|
{
|
||||||
MutexLocker locker(m_lock);
|
MutexLocker locker(m_lock);
|
||||||
|
@ -786,15 +794,13 @@ bool AHCIPort::initiate_sata_reset()
|
||||||
dbgln_if(AHCI_DEBUG, "AHCI Port {}: Initiate SATA reset", representative_port_index());
|
dbgln_if(AHCI_DEBUG, "AHCI Port {}: Initiate SATA reset", representative_port_index());
|
||||||
stop_command_list_processing();
|
stop_command_list_processing();
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
size_t retry = 0;
|
|
||||||
|
// Note: The AHCI specification says to wait now a 500 milliseconds
|
||||||
// Try to wait 1 second for HBA to clear Command List Running
|
// Try to wait 1 second for HBA to clear Command List Running
|
||||||
while (retry < 5000) {
|
wait_until_condition_met_or_timeout(100, 5000, [this]() -> bool {
|
||||||
if (!(m_port_registers.cmd & (1 << 15)))
|
return !(m_port_registers.cmd & (1 << 15));
|
||||||
break;
|
});
|
||||||
// The AHCI specification says to wait now a 500 milliseconds
|
|
||||||
IO::delay(100);
|
|
||||||
retry++;
|
|
||||||
}
|
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
spin_up();
|
spin_up();
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
|
@ -804,14 +810,10 @@ bool AHCIPort::initiate_sata_reset()
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
set_interface_state(AHCI::DeviceDetectionInitialization::NoActionRequested);
|
set_interface_state(AHCI::DeviceDetectionInitialization::NoActionRequested);
|
||||||
full_memory_barrier();
|
full_memory_barrier();
|
||||||
retry = 0;
|
|
||||||
while (retry < 1000) {
|
|
||||||
if (is_phy_enabled())
|
|
||||||
break;
|
|
||||||
|
|
||||||
IO::delay(10);
|
wait_until_condition_met_or_timeout(10, 1000, [this]() -> bool {
|
||||||
retry++;
|
return is_phy_enabled();
|
||||||
}
|
});
|
||||||
|
|
||||||
dmesgln("AHCI Port {}: {}", representative_port_index(), try_disambiguate_sata_status());
|
dmesgln("AHCI Port {}: {}", representative_port_index(), try_disambiguate_sata_status());
|
||||||
|
|
||||||
|
|
|
@ -99,6 +99,8 @@ private:
|
||||||
|
|
||||||
ALWAYS_INLINE bool is_interface_disabled() const { return (m_port_registers.ssts & 0xf) == 4; };
|
ALWAYS_INLINE bool is_interface_disabled() const { return (m_port_registers.ssts & 0xf) == 4; };
|
||||||
|
|
||||||
|
ALWAYS_INLINE void wait_until_condition_met_or_timeout(size_t delay_in_microseconds, size_t retries, Function<bool(void)> condition_being_met) const;
|
||||||
|
|
||||||
// Data members
|
// Data members
|
||||||
|
|
||||||
EntropySource m_entropy_source;
|
EntropySource m_entropy_source;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue