diff --git a/dist/Makefile b/dist/Makefile index 958d85a02acae11711b7e344430ea64265cab467..f2d2ac0ae0afaf68fd3d2879155a1b1bd28b475a 100644 --- a/dist/Makefile +++ b/dist/Makefile @@ -32,9 +32,6 @@ NATIVE_ARCH := $(shell uname -m | sed -e 's/amd64/x86_64/;s/arm64/aarch64/;s/*86 ARCH := $(NATIVE_ARCH) # ARCH to be covered by spec file SPEC_ARCH := x86_64 aarch64 riscv64 -# Kernel variant, will be appended to kernel release string as suffix -# to indicate this is a variant kernel (eg. debug; minimal;) -VARIANT := # Which kernel config to use, this build system supports multiple config targets, # Get the available config by scripts/ls-config.sh CONFIG := generic-release @@ -145,7 +142,7 @@ dist-tarball: $(TARFILE) $(CONFIGFILE): $(DISTFILES) @echo "Generating kernel config style '$(CONFIG)'" - @$(DISTDIR)/scripts/gen-configs.sh $(CONFIG) + @$(DISTDIR)/scripts/gen-configs.sh "$(CONFIG)" "$(GITREF)" dist-configs: $(CONFIGFILE) dist-config: dist-configs @@ -167,13 +164,12 @@ $(SPECFILE): always-rebuild --gitref "$(GITREF)" \ --build-arch "$(SRPM_ARCH)" \ --kernel-config "$(CONFIG)" \ - --kernel-variant "$(VARIANT)" \ --set-default-disabled "$(DEFAULT_DISABLED)" \ --set-default-enabled "$(DEFAULT_ENABLED)" \ > $(SPECFILE) @grep -A2 "# == Package options ==" $(SPECFILE) | cut -c3- -dist-specfile: $(SPECFILE) $(TOPDIR)/.config +dist-specfile: $(SPECFILE) dist-configs @echo "$(SPECFILE)" dist-sources: dist-configs $(TARFILE) $(DISTSOURCES) $(DISTKABIS) $(SPECFILE) @@ -208,8 +204,10 @@ dist-rpm: dist-sources dist-prep: dist-sources $(call DO_RPMBUILD,-bp --nodeps $(RPMCROSSFLAGS) $(RPMFLAGS)) -dist-new-release: - @$(DISTDIR)/scripts/make-release.sh +dist-new-release: dist-new-maj-release + +dist-new-maj-release: + @$(DISTDIR)/scripts/make-release.sh --maj-release dist-new-sub-release: @$(DISTDIR)/scripts/make-release.sh --sub-release @@ -223,14 +221,14 @@ dist-clean: BUILDDEPS=$(shell rpmspec -q --buildrequires $(SPECFILE) | cut -d ' ' -f 1) MISSINGDEPS=$(shell echo "$(BUILDDEPS)" | xargs -n1 echo | while read -r _d; do rpm -q --whatprovides "$$_d" >/dev/null || echo "$$_d"; done) -dist-check-buildrequires: $(SPECFILE) +dist-check-buildrequires: dist-specfile @if [ -n "$(MISSINGDEPS)" ]; then \ echo "Error: Build dependency packages missing, please install: $(MISSINGDEPS)"; \ echo "Hint: You can try run \`make dist-install-buildrequires\` to fix this."; \ exit 1; \ fi; -dist-install-buildrequires: $(SPECFILE) +dist-install-buildrequires: dist-specfile @if [ -n "$(MISSINGDEPS)" ]; then \ echo "Installing kernel build dependency '$(MISSINGDEPS)' using yum..."; \ echo "Missing dependency packages: '$(MISSINGDEPS)...'"; \ @@ -348,10 +346,6 @@ dist-help: @echo ' Targer ARCH coverted by spec/SRPM build.' @echo ' TAG="$(TAG)" (or COMMIT="$(COMMIT)")' @echo ' Specify a git tag or commit, and this Makefile will build the kernel from that version.' - @echo ' VARIANT="$(VARIANT)"' - @echo ' Kernel variant, will be appended to kernel release string as suffix' - @echo ' to indicate this is a variant kernel (eg. debug; minimal;), especially' - @echo ' useful when combined with CONFIG=' @echo ' RPMFLAGS="$(RPMFLAGS)"' @echo ' Extra RPM flags to be passed to rpmbuild for RPM bulding related commands.' @echo ' CONFIG="$(CONFIG)"' diff --git a/dist/configs/50variant/debug/default.config b/dist/configs/50variant/debug/default.config index c6fd4340240479c8e94815f59c1b71724e88f957..243704601619341035f0da7710b0a4719126ab50 100644 --- a/dist/configs/50variant/debug/default.config +++ b/dist/configs/50variant/debug/default.config @@ -1,4 +1,5 @@ CONFIG_ACPI_APEI_ERST_DEBUG=m +CONFIG_LOCALVERSION="+debug" CONFIG_ACPI_CONFIGFS=m CONFIG_ACPI_CUSTOM_METHOD=m CONFIG_ACPI_DEBUG=y diff --git a/dist/scripts/gen-configs.sh b/dist/scripts/gen-configs.sh index 385f839019b28c95e11daf408727d85fd2b2d7b0..51a93b999402a55a8b24a12b6a5e059827ce8304 100755 --- a/dist/scripts/gen-configs.sh +++ b/dist/scripts/gen-configs.sh @@ -14,3 +14,6 @@ populate_configs "$@" # Process the config files with make olddefconfig makedef_configs "$@" + +# Check config values (eg. LOCALVERSION) +sanity_check_configs "$@" diff --git a/dist/scripts/gen-spec.sh b/dist/scripts/gen-spec.sh index 54ba9c0f714fa445f817eb2541e7bd09b3257e9a..aa8014698859296545dfee8639da160dcb7f2d34 100755 --- a/dist/scripts/gen-spec.sh +++ b/dist/scripts/gen-spec.sh @@ -16,6 +16,35 @@ gen-spec.sh [OPTION] EOF } +# gen-spec need to parse info from source (currently only parse LOCALVERSION from config), +# so check if the kernel configs are valid here. +prepare_source_info() { + local localversion arch_localversion file + + if [ -z "$KERNEL_CONFIG" ]; then + die "Config target not specified." + fi + + for arch in $BUILD_ARCH; do + file="$SOURCEDIR/$KERNEL_CONFIG.$arch.config" + if ! [ -e "$file" ]; then + die "Config file missing '$file'" + fi + if [ -z "$localversion" ]; then + localversion=$(sed -ne 's/^CONFIG_LOCALVERSION=\(.*\)$/\1/pg' "$file") + else + arch_localversion=$(sed -ne 's/^CONFIG_LOCALVERSION=\(.*\)$/\1/pg' "$file") + if [ "$arch_localversion" != "$localversion" ]; then + die "LOCALVERSION inconsistent between sub-arches for config target '$file', this breaks SRPM package naming." + fi + fi + done + + localversion=${localversion#\"} + localversion=${localversion%\"} + LOCALVERSION=$localversion +} + DEFAULT_DISALBED=" kabichk " while [[ $# -gt 0 ]]; do case $1 in @@ -23,10 +52,6 @@ while [[ $# -gt 0 ]]; do KERNEL_CONFIG=$2 shift 2 ;; - --kernel-variant ) - KERNEL_VARIANT=$2 - shift 2 - ;; --build-arch ) BUILD_ARCH=$2 shift 2 @@ -53,31 +78,12 @@ while [[ $# -gt 0 ]]; do esac done -# This function will prepare $KERNEL_MAJVER, $KERNEL_RELVER -prepare_kernel_ver "${GITREF:-HEAD}" - BUILD_ARCH="${BUILD_ARCH:-$SPEC_ARCH}" -RPM_NAME="kernel${KERNEL_VARIANT:+-$KERNEL_VARIANT}${KDIST:+-$KDIST}" -RPM_VERSION=${KERNEL_MAJVER//-/.} -RPM_RELEASE=${KERNEL_RELVER//-/.} -RPM_RELEASE=${RPM_RELEASE%".$KDIST"} -RPM_VENDOR=$(get_dist_makefile_var VENDOR_CAPITALIZED) -RPM_URL=$(get_dist_makefile_var URL) - -if [ -z "$KERNEL_CONFIG" ]; then - for config in "$TOPDIR/configs/"*.config; do - # "..config" -> "" - KERNEL_CONFIG=$(basename "$config") - KERNEL_CONFIG=${config%.config} - KERNEL_CONFIG=${config%.*} - break - done - - if [ -z "$KERNEL_CONFIG" ]; then - die "There is no valid kernel config." - fi -fi +# This helper prepares LOCALVERSION +prepare_source_info +# This function will prepare $KERNEL_MAJVER, $KERNEL_RELVER +prepare_kernel_ver "${GITREF:-HEAD}" "$LOCALVERSION" _gen_arch_spec() { local arch kernel_arch @@ -98,16 +104,12 @@ EOF _gen_kerver_spec() { cat << EOF -%define rpm_name $RPM_NAME -%define rpm_version $RPM_VERSION -%define rpm_release $RPM_RELEASE -%define rpm_vendor $RPM_VENDOR -%define rpm_url $RPM_URL %define kernel_majver $KERNEL_MAJVER %define kernel_relver $KERNEL_RELVER -EOF -[ "$KERNEL_VARIANT" ] && cat << EOF -%define kernel_variant $KERNEL_VARIANT +%define kernel_unamer $KERNEL_UNAMER +%define rpm_name $KERNEL_NAME +%define rpm_vendor $(get_dist_makefile_var VENDOR_CAPITALIZED) +%define rpm_url $(get_dist_makefile_var URL) EOF } diff --git a/dist/scripts/lib-config.sh b/dist/scripts/lib-config.sh index 8615de9225052cd96ab24b883b03415b37fe37c3..221a30d370323cc63215012a597849d7bcecd9f4 100755 --- a/dist/scripts/lib-config.sh +++ b/dist/scripts/lib-config.sh @@ -15,7 +15,6 @@ CONFIG_SPECS=( "$CONFIG_PATH"/[0-9][0-9]* ) CONFIG_OUTDIR=$SOURCEDIR CONFIG_CACHE=$DISTDIR/workdir/config_cache - _get_config_cross_compiler () { if [[ "$1" == $(get_native_arch) ]]; then : @@ -382,3 +381,72 @@ makedef_configs () { for_each_config_target _makedef_config "$@" } + +sanity_check_configs () { + # We use LOCALVERSION in Kconfig for variant, save a make flag, but require more sanity check to avoid misuse. + # First ensure all arch have the same value + # Then ensure it's in a acceptable format + _sanity_check_configs() { + local target=$1; shift + local populated_config + local localversion arch_localversion auto_localversion + + for arch in "${CONFIG_ARCH[@]}"; do + populated_config="$CONFIG_OUTDIR/$target.$arch.config" + + # config base name is always in this format: ..config + echo "Checking $(basename "$populated_config")..." + + if ! [ -f "$populated_config" ]; then + error "Config not populated: '$populated_config'" + error "sanity_check_configs need to be called after the configs are populated" + exit 1 + fi + + auto_localversion=$(sed -ne 's/^CONFIG_LOCALVERSION_AUTO=\(.*\)$/\1/pg' "$populated_config") + if [ -n "$auto_localversion" ] && [ "$auto_localversion" != "n" ]; then + error "CONFIG_LOCALVERSION_AUTO must be unset, but it's set in config target $target" + error "This will break dist build system's release versioning." + exit 1 + fi + + if [ -z "$localversion" ]; then + localversion=$(sed -ne 's/^CONFIG_LOCALVERSION=\(.*\)$/\1/pg' "$populated_config") + if [ 1 -lt $(echo "$localversion" | wc -l) ]; then + error "More than one LOCALVERSION is set for config target '$target'" + exit 1 + fi + else + arch_localversion=$(sed -ne 's/^CONFIG_LOCALVERSION=\(.*\)$/\1/pg' "$populated_config") + if [ "$arch_localversion" != "$localversion" ]; then + error "Unexpected '$arch_localversion' != '$localversion':" + error "This breaks SRPM package naming, LOCALVERSION inconsistent between sub-arches for config target '$target'" + exit 1 + fi + fi + done + + localversion=${localversion#\"} + localversion=${localversion%\"} + + case $localversion in + +debuginfo|+core|+devel|+headers|+modules|+$KDIST ) + error "Unexpected LOCALVERSION '$localversion':" + error "LOCALVERSION is using a reserved keyword, this will cause package dependency breakage." + exit 1 + ;; + +* ) + ;; + '' ) + # Empty value is default and fine + ;; + *) + error "Unexpected LOCALVERSION '$localversion':" + error "LOCALVERSION is not in acceptable format, for dist building system, it need to start with a '+'" + error "to distinguish it from release string, and dist build system also need to manipulate the string based on above fact." + exit 1 + esac + } + + for_each_config_target _sanity_check_configs "$@" +} diff --git a/dist/scripts/lib-version.sh b/dist/scripts/lib-version.sh index 7b37d43bcb473356b33f3d92974867184aa81673..c13947a97c999284de1da5d38c8a88a8d7597750 100755 --- a/dist/scripts/lib-version.sh +++ b/dist/scripts/lib-version.sh @@ -5,31 +5,68 @@ # shellcheck source=./lib.sh . "$(dirname "$(realpath "$0")")/lib.sh" -## Autogenerated version pattern: -# -. - -# KERNEL_MAJVER's format: .. -# It's the standdard upstream linux kernel release version, -# eg. 3.10.0; 5.4.119; 5.16.0 +## Standardized kernel package version and uname are composed as follows: # -# KERNEL_RELVER's format: [.]. -# If is 0, indicates it's a snapshot, unofficial release. -# If is >=1, indicates it the n'th release of that kernel version. +# A valid tag: [PREFIX-]-[.] +# uname -r: -[.][+] +# RPM NVR: kepnel[-][-]-- +# -- # -# KERNEL_DIST: /tks/tlinux4/... -# Indicates this is a special build kernel. - -# NOTE: This versioning script fully respects the git tag if tag's -# major kernel version matches the version numbers in kernel Makefile - -# This naming style is compatible with Tencent Kernel public naming style. -# Take TK4 for example: +# Some NOTES about why we compose these string in above way: +# - Notice KERNEL_DIST is moved to N part of the RPM NVR, this is how TK3/TK4 release have been doing +# and that is correct because we need to distingush between kernel release streams. And there are +# things will break if we move it out of this part (mostly due to package name change). +# - RPM split the whole package name by '-', then recognize the right most part as R, second right +# most part is V, so KERNEL_MAJVER and KERNEL_RELVER can't contain '-'. +# - LOCALVER is commonly used to present variants of kernel, that is, using same kernel repo commit/version/tag, +# just built with a different config. +# A example is RPM pkg kernel-5.4.119-1 (uname 5.4.119-1) and kernel-debug-5.4.119-1 (uname 5.4.119-1+debug), +# the later one is same kernel built with more debug configs enabled. When kernel-5.4.119-1 run into unkown +# issues, kernel-debug-5.4.119-1 could be installed to do more diagnosis. +# - Notice LOCALVER is moved to "N" part of the RPM NVR, because adding to "V" or "R" part breaks kernel +# package versioning. A suffix, prefix or in-fix of "V" or "R" could cause the package or repo manager +# to make variants override each other, and fails the system unexpectly. For example, an debug kernel +# could be wrongly installed with a normal system wide package update, since the suffix made it had a +# high version number and it shares same Name with vanilla kernel. +# - Some old TK4 tag will have KERNEL_DIST as part of KERNEL_RELVER, we cover that too. +# +## More explanations of each field: +# +### PREFIX: /release/x86/aarch64/oc/.... +# - Could be some well-known string like "release", "x86", ..., could be used to make tags more distinguishable. +# +### KERNEL_MAJVER: .. +# - It's the standdard upstream linux kernel release version, presents in kernel's root Makefile, eg: +# VERSION = 5 +# PATCHLEVEL = 4 +# SUBLEVEL = 203 +# Which stands for kernel 5.4.203 +# +### KERNEL_RELVER: [0..][.] +# - If starts with 0, indicates it's a snapshot, unofficial release. Else it must be a tagged release. +# The string is automatically generated using git commit as versioning base for untagged +# test builds. +# - If EXTRAVERSION is non-empty, it must present here. +# - REL is a custom release string, should be alphanums be splitted by '.'. +# eg. 0011, 0009.12, 0011.prerelease1, ... +# eg. 2207.1.1, 2207.1.2, ... +# +# NOTE: due to historical reason, in KERNEL_RELVER, it could contain '-', but the final generated string that will be used in +# spec file and uname will always be converted to contain '.' only, to comply the RPM NVR naming style, also make things cleaner. # -# Merge base: git describe --tag make install version Generate version: -# 5.4.119 (master) 5.4.119-1-tlinux4-0007 5.4.119-1 5.4.119-1-tlinux4-0007 -# 5.4.119 (master) 5.4.119-1-tlinux4-0007-2-g884a77bf0ba6 5.4.119-1 5.4.119-0.20211115git1135ec008ef3.1-tlinux4-0007 -# 5.4.119 (master) 5.4.119-1-tlinux4-0007.subrelease 5.4.119-1 5.4.119-1-tlinux4-0007.subrelease -# 5.4.119 (master) 5.4.119-1-tlinux4-0007~rc1 5.4.119-1 5.4.119-1-tlinux4-0007~rc1 (*) +### KERNEL_DIST: /tks/tlinux4/stable/stream/... +# Indicates this is a special build kernel, will show up in RPM package name to distinguish different kernel release stream. +# Is configurable through the KDIST variable in dist/Makefile. +# +# NOTE: Due to historical reason, if KDIST is added as first part of KERNEL_RELVER's string, it will be move to tail. +# To make the KERNEL_RELVER part consistent between RPM name, tag and uname. +# +# Example: +# git describe --tag RPM uname -r +# 5.4.119-1-tlinux4-0007 kernel-tlinux4-5.4.119-1.0007 5.4.119-1.0007.tlinux4 +# 5.4.119-1-tlinux4-0007-2-g884a77bf0ba6 kernel-tlinux4-5.4.119-0.20211115git1135ec008ef3.1.0007 5.4.119-0.20211115git1135ec008ef3.1.0007.tlinux4 +# 5.4.119-1-tlinux4-0007.subrelease kernel-tlinux4-5.4.119-1.0007.subrelease 5.4.119-1.0007.subrelease.tlinux4 +# 5.4.119-1-tlinux4-0007~rc1 kernel-tlinux4-5.4.119-1.0007~rc1 5.4.119-1.0007~rc1.tlinux4 (*) # # NOTE: Sometime TK4's release version may go backwards, it's a known issue we have to live with. # TK4 used tag like 5.4.119-1-tlinux4-0007.prerelease to indicate a release candidate. @@ -40,7 +77,7 @@ # try use tilde symbol to indicate it's a RC. ## Macros and values: -# Standard four-part linux kernel version from kernel's Makefile +# Alias of four-part linux kernel version from kernel's Makefile KVERSION= KPATCHLEVEL= KSUBLEVEL= @@ -57,70 +94,116 @@ KEXTRAVERSION= # To avoid conflict with 5.15 stable build like 5.15.Y-Z, we can't bump the Y part or Z part. # So instead bump to 5.16 and mark it rc0 as 5.16.0-0.rc0. (Just as what Fedora does). KPREMERGEWINDOW= - -# KRCRELEASE: If we are building a rc-release -# KSNAPRELEASE: If we are building a snapshot-release -# Pre-release means we are building from an RC release -# Snap-release means we are building from an git commit without tag -export KRCRELEASE= -export KSNAPRELEASE= -export KTAGRELEASE= +# Set to true if this is a rolling build tracks upstream +KROLLING= +# Set to 1 to allow git tag force override uname +KFORCEUNAMER= # git snapshot versioning KGIT_SNAPSHOT= -# Set if current commit is tagged with valid release info, force use it. -KGIT_FORCE_RELEAE= +# Raw info from current git tag +KGIT_TAG_RELEASE_INFO_RAW= +# Set if current commit is tagged with valid release info +KGIT_TAG_RELEASE_INFO= +# Set if a previous commit is found tagged with valid release info +KGIT_LATEST_TAG_RELEASE_INFO= # Set if current commit is tagged with a valid test tag name KGIT_TESTBUILD_TAG= # Release: Start from 1.0, indicate the release version, info embedded in git tag -KGIT_RELEASE= KGIT_RELEASE_NUM= KGIT_SUB_RELEASE_NUM= ### The formal kernel version and release - # Simulate `uname -r` output, which is always "$KVERSION.$KPATCHLEVEL.$KSUBLEVEL$KEXTRAVERSION" export KERNEL_UNAMER= # Basically: $KVERSION.$KPATCHLEVEL.$KSUBLEVEL (eg. 5.17.0, 5.16.3) export KERNEL_MAJVER= -# Release version, may contain $KEXTRAVERSION (eg. 1, 0.rc0, 0.20220329gita11bf64a6e8f) +# Release version (eg. 1, 0.rc0, 0.20220329gita11bf64a6e8f), see comments at the beginning of this file export KERNEL_RELVER= -# Kernel distro variable (eg. tks, tlinux4, ), with any leading "." or "-" removed +# Kernel distro variable (eg. tks, tlinux4, ), with any leading "." or "-" removed, see comments at the beginning of this file export KERNEL_DIST= -# Only used for make-release +# Only used for make-release sub command, get latest release tag of current commit export KERNEL_PREV_RELREASE_TAG= +# Set if it's a tagged release +export KTAGRELEASE= +# KTESTRELEASE: If we are building based on a test tag +KTESTRELEASE= +# KSNAPRELEASE: If we are building a snapshot-release +KSNAPRELEASE= +# KRCRELEASE: If we are building a rc-release +KRCRELEASE= + +_is_num() { + [ "$1" -eq "$1" ] &>/dev/null +} + # Get the tag of a git ref, if the git ref itself is a valid tag, just return itself # else, search latest tag before this git ref. -_get_last_git_tag_of() { +_get_git_tag_of() { local gitref=$1; shift - local last_tag tag - local tagged + local tag tags - for tag in $(git "$@" tag --points-at "$gitref"); do - tagged=1 - last_tag="$tag" + tags=$(git "$@" tag --points-at "$gitref") + # If multiple tags presents, used the one specified by user + for tag in $tags; do if [[ "$tag" == "$gitref" ]]; then - break + echo "$tag" + return fi - # If HEAD is tagged with multiple tags and user is not asking to use one of them, - # use the first one found matching release info. - if [[ "$gitref" == HEAD ]] && _get_rel_info_from_tag "$tag" > /dev/null; then - break + done + + # If HEAD is tagged with multiple tags and user is not asking to use one of them, + # use the first one found matching release info. + for tag in $tags; do + if _get_rel_info_from_tag "$tag" > /dev/null; then + echo "$tag" + return fi done - if [[ -z "$last_tag" ]]; then - tagged=0 - last_tag=$(git "$@" describe --tags --abbrev=0 "$gitref" 2>/dev/null) + # Else just return the first tag + for tag in $tags; do + echo "$tag" + return + done +} + +# git-describe, but customized for kernel, and prefer specified tag +_get_git_describe_of() { + local gitref=$1; shift + local gitdesc + + gitdesc=$(_get_git_tag_of "$gitref" "$@") + + if [[ -n "$gitdesc" ]]; then + echo "$gitdesc" + else + git "$@" describe --tags --abbrev=12 "$gitref" fi +} + +# Get the tag of a git ref, if the git ref itself is a valid tag, just return itself +# else, search latest tag before this git ref. +# Return 1 if git ref is tagged, +_get_last_git_tag_of() { + local gitref=$1; shift + local gittag - echo "$last_tag" - return $tagged + gittag=$(_get_git_tag_of "$gitref" "$@") + + if [[ -z "$gittag" ]]; then + git "$@" describe --tags --abbrev=0 "$gitref" + return 0 + else + echo "$gittag" + return 1 + fi } # $1: git tag or git commit, defaults to HEAD # $2: kernel source tree, should be a git repo +# Parse fondunmental kernel versioning info from Makefiles. get_kernel_code_version() { local gitref=${1:-HEAD} local repo=${2:-$TOPDIR} @@ -137,13 +220,15 @@ get_kernel_code_version() { KPATCHLEVEL=$(sed -nE '/^PATCHLEVEL\s*:?=\s*/{s///;p;q}' <<< "$makefile") KSUBLEVEL=$(sed -nE '/^SUBLEVEL\s*:?=\s*/{s///;p;q}' <<< "$makefile") KEXTRAVERSION=$(sed -nE '/^EXTRAVERSION\s*:?=\s*/{s///;p;q}' <<< "$makefile") + # Replace '-' in KEXTRAVERSION + KEXTRAVERSION=${KEXTRAVERSION//-/.} + KEXTRAVERSION=${KEXTRAVERSION#.} if [[ -z "$KVERSION" ]] || [[ -z "$KPATCHLEVEL" ]] || [[ -z "$KSUBLEVEL" ]]; then die "Invalid VERSION, PATCHLEVEL or SUBLEVEL in Makefile" return 1 fi - # RC releases are always considered pre-release if [[ "$KEXTRAVERSION" == "rc"* ]] || [[ $KEXTRAVERSION == "-rc"* ]]; then KRCRELEASE=1 fi @@ -187,65 +272,108 @@ _first_merge_window_detection() { return 1 } -# Get release info from git tag -_get_rel_info_from_tag() { - local tag=$1 rel ret=0 - local kextraversion=${KEXTRAVERSION#-} - - if [[ $tag == *"$KVERSION.$KPATCHLEVEL.$KSUBLEVEL"* ]]; then - rel=${tag#*"$KVERSION.$KPATCHLEVEL.$KSUBLEVEL"} - elif [[ "$KSUBLEVEL" = "0" ]] && [[ $tag == *"$KVERSION.$KPATCHLEVEL"* ]]; then - rel=${tag#*"$KVERSION.$KPATCHLEVEL"} - elif [[ $KPREMERGEWINDOW ]] && [[ $tag == *"$KVERSION.$((KPATCHLEVEL + 1)).$KSUBLEVEL"* ]]; then - rel=${tag#*"$KVERSION.$((KPATCHLEVEL + 1)).$KSUBLEVEL"} +_do_strip_kernel_majver() { + local rel + + if [[ $1 == *"$KVERSION.$KPATCHLEVEL.$KSUBLEVEL"* ]]; then + rel=${1#*"$KVERSION.$KPATCHLEVEL.$KSUBLEVEL"} + elif [[ "$KSUBLEVEL" = "0" ]] && [[ $1 == *"$KVERSION.$KPATCHLEVEL"* ]]; then + rel=${1#*"$KVERSION.$KPATCHLEVEL"} + elif [[ $KPREMERGEWINDOW ]] && [[ $1 == *"$KVERSION.$((KPATCHLEVEL + 1)).$KSUBLEVEL"* ]]; then + rel=${1#*"$KVERSION.$((KPATCHLEVEL + 1)).$KSUBLEVEL"} else return 1 fi + echo "$rel" +} + +# Check and strip the leading VERSION.PATCHLEVEL.SUBLEVEL of a tag, +# (eg. 5.18.19) and potential prefixes. If the tag doesn't match its corresponding, +# kernel version, return 1. +_check_strip_kernel_majver() { + local tag=$1 rel + local makefile + local _kversion _kpatchlevel _ksublevel + + if rel=$(_do_strip_kernel_majver "$tag"); then + echo "$rel" + return 0 + fi + + # Update VERSION/PATCHLEVEL/SUBLEVEL using target Makefile, because y upstream + # changes them very frequently and may out of sync with previous tag. + if makefile=$(git show "$tag:Makefile" 2>/dev/null); then + _kversion=$(sed -nE '/^VERSION\s*:?=\s*/{s///;p;q}' <<< "$makefile") + _kpatchlevel=$(sed -nE '/^PATCHLEVEL\s*:?=\s*/{s///;p;q}' <<< "$makefile") + _ksublevel=$(sed -nE '/^SUBLEVEL\s*:?=\s*/{s///;p;q}' <<< "$makefile") + fi + + if rel=$(KVERSION=$_kversion KPATCHLEVEL=$_kpatchlevel KSUBLEVEL=$_ksublevel _do_strip_kernel_majver "$tag"); then + echo "$rel" + return 0 + fi + + return 1 +} + +# Get release info from git tag +_get_rel_info_from_tag() { + local tag=$1 rel + + if ! rel=$(_check_strip_kernel_majver "$@"); then + return 1 + fi rel=${rel//-/.} rel=${rel#.} - if [[ -z "$kextraversion" ]]; then + # If KERNEL_DIST is added as prefix/semi-prefix/suffix, remove it from rel + if [[ $KERNEL_DIST ]]; then + case $rel in + $KERNEL_DIST.*) + rel=${rel#$KERNEL_DIST.} + ;; + $KEXTRAVERSION.$KERNEL_DIST.*) + rel=${rel#$KEXTRAVERSION.$KERNEL_DIST.} + rel=$KEXTRAVERSION.$rel + ;; + *.$KERNEL_DIST) + rel=${rel%.$KERNEL_DIST} + ;; + esac + fi + + # If KEXTRAVERSION is added, remove it + if [[ -z "$KEXTRAVERSION" ]]; then # If previous KEXTRAVERSION is not empty but now empty, # still consider it a valid release tag since release candidate mark may get dropped. # But this really should look at the Makefile corresponding to that tag commit : - elif [ "$kextraversion" -eq "$kextraversion" ] &>/dev/null; then + elif _is_num "$KEXTRAVERSION"; then case $rel in - # Extra version is release number, ok - $kextraversion | "$kextraversion."* ) ;; + # Extra version is release number, remove it and add later + $KEXTRAVERSION | "$KEXTRAVERSION."* ) + rel=${rel#$KEXTRAVERSION} + rel=${rel#.} + ;; * ) return 1; ;; esac else # Remove RC liked tag, append them as suffix later. case $rel in # Plain version tag, eg. 5.17-rc3 - $kextraversion ) + $KEXTRAVERSION ) rel="" ;; # Plain version tag plus suffix, eg. 5.17-rc3.* - "$kextraversion."* ) - rel=${rel#$kextraversion.} - ;; - # Extra tag, eg 5.17-1.rc3* - *".$kextraversion"* | *"-$kextraversion"* ) ;; - * ) return 1; ;; - esac - fi - - # If KERNEL_DIST is added as prefix/semi-prefix/suffix, remove it from rel - if [[ $KERNEL_DIST ]]; then - case $rel in - $KERNEL_DIST.*) - rel=${rel#$KERNEL_DIST.} + "$KEXTRAVERSION."* ) + rel=${rel#$KEXTRAVERSION.} ;; - $kextraversion.$KERNEL_DIST.*) - rel=${rel#$kextraversion.$KERNEL_DIST.} - rel=$kextraversion.$rel - ;; - *.$KERNEL_DIST) - rel=${rel%.$KERNEL_DIST} + # Already appended as , eg 5.17-1.rc3* + *".$KEXTRAVERSION" ) + rel=${rel%.$KEXTRAVERSION} ;; + * ) return 1; ;; esac fi @@ -261,7 +389,7 @@ _search_for_release_tag() { while :; do limit=$((limit - 1)) - if [[ $limit -le 0 ]] || ! tag=$(git -C "$repo" describe --tags --abbrev=0 "$tag^" 2>/dev/null); then + if [[ $limit -le 0 ]] || ! tag=$(git -C "$repo" describe --tags --abbrev=0 "$tag" 2>/dev/null); then warn "No valid tag found that are eligible for versioning, please fix your repo and tag it properly." return 1 fi @@ -275,14 +403,14 @@ _search_for_release_tag() { # Get release info from git tag # -# We try to store the RPM NVR (Name, Version, Release) info's VR part in git tag +# We try to parse and verify RPM NVR (Name, Version, Release) info's 'VR' part using git tag or commit info # N: is always kernel # V: is kernel's major release version (eg. 5.18, 5.18.0, 5.17.2) # R: is a tokens seperated with '.' (eg 1[.KDIST], 2[.KDIST], 2.1[.KDIST], 0.rc1[.KDIST]) # could also be 0.YYYYMMDDgit for snapshot release. # But ideally all git tag are for formal release so snapshot tag shouldn't appear in repo. # -# A tag that contains VR is considered a release tag. +# With a tag that contains valid VR info it's considered a tag release, else it's a snapshot release. # # $1: git tag or git commit, defaults to HEAD # $2: kernel source tree, should be a git repo @@ -307,7 +435,7 @@ get_kernel_git_version() KGIT_SNAPSHOT=$(date +"%Y%m%d")git$KGIT_SNAPSHOT # Check if first merge-window, and set KPREMERGEWINDOW, see comment above about KPREMERGEWINDOW - if _first_merge_window_detection "$@"; then + if [[ $KROLLING ]] && _first_merge_window_detection "$@"; then KPREMERGEWINDOW=1 fi @@ -320,54 +448,68 @@ get_kernel_git_version() # Latest tag is a release tag, just use it release_tag=$last_tag else - warn "Latest git tag '$last_tag' is not a release tag, it does't match Makefile version '$KVERSION.$KPATCHLEVEL.$KSUBLEVEL$KEXTRAVERSION'" + warn "Latest git tag '$last_tag' is not a release tag, it does't match Makefile version '$KVERSION.$KPATCHLEVEL.$KSUBLEVEL-$KEXTRAVERSION'" if release_tag=$(_search_for_release_tag "$last_tag" "$repo"); then warn "Found release tag '$release_tag'." fi fi if [[ "$release_tag" ]]; then - git_desc=$(git -C "$repo" describe --tags --abbrev=12 "$gitref" 2>/dev/null) + git_desc=$(_get_git_describe_of "$gitref" -C "$repo") release_info=$(_get_rel_info_from_tag "$release_tag") + release_info_raw=$(_check_strip_kernel_majver "$release_tag") if ! [[ $release_info ]]; then warn "No extra release info in release tag, might be a upstream tag." \ "Please make a release commit with 'make dist-release' for a formal release." + release_info=0 KGIT_RELEASE_NUM=0 KGIT_SUB_RELEASE_NUM=0 elif [[ $release_info == 0.* ]]; then KGIT_RELEASE_NUM=${release_info##*.} - KGIT_RELEASE_NUM=${KGIT_RELEASE_NUM##*-} - KGIT_SUB_RELEASE_NUM=${release_info%."$KGIT_RELEASE_NUM"} + KGIT_SUB_RELEASE_NUM=${release_info%$KGIT_RELEASE_NUM} + KGIT_SUB_RELEASE_NUM=${KGIT_SUB_RELEASE_NUM%.} KGIT_SUB_RELEASE_NUM=${KGIT_SUB_RELEASE_NUM##*.} else KGIT_RELEASE_NUM=${release_info%%.*} - KGIT_RELEASE_NUM=${KGIT_RELEASE_NUM%%-*} - KGIT_SUB_RELEASE_NUM=${release_info#"$KGIT_RELEASE_NUM".} + KGIT_SUB_RELEASE_NUM=${release_info#$KGIT_RELEASE_NUM} + KGIT_SUB_RELEASE_NUM=${KGIT_SUB_RELEASE_NUM#.} KGIT_SUB_RELEASE_NUM=${KGIT_SUB_RELEASE_NUM%%.*} fi - # Fix release numbers, if it's not a number - if ! [ "$KGIT_RELEASE_NUM" -eq "$KGIT_RELEASE_NUM" ] &>/dev/null; then - warn "Unrecognizable release number: $KGIT_RELEASE_NUM, resetting to 0" - KGIT_RELEASE_NUM=0 - fi - if ! [ "$KGIT_SUB_RELEASE_NUM" -eq "$KGIT_SUB_RELEASE_NUM" ] &>/dev/null; then - KGIT_SUB_RELEASE_NUM=0 - fi + KERNEL_PREV_RELREASE_TAG=$release_tag + KGIT_LATEST_TAG_RELEASE_INFO=$release_info if [[ "$tagged" -eq 1 ]] && [[ "$release_tag" == "$last_tag" ]]; then - if [[ $release_info ]] && [[ "$KGIT_RELEASE_NUM" -ne 0 ]]; then + if [[ $release_info ]]; then # This commit is tagged and it's a valid release tag, juse use it - KGIT_FORCE_RELEAE=$release_info - KTAGRELEASE=$release_tag + if [[ "$KGIT_RELEASE_NUM" != '0' ]]; then + KGIT_TAG_RELEASE_INFO=$release_info + KGIT_TAG_RELEASE_INFO_RAW=$release_info_raw + KTAGRELEASE=$release_tag + else + warn "'$release_tag' is not a formal release tag, using snapshot versioning." + KGIT_SNAPSHOT=1 + fi + else + # Tagged but no release info from current tag, could be upstream style tag + KGIT_TAG_RELEASE_INFO=1 + # It's not a valid tag + KTAGRELEASE= fi + + # If current tag is release tag, previous release tag should be another one + KERNEL_PREV_RELREASE_TAG=$(_search_for_release_tag ${release_tag}^ "$repo") + elif [[ "$last_tag" == "$git_desc" ]]; then + # It's tagged, but the tag is not a release tag # A dumb assumption here, if it's not in *.* format (v5.4, 4.12.0, etc...) it's a test tag if [[ $last_tag != v*.* ]] && [[ $last_tag != *.*.* ]]; then warn "'$last_tag' looks like a test tag, using it as versioning suffix." warn "Please tag properly for release build, now versioning it as a test build." - KGIT_TESTBUILD_TAG=testbuild.$last_tag + KGIT_TESTBUILD_TAG=test.$last_tag + KGIT_TESTBUILD_TAG=${KGIT_TESTBUILD_TAG//-/_} + KTESTRELEASE=1 else warn "'$last_tag' looks like a kernel release tag but out-of-sync with Makefile" \ "ignoring it and versioning as snapshot." @@ -378,13 +520,21 @@ get_kernel_git_version() # Just a simple untagged commit, nothing special KSNAPRELEASE=1 fi - - KERNEL_PREV_RELREASE_TAG=$release_tag else + # No tag or no repo info available, use snapshot version KSNAPRELEASE=1 KGIT_RELEASE_NUM=0 + KGIT_SUB_RELEASE_NUM=0 fi + # Fix release numbers, if it's not a number + if ! _is_num "$KGIT_RELEASE_NUM"; then + warn "Unrecognizable release number: $KGIT_RELEASE_NUM, resetting to 0" + KGIT_RELEASE_NUM=0 + fi + if ! _is_num "$KGIT_SUB_RELEASE_NUM"; then + KGIT_SUB_RELEASE_NUM=0 + fi } _prepare_kernel_ver() { @@ -398,9 +548,10 @@ _prepare_kernel_ver() { # Disable PRE-merge window detection for tagged commit, # We want to following user provided tag strictly - if [[ ! $KGIT_FORCE_RELEAE ]]; then - if [[ $KPREMERGEWINDOW ]]; then + if [[ $KPREMERGEWINDOW ]]; then + if [[ ! $KTAGRELEASE ]]; then KPATCHLEVEL=$(( KPATCHLEVEL + 1 )) + KEXTRAVERSION="rc0" fi fi } @@ -431,36 +582,69 @@ _prepare_kernel_ver() { # As you may have noticed, release always start with '0' unless a git tag have release >= 1, # The tag should be generated by other commands that comes later in this script. prepare_kernel_ver() { - _prepare_kernel_ver "$@" - - # If it's a tagged commit, and the release number in tag is non-zero, use that - if [[ $KGIT_FORCE_RELEAE ]]; then - KERNEL_MAJVER="$KVERSION.$KPATCHLEVEL.$KSUBLEVEL" - KERNEL_RELVER="$KGIT_FORCE_RELEAE" + local gitref=$1 localversion=$2 + local krelease + + case $localversion in + +* | '' ) localversion=${localversion#+} ;; + *) die "Unexpected LOCALVERSION '$localversion', run dist-check-configs for more info." + esac + + _prepare_kernel_ver "$gitref" + if [[ $KSNAPRELEASE ]]; then + # For snpashot version, it should start with 0. and + # KEXTRAVERSION will be appended at the tail of git info. + krelease=0.$KGIT_SNAPSHOT + [[ ${KEXTRAVERSION:-0} != "0" ]] && krelease=$krelease.$KEXTRAVERSION + # Release numbers will be appended too if available as a version hint for users. + [[ ${KGIT_RELEASE_NUM:-0} != "0" ]] && krelease=$krelease.$KGIT_RELEASE_NUM + [[ ${KGIT_SUB_RELEASE_NUM:-0} != "0" ]] && krelease=$krelease.$KGIT_SUB_RELEASE_NUM + elif [[ $KTESTRELEASE ]]; then + # For test tag, use the most recent release tag we can find and + # append the test suffix. + krelease=0 + [[ ${KEXTRAVERSION:-0} != "0" ]] && krelease=$krelease.$KEXTRAVERSION + [[ $KGIT_LATEST_TAG_RELEASE_INFO ]] && krelease=$krelease.$KGIT_LATEST_TAG_RELEASE_INFO.$KGIT_TESTBUILD_TAG else - local krelease=0 - if [[ $KSNAPRELEASE ]]; then - krelease=$krelease.$KGIT_SNAPSHOT - elif [[ $KGIT_RELEASE ]]; then - krelease=$krelease.$KGIT_RELEASE + if [[ $KTAGRELEASE ]]; then + # If the git tag matches all release info, respect it. + krelease=$KGIT_TAG_RELEASE_INFO + else + # Upstream or unknown, set release to start with "0." + # so it can be updated easily later. + # And if it's a rc release, use "0.0" to ensure it have + # lower priority. + if [[ "$KRCRELEASE" ]]; then + krelease=0.0 + else + krelease=0.1 + fi fi + # If KEXTRAVERSION is not number it will break the release syntax + # if added as prefix, add as suffix in such case if [[ $KEXTRAVERSION ]]; then - krelease="$krelease.${KEXTRAVERSION##-}" - elif [[ $KPREMERGEWINDOW ]]; then - krelease="$krelease.rc0" + if _is_num "${KEXTRAVERSION%%.*}"; then + krelease="$KEXTRAVERSION.$krelease" + else + krelease="$krelease.$KEXTRAVERSION" + fi fi + fi - if [[ $KGIT_TESTBUILD_TAG ]]; then - # '-' is not allowed in release name, but commonly used in tag - krelease="$krelease.${KGIT_TESTBUILD_TAG//-/_}" - fi + KERNEL_NAME="kernel${KDIST:+-$KDIST}" + KERNEL_MAJVER="$KVERSION.$KPATCHLEVEL.$KSUBLEVEL" + KERNEL_RELVER="$krelease" + KERNEL_UNAMER="$KERNEL_MAJVER-$KERNEL_RELVER${KDIST:+.$KDIST}" - KERNEL_MAJVER="$KVERSION.$KPATCHLEVEL.$KSUBLEVEL" - KERNEL_RELVER="$krelease${KDIST:+.$KDIST}" + if [[ $KFORCEUNAMER ]] && [[ $KGIT_TAG_RELEASE_INFO_RAW ]]; then + KERNEL_UNAMER="$KERNEL_MAJVER$KGIT_TAG_RELEASE_INFO_RAW" fi - KERNEL_UNAMER="$KERNEL_MAJVER-$KERNEL_RELVER" + if [[ $localversion ]]; then + KERNEL_NAME="$KERNEL_NAME-$localversion" + KERNEL_UNAMER="$KERNEL_UNAMER+$localversion" + fi } ### Generate formal release version based on kernel tag and commit info @@ -496,12 +680,16 @@ prepare_next_kernel_ver() { warn "Upstream is in merge window, forcing a formal release is not recommanded." fi + # TK4 left-pads the release number with 0 + KGIT_RELEASE_NUM=$(echo "$KGIT_RELEASE_NUM" | sed 's/^0*//') krelease=$((KGIT_RELEASE_NUM + 1)) if [[ $KEXTRAVERSION ]]; then - krelease="$krelease.${KEXTRAVERSION##-}" - elif [[ $KPREMERGEWINDOW ]]; then - krelease="$krelease.rc0" + if _is_num "${KEXTRAVERSION%%.*}"; then + krelease="$KEXTRAVERSION.$krelease" + else + krelease="$krelease.$KEXTRAVERSION" + fi fi KERNEL_MAJVER="$KVERSION.$KPATCHLEVEL.$KSUBLEVEL" @@ -519,13 +707,16 @@ prepare_next_sub_kernel_ver() { warn "Upstream is in merge window, forcing a formal release is not recommanded." fi - krelease=$((KGIT_RELEASE_NUM + 0)) + KGIT_RELEASE_NUM=$(echo "$KGIT_RELEASE_NUM" | sed 's/^0*//') + krelease=$KGIT_RELEASE_NUM krelease=$krelease.$((KGIT_SUB_RELEASE_NUM + 1)) if [[ $KEXTRAVERSION ]]; then - krelease="$krelease.${KEXTRAVERSION##-}" - elif [[ $KPREMERGEWINDOW ]]; then - krelease="$krelease.rc0" + if _is_num "${KEXTRAVERSION%%.*}"; then + krelease="$KEXTRAVERSION.$krelease" + else + krelease="$krelease.$KEXTRAVERSION" + fi fi KERNEL_MAJVER="$KVERSION.$KPATCHLEVEL.$KSUBLEVEL" diff --git a/dist/scripts/lib.sh b/dist/scripts/lib.sh index f9af8f494c5e5cf6e8f91ad2d3425c45fd137029..f2afc007d173b604569643f75d6832f037cc611d 100755 --- a/dist/scripts/lib.sh +++ b/dist/scripts/lib.sh @@ -96,7 +96,7 @@ get_dist_makefile_var() { local _repo=${3:-$TOPDIR} local _val - _val=$(cat_repo_file "dist/Makefile" | sed -nE -e "$_sedexp") + _val=$(cat_repo_file "dist/Makefile" "$_gitref" "$_repo" | sed -nE -e "$_sedexp") case $_val in *\$* ) die "Can't parse Makefile variable '$1', it references to other variables." diff --git a/dist/scripts/make-release.sh b/dist/scripts/make-release.sh index 47b27c718ded68842ae6567ec15c7d0bcecea7f3..0a3be15c4d5fe7e1637c6a251559717c3b3445a8 100755 --- a/dist/scripts/make-release.sh +++ b/dist/scripts/make-release.sh @@ -10,32 +10,58 @@ case $1 in --sub-release ) prepare_next_sub_kernel_ver "$COMMIT" "$TOPDIR" || die "Failed preparing next sub release version info" ;; - "") + --maj-release) prepare_next_kernel_ver "$COMMIT" "$TOPDIR" || die "Failed preparing next release version info" ;; *) - die "Invalid param $1" + die "Invalid param $1, usage $0 {--maj-release|--sub-release}" ;; esac AUTHOR_NAME=$(git config user.name) || die "Failed getting author name info from git config" AUTHOR_MAIL=$(git config user.email) || die "Failed getting author email info from git config" GITLOG=$(git -C "$TOPDIR" log "$KERNEL_PREV_RELREASE_TAG..$COMMIT" --pretty=oneline) || die "Failed getting changelog from git log" +if [[ "$KTAGRELEASE" ]]; then + warn "You are generating changelog from a tagged release commit, however changelog update" + warn "should be done before tagging a release, please be careful with what you are doing or fix your workflow." + prepare_kernel_ver "$COMMIT" +fi + +if [[ -z "$GITLOG" ]]; then + error "No change found since last tag, using dummy changelog." + GITLOG="- Accumulated bug fix and improvements." +fi + AUTHOR="$AUTHOR_NAME <$AUTHOR_MAIL>" RELEASE_VERSION="$KERNEL_MAJVER-$KERNEL_RELVER" -TAG_VERSION="release-$KERNEL_UNAMER" -CHANGELOG="* $(date +"%a %b %e %Y") $AUTHOR - $RELEASE_VERSION -$(echo "$GITLOG" | sed -E "s/^\S+/-/g")" +TAG_VERSION="$KERNEL_UNAMER" +CHANGELOG_HDR="* $(date +"%a %b %e %Y") $AUTHOR - $RELEASE_VERSION" +CHANGELOG="$(echo "$GITLOG" | sed -E "s/^\S+/-/g")" + +print_preview() { + cat << EOF +Please review following info: +Tag: ${TAG_VERSION:-} +Release Version: $RELEASE_VERSION +Release Author: $AUTHOR +Changelog: +$CHANGELOG_HDR +$CHANGELOG +EOF +} print_info() { cat << EOF Please review following info: -\* DO NOT CHANGE THE FILE FORMAT \* +!!! DO NOT CHANGE THE FILE FORMAT !!! +// You can set "Tag:" to empty to skip tagging. +// but it's strongly recommended to tag after changlog update, to make versioning more consistent. Tag: $TAG_VERSION Release Version: $RELEASE_VERSION Release Author: $AUTHOR Changelog: +* $(date +"%a %b %e %Y") - " $CHANGELOG EOF } @@ -53,16 +79,17 @@ parse_info() { TAG_VERSION=$(sed -E -ne "s/^Tag:\s*(.*)/\1/p" "$DISTDIR/.release.stash") RELEASE_VERSION=$(sed -E -ne "s/\s*Release Version:\s*(.*)/\1/p" "$DISTDIR/.release.stash") AUTHOR=$(sed -E -ne "s/^Release Author:\s*(.*)/\1/p" "$DISTDIR/.release.stash") - CHANGELOG=$(sed -n '/^* /,$p' "$DISTDIR/.release.stash") + CHANGELOG=$(sed -n '/^* /,$p' "$DISTDIR/.release.stash" | tail -n +2) + CHANGELOG_HDR="* $(date +"%a %b %e %Y") $AUTHOR - $RELEASE_VERSION" } while :; do _res="?" while :; do { - print_info + print_preview echo - echo "(Press 'q' to exit preview.)" + echo "(Press 'q' to exit preview, Press 'e' to edit above info, Press 'y' to commit.)" } | less echo "Is this OK? (y/n/q/e, Y: Do the release, N/Q: quit, E: edit)" read -r -n1 _res @@ -71,6 +98,8 @@ while :; do exit 0 ;; y|Y ) + info "Updating spec changelog and tagging HEAD... " + echo "$CHANGELOG_HDR" >> "$DISTDIR/templates/changelog.new" echo "$CHANGELOG" >> "$DISTDIR/templates/changelog.new" echo "" >> "$DISTDIR/templates/changelog.new" cat "$DISTDIR/templates/changelog" >> "$DISTDIR/templates/changelog.new" @@ -81,7 +110,15 @@ while :; do Upstream: no Signed-off-by: $AUTHOR" - git -C "$TOPDIR" tag "$TAG_VERSION" + if [[ $TAG_VERSION ]]; then + if ! git -C "$TOPDIR" tag "$TAG_VERSION"; then + error "Failed to tag '$TAG_VERSION', this tag may already exists." + error "Changelog update should be done before tagging a release, so you may either use dist-new-release to tag, or fix the tag later manually." + fi + else + warn "Please ensure a tag corresponding to '$RELEASE_VERSION' is added to repo to make changelog consistent." + fi + exit 0 ;; e|E ) diff --git a/dist/sources/filter-modules.sh b/dist/sources/filter-modules.sh index ea98a88c8015008103914db61f9a961f55c252a5..1326883cc04439036eefd0e656bb6b23596192c0 100755 --- a/dist/sources/filter-modules.sh +++ b/dist/sources/filter-modules.sh @@ -43,7 +43,7 @@ fsdrvs="affs befs cifs coda cramfs dlm ecryptfs hfs hfsplus jfs jffs2 minix ncpf singlemods="ntb_netdev iscsi_ibft iscsi_boot_sysfs megaraid pmcraid qedi qla1280 9pnet_rdma rpcrdma nvmet-rdma nvme-rdma hid-picolcd hid-prodikeys hwa-hc hwpoison-inject hid-sensor-hub target_core_user sbp_target cxgbit iw_cxgb3 iw_cxgb4 cxgb3i cxgb3i cxgb3i_ddp cxgb4i chcr chtls parport_serial ism regmap-sdw regmap-sdw-mbq arizona-micsupp hid-asus iTCO_wdt rnbd-client rnbd-server mlx5_ib mlx5_vdpa spi-altera-dfl nct6775 hid-playstation hid-nintendo ntc_thermistor configs" # Overrides is individual modules which need to remain in kernel-core due to deps. -overrides="cec" +overrides="cec wmi" BASE_DIR=$1 KERNEL_UNAMER=$2 @@ -95,8 +95,8 @@ filter_override() { local filter_list for mod in $1; do - if filter_list=$(grep "$mod.ko" <<< "$modules_list"); then - modules_list=$(grep -v "$mod.ko" <<< "$modules_list") + if filter_list=$(grep "/$mod.ko" <<< "$modules_list"); then + modules_list=$(grep -v "/$mod.ko" <<< "$modules_list") core_modules_list+=$filter_list core_modules_list+=$'\n' fi diff --git a/dist/templates/kernel.template.spec b/dist/templates/kernel.template.spec index 9bf560f03a3ed57aa1b3735703e2faad13e3a261..fbe34230fe844132549b8c91f5900896efe10f24 100644 --- a/dist/templates/kernel.template.spec +++ b/dist/templates/kernel.template.spec @@ -2,18 +2,20 @@ # # By changing a few rpm macros, it's very convenient to build for different archs or # kernel config styles, and build different components. - +### Kenrel version relation macros # Following variables filled by automation scripts: -# %%{kernel_majver}: example. 5.15.0, 5.15.3, 5.16.0 -# %%{kernel_relver}: example. 2207.1, 0.20211115git1135ec008ef3.rc0.2207, rc1 -# %%{kernel_variant}: example. %%{nil}; debug -# %%{rpm_name}: RPM package name -# %%{rpm_version}: RPM package version -# %%{rpm_release}: RPM package release +# %%{kernel_unamer}: `uname -r` output, needed by scriptlets so prepare it early, eg. 5.18.19-2207.2.1.tks, 5.18.19-2207.2.1.tks+debug, 5.4.119-1-0009.1 +# %%{kernel_majver}: Kernel RPM package version, eg. 5.15.0, 5.15.3, 5.16.0 +# %%{kernel_relver}: Kernel RPM package release, eg. 2207.1, 0.20211115git1135ec008ef3.rc0.2207, 0009.11 +# %%{rpm_name}: Kernel RPM package name, eg. kernel, kernel-tlinux4, kernel-stream kernel-stream-debug # %%{rpm_vendor}: RPM package vendor # %%{rpm_url}: RPM url +# TODO: kernel_unamer don't have distro mark {{VERSIONSPEC}} +# TODO: We have a fixed tar name, might be better to include KDIST in tarname +%define kernel_tarname kernel-%{kernel_majver}-%{kernel_relver} + # This section defines following value: # %%{kernel_arch} # Since kernel arch name differs from many other definations, this will insert a script snip @@ -70,19 +72,6 @@ %define use_builtin_module_signer %{?_module_signer: 0} %{?!_module_signer: 1} ###### Required RPM macros ##################################################### -### Kenrel version relation macros -# We only have one kernel core per spec file -# Following three macros is generated by scripts, see VERSIONSPEC above. -# %%{kernel_majver} -# %%{kernel_relver} -# %%{kernel_variant} -%define kernel_tarname kernel-%{kernel_majver}-%{kernel_relver} -# Used for simulate `uname -r` output -%define kernel_unamer %{kernel_majver}-%{kernel_relver}%{?kernel_variant:+%{kernel_variant}} -# Regex to match kernel_unamer -%define kernel_unamer_regex %{kernel_majver}-%{kernel_relver}%{?kernel_variant:[+]%{kernel_variant}} -# kernel_unamer with distro mark -%define kernel_unamer_dist %{kernel_unamer}%{?dist} ### Debuginfo handling # Following macros controls RPM's builtin debuginfo extracting behaviour, @@ -198,8 +187,8 @@ Source2001: cpupower.config ### Main meta package Summary: %{rpm_vendor} Linux kernel meta package Name: %{rpm_name} -Version: %{rpm_version} -Release: %{rpm_release}%{?dist} +Version: %{kernel_majver} +Release: %{kernel_relver}%{?dist} License: GPLv2 URL: %{rpm_url} Vendor: ${rpm_vendor} @@ -235,7 +224,7 @@ Requires(preun): coreutils kmod Requires(post): %{_bindir}/kernel-install Requires(preun): %{_bindir}/kernel-install # Kernel install hooks & initramfs -%if 0%{?rhel} == 7 +%if 0%{?rhel} == 7 || "%{?dist}" == ".tl2" Requires(post): systemd Requires(preun): systemd %else @@ -295,7 +284,8 @@ This is required to use SystemTap with %{rpm_name}. %global _find_debuginfo_opts %{_find_debuginfo_opts} --keep-section '.BTF' %endif # Debuginfo file list for main kernel package -%global _find_debuginfo_opts %{_find_debuginfo_opts} -p '.*\/usr\/src\/kernels/.*|XXX' -o ignored-debuginfo.list -p '/.*/%{kernel_unamer_regex}/.*|/.*%{kernel_unamer_regex}(\.debug)?' -o debuginfo.list +# The (\+.*)? is used to match all variant kernel +%global _find_debuginfo_opts %{_find_debuginfo_opts} -p '.*\/usr\/src\/kernels/.*|XXX' -o ignored-debuginfo.list -p $(echo '/.*/%{kernel_unamer}/.*|/.*%{kernel_unamer}(\.debug)?' | sed 's/+/[+]/g') -o debuginfo.list # with_debuginfo %endif # with_core @@ -461,7 +451,6 @@ This package provides debug information for the bpftool package. # _KernBuild: Path to the built kernel objects, could be same as $_KernSrc (just like source points to build under /lib/modules/) # _KernVmlinuxH: path to vmlinux.h for BTF, located in _buildir # KernUnameR: Get `uname -r` output of the built kernel -# KernExtVer: Kernel EXTRAVERSION plus debug/kasan/syzkaller marker # KernModule: Kernel modules install path, located in %%{buildroot} # KernDevel: Kernel headers and sources install path, located in %%{buildroot} %global prepare_buildvar \ @@ -470,7 +459,6 @@ This package provides debug information for the bpftool package. _KernBuild=%{_builddir}/%{rpm_name}-%{kernel_unamer}/%{kernel_unamer}-obj \ _KernVmlinuxH=%{_builddir}/%{rpm_name}-%{kernel_unamer}/vmlinux.h \ KernUnameR=%{kernel_unamer} \ - KernExtVer=%{kernel_relver}%{?kernel_variant:+%{kernel_variant:}} \ KernModule=%{buildroot}/lib/modules/%{kernel_unamer} \ KernDevel=%{buildroot}/usr/src/kernels/%{kernel_unamer} \ @@ -482,9 +470,6 @@ This package provides debug information for the bpftool package. # TODO: Apply test patch here : -# This Prevents scripts/setlocalversion from mucking with our version numbers. -touch .scmversion - # Mangle /usr/bin/python shebangs to /usr/bin/python3 # Mangle all Python shebangs to be Python 3 explicitly # -p preserves timestamps @@ -500,12 +485,41 @@ find scripts/ tools/ Documentation/ \ -exec pathfix.py -i "%{__python3} %{py3_shbang_opts}" -p -n {} \+; # Update kernel version and suffix info to make uname consistent with RPM version -sed -i "/^EXTRAVERSION/cEXTRAVERSION = -$KernExtVer" $_KernSrc/Makefile # PATCHLEVEL inconsistent only happen on first merge window, but patch them all just in case sed -i "/^VESION/cVERSION = $(echo %{kernel_majver} | cut -d '.' -f 1)" $_KernSrc/Makefile sed -i "/^PATCHLEVEL/cPATCHLEVEL = $(echo %{kernel_majver} | cut -d '.' -f 2)" $_KernSrc/Makefile sed -i "/^SUBLEVEL/cSUBLEVEL = $(echo %{kernel_majver} | cut -d '.' -f 3)" $_KernSrc/Makefile +# Patch the kernel to apply uname, the reason we use EXTRAVERSION to control uname +# instead of complete use LOCALVERSION is that, we don't want out scm/rpm version info +# get inherited by random kernels built reusing the config file under /boot, which +# will be confusing. +_KVERSION=$(sed -nE "/^VERSION\s*:?=\s*(.*)/{s/^\s*^VERSION\s*:?=\s*//;h};\${x;p}" $_KernSrc/Makefile) +_KPATCHLEVEL=$(sed -nE "/^PATCHLEVEL\s*:?=\s*(.*)/{s/^\s*^PATCHLEVEL\s*:?=\s*//;h};\${x;p}" $_KernSrc/Makefile) +_KSUBLEVEL=$(sed -nE "/^SUBLEVEL\s*:?=\s*(.*)/{s/^\s*^SUBLEVEL\s*:?=\s*//;h};\${x;p}" $_KernSrc/Makefile) +_KUNAMER_PREFIX=${_KVERSION}.${_KPATCHLEVEL}.${_KSUBLEVEL} +_KEXTRAVERSION="" +_KLOCALVERSION="" + +case $KernUnameR in + $_KUNAMER_PREFIX* ) + _KEXTRAVERSION=$(echo "$KernUnameR" | sed -e "s/^$_KUNAMER_PREFIX//") + + # Anything after "+" belongs to LOCALVERSION, eg, +debug/+minimal marker. + _KLOCALVERSION=$(echo "$_KEXTRAVERSION" | sed -ne 's/.*\([+].*\)$/\1/p') + _KEXTRAVERSION=$(echo "$_KEXTRAVERSION" | sed -e 's/[+].*$//') + + # Update Makefile to embed uname + sed -i "/^EXTRAVERSION/cEXTRAVERSION = $_KEXTRAVERSION" $_KernSrc/Makefile + # Save LOCALVERSION in .dist.localversion, it will be set to .config after + # .config is ready in BuildConfig. + echo "$_KLOCALVERSION" > $_KernSrc/.dist.localversion + ;; + * ) + echo "FATAL: error: kernel version doesn't match with kernel spec." >&2 && exit 1 + ;; + esac + ###### Rpmbuild Build Stage #################################################### %build @@ -559,13 +573,16 @@ BuildConfig() { cp $1 .config [ "$_KernBuild" != "$_KernSrc" ] && echo "include $_KernSrc/Makefile" > Makefile + [ "$_KernBuild" != "$_KernSrc" ] && cp $_KernSrc/.dist.localversion ./ + + # Respect scripts/setlocalversion, avoid it from potentially mucking with our version numbers. + # Also update LOCALVERSION in .config + cp .dist.localversion .scmversion + "$_KernSrc"/scripts/config --file .config --set-str LOCALVERSION "$(cat .dist.localversion)" # Ensures build-ids are unique to allow parallel debuginfo sed -i -e "s/^CONFIG_BUILD_SALT.*/CONFIG_BUILD_SALT=\"$KernUnameR\"/" .config - # Erase LOCALVERSION to prevent it from mucking with our version numbers - sed -i -e 's/^CONFIG_LOCALVERSION=.*/CONFIG_LOCALVERSION=""/' .config - # Call olddefconfig before make all, set all unset config to default value. # The packager uses CROSS_COMPILE=scripts/dummy-tools for generating .config # so compiler related config are always unset, let's just use defconfig for them for now @@ -1043,7 +1060,7 @@ if command -v uname > /dev/null; then fi %post core -touch %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.installing_core +touch %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.installing_core %posttrans core # Weak modules @@ -1062,7 +1079,7 @@ fi # Just in case kernel-install didn't depmod depmod -A %{kernel_unamer} # Core install done -rm -f %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.installing_core +rm -f %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.installing_core %preun core # Boot entry and depmod files @@ -1082,14 +1099,14 @@ fi ### Module package %post modules depmod -a %{kernel_unamer} -if [ ! -f %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.installing_core ]; then - touch %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.need_to_run_dracut +if [ ! -f %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.installing_core ]; then + touch %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.need_to_run_dracut fi %posttrans modules -if [ -f %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.need_to_run_dracut ]; then\ +if [ -f %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.need_to_run_dracut ]; then\ dracut -f --kver "%{kernel_unamer}" - rm -f %{_localstatedir}/lib/rpm-state/%{rpm_name}-%{rpm_version}-%{rpm_release}%{?dist}.need_to_run_dracut + rm -f %{_localstatedir}/lib/rpm-state/%{name}-%{version}-%{version}%{?dist}.need_to_run_dracut fi %postun modules