[partition] Be defensive against no device-device-available.
Scenario is this: you have no suitable installation devices on your system (everything is mounted, or HDD has died), click through to partition page, where you have all the buttons available, but no devices in the list. The following actions then cause a crash: - clicking "back" - clicking any button Prevent that: - you can click "back", but if there is no device selected nothing happens to the device state (no nullptr deref, and no crash) - button code is now more resilient to this scenario - buttons are hidden until a device is available, so you can't even click on them to trigger the code.
This commit is contained in:
parent
a35a7b108f
commit
05967311de
@ -300,6 +300,16 @@ ChoicePage::selectedDevice()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void
|
||||||
|
ChoicePage::hideButtons()
|
||||||
|
{
|
||||||
|
m_eraseButton->hide();
|
||||||
|
m_replaceButton->hide();
|
||||||
|
m_alongsideButton->hide();
|
||||||
|
m_somethingElseButton->hide();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief ChoicePage::applyDeviceChoice handler for the selected event of the device
|
* @brief ChoicePage::applyDeviceChoice handler for the selected event of the device
|
||||||
* picker. Calls ChoicePage::selectedDevice() to get the current Device*, then
|
* picker. Calls ChoicePage::selectedDevice() to get the current Device*, then
|
||||||
@ -311,7 +321,10 @@ void
|
|||||||
ChoicePage::applyDeviceChoice()
|
ChoicePage::applyDeviceChoice()
|
||||||
{
|
{
|
||||||
if ( !selectedDevice() )
|
if ( !selectedDevice() )
|
||||||
|
{
|
||||||
|
hideButtons();
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if ( m_core->isDirty() )
|
if ( m_core->isDirty() )
|
||||||
{
|
{
|
||||||
@ -342,11 +355,14 @@ ChoicePage::continueApplyDeviceChoice()
|
|||||||
// applyDeviceChoice() will be called again momentarily as soon as we handle the
|
// applyDeviceChoice() will be called again momentarily as soon as we handle the
|
||||||
// PartitionCoreModule::reverted signal.
|
// PartitionCoreModule::reverted signal.
|
||||||
if ( !currd )
|
if ( !currd )
|
||||||
|
{
|
||||||
|
hideButtons();
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
updateDeviceStatePreview();
|
updateDeviceStatePreview();
|
||||||
// Preview setup done. Now we show/hide choices as needed.
|
|
||||||
|
|
||||||
|
// Preview setup done. Now we show/hide choices as needed.
|
||||||
setupActions();
|
setupActions();
|
||||||
|
|
||||||
m_lastSelectedDeviceIndex = m_drivesCombo->currentIndex();
|
m_lastSelectedDeviceIndex = m_drivesCombo->currentIndex();
|
||||||
@ -562,7 +578,11 @@ ChoicePage::onLeave()
|
|||||||
{
|
{
|
||||||
if ( m_bootloaderComboBox.isNull() )
|
if ( m_bootloaderComboBox.isNull() )
|
||||||
{
|
{
|
||||||
m_core->setBootLoaderInstallPath( selectedDevice()->deviceNode() );
|
auto d_p = selectedDevice();
|
||||||
|
if ( d_p )
|
||||||
|
m_core->setBootLoaderInstallPath( d_p->deviceNode() );
|
||||||
|
else
|
||||||
|
cDebug() << "WARNING: No device selected for bootloader.";
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -1156,6 +1176,9 @@ ChoicePage::setupActions()
|
|||||||
else
|
else
|
||||||
m_deviceInfoWidget->setPartitionTableType( PartitionTable::unknownTableType );
|
m_deviceInfoWidget->setPartitionTableType( PartitionTable::unknownTableType );
|
||||||
|
|
||||||
|
// Manual partitioning is always a possibility
|
||||||
|
m_somethingElseButton->show();
|
||||||
|
|
||||||
bool atLeastOneCanBeResized = false;
|
bool atLeastOneCanBeResized = false;
|
||||||
bool atLeastOneCanBeReplaced = false;
|
bool atLeastOneCanBeReplaced = false;
|
||||||
bool atLeastOneIsMounted = false; // Suppress 'erase' if so
|
bool atLeastOneIsMounted = false; // Suppress 'erase' if so
|
||||||
@ -1332,18 +1355,16 @@ ChoicePage::updateNextEnabled()
|
|||||||
{
|
{
|
||||||
bool enabled = false;
|
bool enabled = false;
|
||||||
|
|
||||||
|
auto sm_p = m_beforePartitionBarsView ? m_beforePartitionBarsView->selectionModel() : nullptr;
|
||||||
|
|
||||||
switch ( m_choice )
|
switch ( m_choice )
|
||||||
{
|
{
|
||||||
case NoChoice:
|
case NoChoice:
|
||||||
enabled = false;
|
enabled = false;
|
||||||
break;
|
break;
|
||||||
case Replace:
|
case Replace:
|
||||||
enabled = m_beforePartitionBarsView->selectionModel()->
|
|
||||||
currentIndex().isValid();
|
|
||||||
break;
|
|
||||||
case Alongside:
|
case Alongside:
|
||||||
enabled = m_beforePartitionBarsView->selectionModel()->
|
enabled = sm_p && sm_p->currentIndex().isValid();
|
||||||
currentIndex().isValid();
|
|
||||||
break;
|
break;
|
||||||
case Erase:
|
case Erase:
|
||||||
case Manual:
|
case Manual:
|
||||||
|
@ -113,8 +113,12 @@ private:
|
|||||||
void setupChoices();
|
void setupChoices();
|
||||||
QComboBox* createBootloaderComboBox( QWidget* parentButton );
|
QComboBox* createBootloaderComboBox( QWidget* parentButton );
|
||||||
Device* selectedDevice();
|
Device* selectedDevice();
|
||||||
void applyDeviceChoice();
|
|
||||||
void continueApplyDeviceChoice();
|
/* Change the UI depending on the device selected. */
|
||||||
|
void hideButtons(); // Hide everything when no device
|
||||||
|
void applyDeviceChoice(); // Start scanning new device
|
||||||
|
void continueApplyDeviceChoice(); // .. called after scan
|
||||||
|
|
||||||
void updateDeviceStatePreview();
|
void updateDeviceStatePreview();
|
||||||
void updateActionChoicePreview( ChoicePage::Choice choice );
|
void updateActionChoicePreview( ChoicePage::Choice choice );
|
||||||
void setupActions();
|
void setupActions();
|
||||||
|
Loading…
Reference in New Issue
Block a user