diff options
-rw-r--r-- | zephyr/zmake/tests/test_version.py | 88 | ||||
-rw-r--r-- | zephyr/zmake/zmake/version.py | 75 |
2 files changed, 163 insertions, 0 deletions
diff --git a/zephyr/zmake/tests/test_version.py b/zephyr/zmake/tests/test_version.py new file mode 100644 index 0000000000..4235561545 --- /dev/null +++ b/zephyr/zmake/tests/test_version.py @@ -0,0 +1,88 @@ +# Copyright 2021 The Chromium OS Authors. All rights reserved. +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +import subprocess + +import zmake.project +import zmake.version as version + + +def _git_init(repo): + """Create a new git repository.""" + repo.mkdir() + subprocess.run(['git', '-c', 'init.defaultBranch=main', '-C', repo, 'init'], + check=True) + + +def _git_add(repo, path, contents='example!\n'): + """Write contents and stage a file.""" + path.write_text(contents) + subprocess.run(['git', '-C', repo, 'add', path], check=True) + + +def _git_commit(repo, message='message!'): + env = { + 'GIT_AUTHOR_NAME': 'Alyssa P. Hacker', + 'GIT_AUTHOR_EMAIL': 'aphacker@example.org', + 'GIT_AUTHOR_DATE': 'Thu, 07 Apr 2005 22:13:13 +0200', + 'GIT_COMMITTER_NAME': 'Ben Bitdiddle', + 'GIT_COMMITTER_EMAIL': 'bitdiddle@example.org', + 'GIT_COMMITTER_DATE': 'Tue, 30 Aug 2005 10:50:30 -0700', + } + subprocess.run(['git', '-C', repo, 'commit', '-m', message], check=True, + env=env) + + +def _setup_example_repos(tmp_path): + """Setup temporary project, zephyr base, and module repos. + + Args: + tmp_path: Directory to set up files in. + + Returns: + A 3-tuple of project, zephyr_base, modules_dict. + """ + project_path = tmp_path / 'prj' + project_path.mkdir() + + project = zmake.project.Project( + project_path, + config_dict={'board': 'foo', 'toolchain': 'bar', + 'output-type': 'raw', + 'supported-zephyr-versions': ['v2.5']}) + # Has one commit. + zephyr_base = tmp_path / 'zephyr_base' + _git_init(zephyr_base) + _git_add(zephyr_base, zephyr_base / 'VERSION', + 'VERSION_MAJOR=2\nVERSION_MINOR=5\nPATCHLEVEL=99\n') + _git_commit(zephyr_base, 'Added version file') + + # Has one commit. + mod1 = tmp_path / 'mod1' + _git_init(mod1) + _git_add(mod1, mod1 / 'file1') + _git_commit(mod1) + + # Has two commits. + mod2 = tmp_path / 'mod2' + _git_init(mod2) + _git_add(mod2, mod2 / 'file2') + _git_commit(mod2) + _git_add(mod2, mod2 / 'file3') + _git_commit(mod2) + + return project, zephyr_base, {'mod1': mod1, 'mod2': mod2} + + +def test_version_string(tmp_path): + project, zephyr_base, modules = _setup_example_repos(tmp_path) + assert (version.get_version_string(project, zephyr_base, modules) + == 'prj_v2.5.4_mod1:02fd7a,mod2:b5991f,os:2c65cb') + + +def test_version_string_static(tmp_path): + project, zephyr_base, modules = _setup_example_repos(tmp_path) + assert (version.get_version_string(project, zephyr_base, modules, + static=True) + == 'prj_v2.5.0_STATIC') diff --git a/zephyr/zmake/zmake/version.py b/zephyr/zmake/zmake/version.py new file mode 100644 index 0000000000..03ffada947 --- /dev/null +++ b/zephyr/zmake/zmake/version.py @@ -0,0 +1,75 @@ +# Copyright 2021 The Chromium OS Authors. All rights reserved. +# Use of this source code is governed by a BSD-style license that can be +# found in the LICENSE file. + +import subprocess + +import zmake.util as util + + +def _get_num_commits(repo): + """Get the number of commits that have been made in a Git repository. + + Args: + repo: The path to the git repo. + + Returns: + An integer, the number of commits that have been made. + """ + result = subprocess.run(['git', '-C', repo, 'rev-list', 'HEAD', '--count'], + check=True, stdout=subprocess.PIPE, + encoding='utf-8') + return int(result.stdout) + + +def _get_revision(repo): + """Get the index's current revision of a Git repo. + + Args: + repo: The path to the git repo. + + Returns: + A string, of the current revision. + """ + result = subprocess.run(['git', '-C', repo, 'log', '-n1', '--format=%H'], + check=True, stdout=subprocess.PIPE, + encoding='utf-8') + return result.stdout + + +def get_version_string(project, zephyr_base, modules, static=False): + """Get the version string associated with a build. + + Args: + project: a zmake.project.Project object + zephyr_base: the path to the zephyr directory + modules: a dictionary mapping module names to module paths + static: if set, create a version string not dependent on git + commits, thus allowing binaries to be compared between two + commits. + + Returns: + A version string which can be placed in FRID, FWID, or used in + the build for the OS. + """ + major_version, minor_version, *_ = util.read_zephyr_version(zephyr_base) + project_id = project.project_dir.parts[-1] + num_commits = 0 + + if static: + vcs_hashes = 'STATIC' + else: + repos = { + 'os': zephyr_base, + **modules, + } + + for repo in repos.values(): + num_commits += _get_num_commits(repo) + + vcs_hashes = ','.join( + '{}:{}'.format(name, _get_revision(repo)[:6]) + for name, repo in sorted(repos.items())) + + return '{}_v{}.{}.{}_{}'.format( + project_id, major_version, minor_version, num_commits, vcs_hashes) |