diff --git a/MODULE.bazel.lock b/MODULE.bazel.lock index 6160c3c..27b909e 100644 --- a/MODULE.bazel.lock +++ b/MODULE.bazel.lock @@ -869,7 +869,7 @@ "moduleExtensions": { "//:extensions.bzl%arm_toolchain": { "general": { - "bzlTransitiveDigest": "cMJJ7TWcbR1Ywfy9fx9zPw3P6lQJ5msZ2UjVsYibxq0=", + "bzlTransitiveDigest": "EXL8Hi/m20JvnpquGOQ6fG/k6kAEh+mtGNhs7x/wX4A=", "accumulatedFileDigests": {}, "envVariables": {}, "generatedRepoSpecs": { diff --git a/deps.bzl b/deps.bzl index 8ac0dbf..fe584a9 100644 --- a/deps.bzl +++ b/deps.bzl @@ -1,5 +1,6 @@ """deps.bzl""" +load("@toolchains_arm_gnu//:version.bzl", "latest_version") load("@toolchains_arm_gnu//toolchain:toolchain.bzl", "tools") load("@toolchains_arm_gnu//toolchain/archives:aarch64_none_elf.bzl", "AARCH64_NONE_ELF") load("@toolchains_arm_gnu//toolchain/archives:aarch64_none_linux_gnu.bzl", "AARCH64_NONE_LINUX_GNU") @@ -120,7 +121,7 @@ def toolchains_arm_gnu_deps(toolchain, toolchain_prefix, version, archives): **attrs ) -def arm_none_eabi_deps(version = "13.2.1", archives = ARM_NONE_EABI): +def arm_none_eabi_deps(version = latest_version("arm-none-eabi"), archives = ARM_NONE_EABI): """Workspace dependencies for the arm none eabi gcc toolchain Args: @@ -134,7 +135,7 @@ def arm_none_eabi_deps(version = "13.2.1", archives = ARM_NONE_EABI): archives, ) -def arm_none_linux_gnueabihf_deps(version = "13.2.1", archives = ARM_NONE_LINUX_GNUEABIHF): +def arm_none_linux_gnueabihf_deps(version = latest_version("arm-none-linux-gnueabihf"), archives = ARM_NONE_LINUX_GNUEABIHF): """Workspace dependencies for the arm linux gcc toolchain Args: @@ -148,7 +149,7 @@ def arm_none_linux_gnueabihf_deps(version = "13.2.1", archives = ARM_NONE_LINUX_ archives, ) -def aarch64_none_elf_deps(version = "13.2.1-1.1", archives = AARCH64_NONE_ELF): +def aarch64_none_elf_deps(version = latest_version("aarch64-none-elf"), archives = AARCH64_NONE_ELF): """Workspace dependencies for the arm gcc toolchain Args: @@ -162,7 +163,7 @@ def aarch64_none_elf_deps(version = "13.2.1-1.1", archives = AARCH64_NONE_ELF): archives, ) -def aarch64_none_linux_gnu_deps(version = "13.2.1", archives = AARCH64_NONE_LINUX_GNU): +def aarch64_none_linux_gnu_deps(version = latest_version("aarch64-none-linux-gnu"), archives = AARCH64_NONE_LINUX_GNU): """Workspace dependencies for the arm linux gcc toolchain Args: diff --git a/extensions.bzl b/extensions.bzl index f5b004f..38765b4 100644 --- a/extensions.bzl +++ b/extensions.bzl @@ -7,28 +7,7 @@ load( "arm_none_eabi_deps", "arm_none_linux_gnueabihf_deps", ) -load("@toolchains_arm_gnu//toolchain/archives:aarch64_none_elf.bzl", "AARCH64_NONE_ELF") -load( - "@toolchains_arm_gnu//toolchain/archives:aarch64_none_linux_gnu.bzl", - "AARCH64_NONE_LINUX_GNU", -) -load( - "@toolchains_arm_gnu//toolchain/archives:arm_none_eabi.bzl", - "ARM_NONE_EABI", -) -load( - "@toolchains_arm_gnu//toolchain/archives:arm_none_linux_gnueabihf.bzl", - "ARM_NONE_LINUX_GNUEABIHF", -) - -def _semver(version): - """Parse a semantic version string into a list of integers.""" - parts = [int(i.split("-")[0]) for i in version.split(".")] - return struct( - major = parts[0], - minor = parts[1], - patch = parts[2], - ) +load("@toolchains_arm_gnu//:version.bzl", "latest_version", "min_version") def _module_toolchain(tag, deps): """Return a module toolchain.""" @@ -37,39 +16,6 @@ def _module_toolchain(tag, deps): deps = deps, ) -def _compare_versions(left, right): - """Compare two semantic versions.""" - left = _semver(left) - right = _semver(right) - - # (a < b): -1, (a > b): 1, (a == b): 0. - compare = lambda a, b: int(a > b) - int(a < b) - - return compare(left.major, right.major) or \ - compare(left.minor, right.minor) or \ - compare(left.patch, right.patch) or \ - 0 - -def _max_version(versions): - """Obtains the minimum version from the list of version strings.""" - if versions: - maximum = versions.pop(0) - for version in versions: - if _compare_versions(maximum, version) < 0: - maximum = version - return maximum - return None - -def _min_version(versions): - """Obtains the minimum version from the list of version strings.""" - if versions: - minimum = versions.pop(0) - for version in versions: - if _compare_versions(minimum, version) > 0: - minimum = version - return minimum - return None - def _arm_toolchain_impl(ctx): """Implement the module extension.""" @@ -94,7 +40,7 @@ def _arm_toolchain_impl(ctx): for toolchain in available_toolchains: versions = [attr.version for mod in ctx.modules for attr in toolchain.tag(mod)] - selected = _min_version(versions) + selected = min_version(versions) if selected: toolchain.deps(version = selected) @@ -102,16 +48,16 @@ arm_toolchain = module_extension( implementation = _arm_toolchain_impl, tag_classes = { "arm_none_eabi": tag_class(attrs = { - "version": attr.string(default = _max_version(ARM_NONE_EABI.keys())), + "version": attr.string(default = latest_version("arm-none-eabi")), }), "arm_none_linux_gnueabihf": tag_class(attrs = { - "version": attr.string(default = _max_version(ARM_NONE_LINUX_GNUEABIHF.keys())), + "version": attr.string(default = latest_version("arm-none-linux-gnueabihf")), }), "aarch64_none_elf": tag_class(attrs = { - "version": attr.string(default = _max_version(AARCH64_NONE_ELF.keys())), + "version": attr.string(default = latest_version("aarch64-none-elf")), }), "aarch64_none_linux_gnu": tag_class(attrs = { - "version": attr.string(default = _max_version(AARCH64_NONE_LINUX_GNU.keys())), + "version": attr.string(default = latest_version("aarch64-none-linux-gnu")), }), }, ) diff --git a/version.bzl b/version.bzl new file mode 100644 index 0000000..6c01adc --- /dev/null +++ b/version.bzl @@ -0,0 +1,70 @@ +"""Version rules for toolchains""" + +load( + "@toolchains_arm_gnu//toolchain/archives:aarch64_none_elf.bzl", + "AARCH64_NONE_ELF", +) +load( + "@toolchains_arm_gnu//toolchain/archives:aarch64_none_linux_gnu.bzl", + "AARCH64_NONE_LINUX_GNU", +) +load( + "@toolchains_arm_gnu//toolchain/archives:arm_none_eabi.bzl", + "ARM_NONE_EABI", +) +load( + "@toolchains_arm_gnu//toolchain/archives:arm_none_linux_gnueabihf.bzl", + "ARM_NONE_LINUX_GNUEABIHF", +) + +def _semver(version): + """Parse a semantic version string into a list of integers.""" + parts = [int(i.split("-")[0]) for i in version.split(".")] + return struct( + major = parts[0], + minor = parts[1], + patch = parts[2], + ) + +def _compare_versions(left, right): + """Compare two semantic versions.""" + left = _semver(left) + right = _semver(right) + + # (a < b): -1, (a > b): 1, (a == b): 0. + compare = lambda a, b: int(a > b) - int(a < b) + + return compare(left.major, right.major) or \ + compare(left.minor, right.minor) or \ + compare(left.patch, right.patch) or \ + 0 + +def max_version(versions): + """Obtains the minimum version from the list of version strings.""" + if versions: + maximum = versions.pop(0) + for version in versions: + if _compare_versions(maximum, version) < 0: + maximum = version + return maximum + return None + +def min_version(versions): + """Obtains the minimum version from the list of version strings.""" + if versions: + minimum = versions.pop(0) + for version in versions: + if _compare_versions(minimum, version) > 0: + minimum = version + return minimum + return None + +def latest_version(name): + """Return the latest version of the toolchain.""" + latest = { + "arm-none-eabi": max_version(ARM_NONE_EABI.keys()), + "arm-none-linux-gnueabihf": max_version(ARM_NONE_LINUX_GNUEABIHF.keys()), + "aarch64-none-elf": max_version(AARCH64_NONE_ELF.keys()), + "aarch64-none-linux-gnu": max_version(AARCH64_NONE_LINUX_GNU.keys()), + } + return latest.get(name, None)