Skip to content

Commit

Permalink
Add support for isomd5sum for tagging iso files
Browse files Browse the repository at this point in the history
The isomd5sum tool suite is used and available on all supported
distributions except SUSE distributions, and is necessary to produce
conformant ISOs for most Linux distributions.

This change adds support for isomd5sum tool suite for kiwi, though
it does not extend the kiwi-live dracut module to use it. The upstream
dracut dmsquash-live module must be used instead.

Co-authored-by: Dan Čermák <[email protected]>
  • Loading branch information
Conan-Kudo and dcermak committed Aug 26, 2024
1 parent 11ce3a5 commit 0031b6c
Show file tree
Hide file tree
Showing 11 changed files with 113 additions and 13 deletions.
3 changes: 3 additions & 0 deletions kiwi.yml
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,9 @@
# # Specify tool category which should be used to build iso images
# # Possible values are: xorriso
# - tool_category: xorriso
# # Specify media tag tool used to implant iso checksums
# # Possible values are checkmedia and isomd5sum
# - media_tag_tool: checkmedia


# Setup process parameters for OCI toolchain
Expand Down
11 changes: 11 additions & 0 deletions kiwi/defaults.py
Original file line number Diff line number Diff line change
Expand Up @@ -1758,6 +1758,17 @@ def get_iso_tool_category():
"""
return 'xorriso'

@staticmethod
def get_iso_media_tag_tool():
"""
Provides default iso media tag tool
:return: name
:rtype: str
"""
return 'checkmedia'

@staticmethod
def get_container_compression():
"""
Expand Down
29 changes: 20 additions & 9 deletions kiwi/iso_tools/iso.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
# project
from kiwi.defaults import Defaults
from kiwi.command import Command
from kiwi.runtime_config import RuntimeConfig


class Iso:
Expand All @@ -42,12 +43,22 @@ def set_media_tag(isofile: str) -> None:
:param str isofile: path to the ISO file
"""
Command.run(
[
'tagmedia',
'--digest', 'sha256',
'--check',
'--pad', '0',
isofile
]
)
media_tagger = RuntimeConfig().get_iso_media_tag_tool()
if media_tagger == 'checkmedia':
Command.run(
[
'tagmedia',
'--digest', 'sha256',
'--check',
'--pad', '0',
isofile
]
)
elif media_tagger == 'isomd5sum':
Command.run(
[
'implantisomd5',
'--force',
isofile
]
)
5 changes: 5 additions & 0 deletions kiwi/runtime_checker.py
Original file line number Diff line number Diff line change
Expand Up @@ -919,6 +919,11 @@ def check_mediacheck_installed(self) -> None:
''')
if self.xml_state.build_type.get_mediacheck() is True:
tool = 'tagmedia'
media_tagger = RuntimeConfig().get_iso_media_tag_tool()
if media_tagger == 'checkmedia':
tool = 'tagmedia'
elif media_tagger == 'isomd5sum':
tool = 'implantisomd5'
if not Path.which(filename=tool, access_mode=os.X_OK):
raise KiwiRuntimeError(
message_tool_not_found.format(name=tool)
Expand Down
31 changes: 31 additions & 0 deletions kiwi/runtime_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -309,6 +309,37 @@ def get_iso_tool_category(self):
)
return Defaults.get_iso_tool_category()

def get_iso_media_tag_tool(self):
"""
Return media tag tool used to checksum iso images
iso:
- media_tag_tool: checkmedia
if no or invalid configuration exists the default media tagger
from the Defaults class is returned
:return: A name
:rtype: str
"""
iso_media_tag_tool = self._get_attribute(
element='iso', attribute='media_tag_tool'
)
if not iso_media_tag_tool:
return Defaults.get_iso_media_tag_tool()
elif 'checkmedia' in iso_media_tag_tool:
return iso_media_tag_tool
elif 'isomd5sum' in iso_media_tag_tool:
return iso_media_tag_tool
else:
log.warning(
'Skipping invalid iso media tag tool: {0}'.format(
iso_media_tag_tool
)
)
return Defaults.get_iso_media_tag_tool()

def get_oci_archive_tool(self):
"""
Return OCI archive tool which should be used on creation of
Expand Down
1 change: 1 addition & 0 deletions test/data/kiwi_config/invalid/.config/kiwi/config.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
iso:
- tool_category: foo
- media_tag_tool: foo

container:
- compress: foo
1 change: 1 addition & 0 deletions test/data/kiwi_config/ok/.config/kiwi/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ obs:

iso:
- tool_category: xorriso
- media_tag_tool: isomd5sum

oci:
- archive_tool: umoci
Expand Down
3 changes: 3 additions & 0 deletions test/data/kiwi_config/other/.config/kiwi/config.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,6 @@ bundle:

container:
- compress: true

iso:
- media_tag_tool: checkmedia
19 changes: 17 additions & 2 deletions test/unit/iso_tools/iso_test.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
from unittest.mock import patch
from unittest.mock import patch, Mock

from kiwi.defaults import Defaults
from kiwi.iso_tools.iso import Iso
Expand All @@ -13,8 +13,23 @@ def setup_method(self, cls):
self.setup()

@patch('kiwi.iso_tools.iso.Command.run')
def test_set_media_tag(self, mock_command):
@patch('kiwi.iso_tools.iso.RuntimeConfig')
def test_set_media_tag_checkmedia(self, mock_RuntimeConfig, mock_command):
runtime_config = Mock()
runtime_config.get_iso_media_tag_tool.return_value = 'checkmedia'
mock_RuntimeConfig.return_value = runtime_config
Iso.set_media_tag('foo')
mock_command.assert_called_once_with(
['tagmedia', '--digest', 'sha256', '--check', '--pad', '0', 'foo']
)

@patch('kiwi.iso_tools.iso.Command.run')
@patch('kiwi.iso_tools.iso.RuntimeConfig')
def test_set_media_tag_isomd5sum(self, mock_RuntimeConfig, mock_command):
runtime_config = Mock()
runtime_config.get_iso_media_tag_tool.return_value = 'isomd5sum'
mock_RuntimeConfig.return_value = runtime_config
Iso.set_media_tag('foo')
mock_command.assert_called_once_with(
['implantisomd5', '--force', 'foo']
)
15 changes: 13 additions & 2 deletions test/unit/runtime_checker_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
from pytest import (
raises, fixture
)
import pytest

from .test_helper import argv_kiwi_tests

Expand Down Expand Up @@ -358,16 +359,26 @@ def test_check_efi_mode_for_disk_overlay_correctly_setup(self):
self.runtime_checker.\
check_efi_mode_for_disk_overlay_correctly_setup()

@pytest.mark.parametrize("tool_name, tool_binary", [("isomd5sum", "implantisomd5"), ("checkmedia", "tagmedia")])
@patch('kiwi.runtime_checker.Path.which')
def test_check_mediacheck_installed_tagmedia_missing(self, mock_which):
@patch('kiwi.runtime_checker.RuntimeConfig')
def test_check_mediacheck_installed_implantisomd5_missing(
self, mock_RuntimeConfig, mock_which, tool_name, tool_binary
):
runtime_config = Mock()
runtime_config.get_iso_media_tag_tool.return_value = tool_name
mock_RuntimeConfig.return_value = runtime_config

mock_which.return_value = False
xml_state = XMLState(
self.description.load(), ['vmxFlavour'], 'iso'
)
runtime_checker = RuntimeChecker(xml_state)
with raises(KiwiRuntimeError):
with raises(KiwiRuntimeError) as rt_err_ctx:
runtime_checker.check_mediacheck_installed()

assert f"Required tool {tool_binary} not found in caller environment" in str(rt_err_ctx.value)

def test_check_dracut_module_for_live_iso_in_package_list(self):
xml_state = XMLState(
self.description.load(), ['vmxFlavour'], 'iso'
Expand Down
8 changes: 8 additions & 0 deletions test/unit/runtime_config_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ def test_config_sections_from_home_base_config(self, mock_is_buildservice_worker
'https://api.example.com'
assert runtime_config.get_container_compression() is False
assert runtime_config.get_iso_tool_category() == 'xorriso'
assert runtime_config.get_iso_media_tag_tool() == 'isomd5sum'
assert runtime_config.get_oci_archive_tool() == 'umoci'
assert runtime_config.get_mapper_tool() == 'partx'
assert runtime_config.get_package_changes() is True
Expand Down Expand Up @@ -96,6 +97,7 @@ def test_config_sections_defaults(
Defaults.get_obs_api_server_url()
assert runtime_config.get_container_compression() is True
assert runtime_config.get_iso_tool_category() == 'xorriso'
assert runtime_config.get_iso_media_tag_tool() == 'checkmedia'
assert runtime_config.get_oci_archive_tool() == 'umoci'
assert runtime_config.get_mapper_tool() == 'kpartx'
assert runtime_config.get_package_changes() is False
Expand All @@ -120,9 +122,15 @@ def test_config_sections_invalid(self):
assert 'Skipping invalid iso tool category: foo' in \
self._caplog.text

with self._caplog.at_level(logging.WARNING):
assert runtime_config.get_iso_media_tag_tool() == "checkmedia"
assert 'Skipping invalid iso media tag tool: foo' in \
self._caplog.text

def test_config_sections_other_settings(self):
with patch.dict('os.environ', {'HOME': '../data/kiwi_config/other'}):
runtime_config = RuntimeConfig(reread=True)

assert runtime_config.get_container_compression() is True
assert runtime_config.get_package_changes() is True
assert runtime_config.get_iso_media_tag_tool() == "checkmedia"

0 comments on commit 0031b6c

Please sign in to comment.