Merge branch 'calamares' of https://github.com/calamares/calamares into development
This commit is contained in:
commit
100f408dae
@ -54,8 +54,9 @@ class cpuinfo(object):
|
||||
self.number_of_cores = 0
|
||||
|
||||
cpu = self._cpuinfo()
|
||||
self.is_intel = cpu['proc0']['vendor_id'].lower() == "genuineintel"
|
||||
self.is_amd = cpu['proc0']['vendor_id'].lower() == "authenticamd"
|
||||
if 'vendor_id' in cpu['proc0']:
|
||||
self.is_intel = cpu['proc0']['vendor_id'].lower() == "genuineintel"
|
||||
self.is_amd = cpu['proc0']['vendor_id'].lower() == "authenticamd"
|
||||
self.number_of_cores = len(cpu)
|
||||
|
||||
@staticmethod
|
||||
|
@ -9,7 +9,6 @@ calamares_add_plugin(luksbootkeyfile
|
||||
SOURCES
|
||||
LuksBootKeyFileJob.cpp
|
||||
SHARED_LIB
|
||||
NO_CONFIG
|
||||
)
|
||||
|
||||
calamares_add_test(luksbootkeyfiletest SOURCES Tests.cpp LuksBootKeyFileJob.cpp)
|
||||
|
@ -135,34 +135,64 @@ generateTargetKeyfile()
|
||||
}
|
||||
|
||||
static bool
|
||||
setupLuks( const LuksDevice& d )
|
||||
setupLuks( const LuksDevice& d, const QString& luks2Hash )
|
||||
{
|
||||
// Sometimes this error is thrown: "All key slots full"
|
||||
// luksAddKey will fail. So, remove the first slot to make room
|
||||
// Get luksDump for this device
|
||||
auto luks_dump = CalamaresUtils::System::instance()->targetEnvCommand(
|
||||
{ "cryptsetup", "luksDump", d.device }, QString(), QString(), std::chrono::seconds( 5 ) );
|
||||
if ( luks_dump.getExitCode() == 0 )
|
||||
{ QStringLiteral( "cryptsetup" ), QStringLiteral( "luksDump" ), d.device },
|
||||
QString(),
|
||||
QString(),
|
||||
std::chrono::seconds( 5 ) );
|
||||
if ( luks_dump.getExitCode() != 0 )
|
||||
{
|
||||
QRegularExpression re( QStringLiteral( R"(\d+:\s*enabled)" ), QRegularExpression::CaseInsensitiveOption );
|
||||
int count = luks_dump.getOutput().count( re );
|
||||
cDebug() << "Luks Dump slot count: " << count;
|
||||
if ( count >= 7 )
|
||||
cWarning() << "Could not get LUKS information on " << d.device << ':' << luks_dump.getOutput() << "(exit code"
|
||||
<< luks_dump.getExitCode() << ')';
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check LUKS version
|
||||
int luks_version = 0;
|
||||
QRegularExpression version_re( QStringLiteral( R"(version:\s*([0-9]))" ),
|
||||
QRegularExpression::CaseInsensitiveOption );
|
||||
QRegularExpressionMatch match = version_re.match( luks_dump.getOutput() );
|
||||
if ( ! match.hasMatch() )
|
||||
{
|
||||
cWarning() << "Could not get LUKS version on device: " << d.device;
|
||||
return false;
|
||||
}
|
||||
bool ok;
|
||||
luks_version = match.captured(1).toInt(&ok);
|
||||
if( ! ok )
|
||||
{
|
||||
cWarning() << "Could not get LUKS version on device: " << d.device;
|
||||
return false;
|
||||
}
|
||||
cDebug() << "LUKS" << luks_version << " found on device: " << d.device;
|
||||
|
||||
// Check the number of slots used for LUKS1 devices
|
||||
if ( luks_version == 1 )
|
||||
{
|
||||
QRegularExpression slots_re( QStringLiteral( R"(\d+:\s*enabled)" ),
|
||||
QRegularExpression::CaseInsensitiveOption );
|
||||
if ( luks_dump.getOutput().count( slots_re ) == 8 )
|
||||
{
|
||||
auto r = CalamaresUtils::System::instance()->targetEnvCommand(
|
||||
{ "cryptsetup", "luksKillSlot", d.device, "1" }, QString(), d.passphrase, std::chrono::seconds( 60 ) );
|
||||
if ( r.getExitCode() != 0 )
|
||||
{
|
||||
cWarning() << "Could not kill a slot to make room on" << d.device << ':' << r.getOutput()
|
||||
<< "(exit code" << r.getExitCode() << ')';
|
||||
return false;
|
||||
}
|
||||
cWarning() << "No key slots left on LUKS1 device: " << d.device;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Adding the key can take some times, measured around 15 seconds with
|
||||
// a HDD (spinning rust) and a slow-ish computer. Give it a minute.
|
||||
// Add the key to the keyfile
|
||||
QStringList args = { QStringLiteral( "cryptsetup" ), QStringLiteral( "luksAddKey" ), d.device, keyfile };
|
||||
if ( luks_version == 2 && luks2Hash != QString() )
|
||||
{
|
||||
args.insert(2, "--pbkdf");
|
||||
args.insert(3, luks2Hash);
|
||||
}
|
||||
auto r = CalamaresUtils::System::instance()->targetEnvCommand(
|
||||
{ "cryptsetup", "luksAddKey", d.device, keyfile }, QString(), d.passphrase, std::chrono::seconds( 60 ) );
|
||||
args,
|
||||
QString(),
|
||||
d.passphrase,
|
||||
std::chrono::seconds( 60 ) );
|
||||
if ( r.getExitCode() != 0 )
|
||||
{
|
||||
cWarning() << "Could not configure LUKS keyfile on" << d.device << ':' << r.getOutput() << "(exit code"
|
||||
@ -259,15 +289,15 @@ LuksBootKeyFileJob::exec()
|
||||
|
||||
if ( it == s.devices.begin() )
|
||||
{
|
||||
// Then there was no root partition
|
||||
cDebug() << Logger::SubEntry << "No root partition.";
|
||||
// User has configured non-root partition for encryption
|
||||
cDebug() << Logger::SubEntry << "No root partition, skipping keyfile creation.";
|
||||
return Calamares::JobResult::ok();
|
||||
}
|
||||
|
||||
// /boot partition is not encrypted, keyfile must not be used
|
||||
// But only if root partition is not encrypted
|
||||
if ( hasUnencryptedSeparateBoot() && !hasEncryptedRoot() )
|
||||
{
|
||||
// /boot partition is not encrypted, keyfile must not be used
|
||||
// But only if root partition is not encrypted
|
||||
cDebug() << Logger::SubEntry << "/boot partition is not encrypted, skipping keyfile creation.";
|
||||
return Calamares::JobResult::ok();
|
||||
}
|
||||
@ -295,13 +325,22 @@ LuksBootKeyFileJob::exec()
|
||||
continue;
|
||||
}
|
||||
|
||||
if ( !setupLuks( d ) )
|
||||
return Calamares::JobResult::error(
|
||||
tr( "Encrypted rootfs setup error" ),
|
||||
tr( "Could not configure LUKS key file on partition %1." ).arg( d.device ) );
|
||||
if ( !setupLuks( d, m_luks2Hash ) )
|
||||
{
|
||||
// Could not configure the LUKS partition
|
||||
// This should not stop the installation: do not return Calamares::JobResult::error.
|
||||
cError() << "Encrypted rootfs setup error: could not configure LUKS key file on partition " << d.device;
|
||||
}
|
||||
}
|
||||
|
||||
return Calamares::JobResult::ok();
|
||||
}
|
||||
|
||||
void
|
||||
LuksBootKeyFileJob::setConfigurationMap( const QVariantMap& configurationMap )
|
||||
{
|
||||
m_luks2Hash = CalamaresUtils::getString(
|
||||
configurationMap, QStringLiteral( "luks2Hash" ), QString() );
|
||||
}
|
||||
|
||||
CALAMARES_PLUGIN_FACTORY_DEFINITION( LuksBootKeyFileJobFactory, registerPlugin< LuksBootKeyFileJob >(); )
|
||||
|
@ -30,6 +30,11 @@ public:
|
||||
QString prettyName() const override;
|
||||
|
||||
Calamares::JobResult exec() override;
|
||||
|
||||
void setConfigurationMap( const QVariantMap& configurationMap ) override;
|
||||
|
||||
private:
|
||||
QString m_luks2Hash;
|
||||
};
|
||||
|
||||
CALAMARES_PLUGIN_FACTORY_DECLARATION( LuksBootKeyFileJobFactory )
|
||||
|
13
src/modules/luksbootkeyfile/luksbootkeyfile.conf
Normal file
13
src/modules/luksbootkeyfile/luksbootkeyfile.conf
Normal file
@ -0,0 +1,13 @@
|
||||
# SPDX-FileCopyrightText: no
|
||||
# SPDX-License-Identifier: CC0-1.0
|
||||
#
|
||||
# Luksbootkeyfile configuration. A key file is created for the
|
||||
# LUKS encrypted devices.
|
||||
---
|
||||
# Set Password-Based Key Derivation Function (PBKDF) algorithm
|
||||
# for LUKS keyslot.
|
||||
#
|
||||
# There are three usable values: pbkdf2, argon2i or argon2id.
|
||||
#
|
||||
# When not set, the cryptsetup default is used
|
||||
#luks2Hash: argon2id
|
9
src/modules/luksbootkeyfile/luksbootkeyfile.schema.yaml
Normal file
9
src/modules/luksbootkeyfile/luksbootkeyfile.schema.yaml
Normal file
@ -0,0 +1,9 @@
|
||||
# SPDX-FileCopyrightText: 2023 Arjen Balfoort <arjenbalfoort@hotmail.com>
|
||||
# SPDX-License-Identifier: GPL-3.0-or-later
|
||||
---
|
||||
$schema: https://json-schema.org/schema#
|
||||
$id: https://calamares.io/schemas/luksbootkeyfile
|
||||
additionalProperties: false
|
||||
type: object
|
||||
properties:
|
||||
luks2Hash: { type: string, enum: [ pbkdf2, argon2i, argon2id ] }
|
@ -31,7 +31,7 @@
|
||||
# # finally masks pacman-init (an ArchLinux-only service).
|
||||
# #
|
||||
# units:
|
||||
# - name: "NetworkManager"
|
||||
# - name: "NetworkManager.service"
|
||||
# action: "enable"
|
||||
# mandatory: true
|
||||
#
|
||||
@ -40,12 +40,12 @@
|
||||
# # The property "mandatory" is taken to be false by default here
|
||||
# # because it is not specified
|
||||
#
|
||||
# - name: "graphical"
|
||||
# - name: "graphical.target"
|
||||
# action: "enable"
|
||||
# # The property "mandatory" is taken to be false by default here
|
||||
# # because it is not specified
|
||||
#
|
||||
# - name: "pacman-init"
|
||||
# - name: "pacman-init.service"
|
||||
# action: "mask"
|
||||
# # The property "mandatory" is taken to be false by default here
|
||||
# # because it is not specified
|
||||
|
Loading…
Reference in New Issue
Block a user