From: Jeff Mahoney <jeffm@suse.com>
Subject: kernel: add product-identifying information to kernel build
Patch-mainline: Never, SUSE specific
References: FATE#325281
Our kernels may be offered using the same base kernel version across
several product streams. We have tags in our git repository to map
specific versions to a release, but that requires having easy access
to the repository and taking the multiple steps to resolve the release
information.
This patch makes the product release easier to discover by both SUSE
support staff and third-party developers.
This adds a new <linux/suse_version.h> header that defines several
values that can be used to programatically discover what kernel
version is being used:
* SUSE_PRODUCT_FAMILY The "family" of product, e.g. SLE or Leap
* SUSE_PRODUCT_NAME The full product name, which may consist of
several whitespace-separated words
* SUSE_PRODUCT_SHORTNAME The abbreviated product name where it makes
sense, e.g. SLE15-SP1.
* SUSE_VERSION Numeric major number of release
* SUSE_PATCHLEVEL The minor numer or service pack level of the
release
* SUSE_AUXRELEASE Currently unused
* SUSE_PRODUCT_CODE An encoded product code that is the result of
combining the family, version, patchlevel, and
aux release
* SUSE_PRODUCT Macro to use to generate the code
It also adds a new "suserelease" module tag that contains the
shortname and also prints the shortname after the kernel version during
system faults.
Signed-off-by: Jeff Mahoney <jeffm@suse.com>
---
Makefile | 12 +++++-
init/Kconfig.suse | 70 ++++++++++++++++++++++++++++++
lib/dump_stack.c | 5 ++-
scripts/gen-suse_version_h.sh | 81 +++++++++++++++++++++++++++++++++++
scripts/mod/modpost.c | 10 +++++
5 files changed, 175 insertions(+), 3 deletions(-)
create mode 100644 scripts/gen-suse_version_h.sh
--- a/Makefile
+++ b/Makefile
@@ -1013,6 +1013,15 @@ PHONY += prepare0
export MODORDER := $(if $(KBUILD_EXTMOD),$(KBUILD_EXTMOD)/)modules.order
export MODULES_NSDEPS := $(if $(KBUILD_EXTMOD),$(KBUILD_EXTMOD)/)modules.nsdeps
+suse_version_h := include/generated/uapi/linux/suse_version.h
+
+define filechk_suse_version
+ $(CONFIG_SHELL) $(srctree)/scripts/gen-suse_version_h.sh
+endef
+
+$(suse_version_h): include/config/auto.conf FORCE
+ $(call filechk,suse_version)
+
ifeq ($(KBUILD_EXTMOD),)
core-y += kernel/ certs/ mm/ fs/ ipc/ security/ crypto/ block/
@@ -1128,7 +1137,8 @@ ifdef building_out_of_srctree
endif
archprepare: archheaders archscripts scripts prepare3 outputmakefile \
- asm-generic $(version_h) $(autoksyms_h) include/generated/utsrelease.h
+ asm-generic $(version_h) $(autoksyms_h) include/generated/utsrelease.h \
+ $(suse_version_h)
prepare0: archprepare
$(Q)$(MAKE) $(build)=scripts/mod
--- a/init/Kconfig.suse
+++ b/init/Kconfig.suse
@@ -1,6 +1,75 @@
config SUSE_KERNEL
def_bool y
+menu "SUSE Release Details"
+choice SUSE_PRODUCT_CODE
+ prompt "SUSE Product Family"
+ default SUSE_PRODUCT_SLE
+ depends on SUSE_KERNEL
+ help
+ This option defines the SUSE product family that owns this
+ kernel release.
+
+config SUSE_PRODUCT_SLE
+ bool "SUSE Linux Enteprise"
+
+config SUSE_PRODUCT_OPENSUSE_LEAP
+ bool "openSUSE Leap"
+
+config SUSE_PRODUCT_OPENSUSE_TUMBLEWEED
+ bool "openSUSE Tumbleweed"
+endchoice
+
+config SUSE_PRODUCT_CODE
+ int
+ range 1 3
+ default 1 if SUSE_PRODUCT_SLE
+ default 2 if SUSE_PRODUCT_OPENSUSE_LEAP
+ default 3 if SUSE_PRODUCT_OPENSUSE_TUMBLEWEED
+
+if SUSE_PRODUCT_SLE
+config SUSE_VERSION
+ int "Release Version"
+ range 0 255
+ default 255
+
+config SUSE_PATCHLEVEL
+ int "Service Pack Version"
+ range 0 255
+ default 255
+endif
+
+if SUSE_PRODUCT_OPENSUSE_LEAP
+config SUSE_VERSION
+ int "Release Major Version"
+ range 0 255
+ default 255
+
+config SUSE_PATCHLEVEL
+ int "Release Minor Version"
+ range 0 255
+ default 255
+endif
+
+# Tumbleweed doesn't currently use version information, but we should
+# still have the values defined even if zeroed out.
+if SUSE_PRODUCT_OPENSUSE_TUMBLEWEED
+config SUSE_VERSION
+ int
+ range 0 255
+ default 0
+
+config SUSE_PATCHLEVEL
+ int
+ range 0 255
+ default 0
+endif
+
+config SUSE_AUXRELEASE
+ int
+ range 0 255
+ default 0
+
config SUSE_KERNEL_SUPPORTED
bool "Enable enterprise support facility"
depends on SUSE_KERNEL
@@ -18,3 +87,4 @@ config SUSE_KERNEL_SUPPORTED
If you aren't building a kernel for an enterprise distribution,
say n.
+endmenu
--- a/lib/dump_stack.c
+++ b/lib/dump_stack.c
@@ -12,6 +12,7 @@
#include <linux/atomic.h>
#include <linux/kexec.h>
#include <linux/utsname.h>
+#include <linux/suse_version.h>
static char dump_stack_arch_desc_str[128];
@@ -44,13 +45,13 @@ void __init dump_stack_set_arch_desc(const char *fmt, ...)
*/
void dump_stack_print_info(const char *log_lvl)
{
- printk("%sCPU: %d PID: %d Comm: %.20s %s%s %s %.*s\n",
+ printk("%sCPU: %d PID: %d Comm: %.20s %s%s %s %.*s %s\n",
log_lvl, raw_smp_processor_id(), current->pid, current->comm,
kexec_crash_loaded() ? "Kdump: loaded " : "",
print_tainted(),
init_utsname()->release,
(int)strcspn(init_utsname()->version, " "),
- init_utsname()->version);
+ init_utsname()->version, SUSE_PRODUCT_SHORTNAME);
if (dump_stack_arch_desc_str[0] != '\0')
printk("%sHardware name: %s\n",
--- /dev/null
+++ b/scripts/gen-suse_version_h.sh
@@ -0,0 +1,81 @@
+#!/bin/bash
+
+if test -e include/config/auto.conf; then
+ . include/config/auto.conf
+else
+ echo "Error: auto.conf not generated - run 'make prepare' to create it" >&2
+ exit 1
+fi
+
+VERSION="${CONFIG_SUSE_VERSION}"
+PATCHLEVEL="${CONFIG_SUSE_PATCHLEVEL}"
+AUXRELEASE="${CONFIG_SUSE_AUXRELEASE}"
+
+if [ -z "$VERSION" -o -z "$PATCHLEVEL" -o -z "$AUXRELEASE" ]; then
+ # This would be a bug in the Kconfig
+ cat <<- END >&2
+ ERROR: Missing VERSION, PATCHLEVEL, or AUXRELEASE."
+ Please check init/Kconfig.suse for correctness.
+ END
+ exit 1
+fi
+
+if [ "$VERSION" = 255 -o "$PATCHLEVEL" = 255 ]; then
+ cat <<- END >&2
+
+ ERROR: This release needs to be properly configured.
+ Please add real values for SUSE_VERSION and SUSE_PATCHLEVEL.
+
+ END
+ exit 1
+fi
+
+
+case "$CONFIG_SUSE_PRODUCT_CODE" in
+ 1)
+ if [ "${PATCHLEVEL}" = "0" ]; then
+ SP=""
+ else
+ SP="${PATCHLEVEL}"
+ fi
+ SUSE_PRODUCT_NAME="SUSE Linux Enterprise ${VERSION}${SP:+ SP}${SP}"
+ SUSE_PRODUCT_SHORTNAME="SLE${VERSION}${SP:+-SP}${SP}"
+ SUSE_PRODUCT_FAMILY="SLE"
+ ;;
+ 2)
+ SUSE_PRODUCT_NAME="openSUSE Leap ${VERSION}.${PATCHLEVEL}"
+ SUSE_PRODUCT_SHORTNAME="$SUSE_PRODUCT_NAME"
+ SUSE_PRODUCT_FAMILY="Leap"
+ ;;
+ 3)
+ SUSE_PRODUCT_NAME="openSUSE Tumbleweed"
+ SUSE_PRODUCT_SHORTNAME="$SUSE_PRODUCT_NAME"
+ SUSE_PRODUCT_FAMILY="Tumbleweed"
+ ;;
+ *)
+ echo "Unknown SUSE_PRODUCT_CODE=${CONFIG_SUSE_PRODUCT_CODE}" >&2
+ exit 1
+ ;;
+esac
+
+SUSE_PRODUCT_CODE=$(( (${CONFIG_SUSE_PRODUCT_CODE} << 24) + \
+ (${VERSION} << 16) + (${PATCHLEVEL} << 8) + \
+ ${AUXRELEASE} ))
+
+cat <<END
+#ifndef _SUSE_VERSION_H
+#define _SUSE_VERSION_H
+
+#define SUSE_PRODUCT_FAMILY "${SUSE_PRODUCT_FAMILY}"
+#define SUSE_PRODUCT_NAME "${SUSE_PRODUCT_NAME}"
+#define SUSE_PRODUCT_SHORTNAME "${SUSE_PRODUCT_SHORTNAME}"
+#define SUSE_VERSION ${VERSION}
+#define SUSE_PATCHLEVEL ${PATCHLEVEL}
+#define SUSE_AUXRELEASE ${AUXRELEASE}
+#define SUSE_PRODUCT_CODE ${SUSE_PRODUCT_CODE}
+#define SUSE_PRODUCT(product, version, patchlevel, auxrelease) \\
+ (((product) << 24) + ((version) << 16) + \\
+ ((patchlevel) << 8) + (auxrelease))
+
+#endif /* _SUSE_VERSION_H */
+END
--- a/scripts/mod/modpost.c
+++ b/scripts/mod/modpost.c
@@ -22,6 +22,7 @@
#include "modpost.h"
#include "../../include/generated/autoconf.h"
#include "../../include/linux/license.h"
+#include "../../include/generated/uapi/linux/suse_version.h"
/* Are we using CONFIG_MODVERSIONS? */
static int modversions = 0;
@@ -2475,6 +2476,14 @@ static void add_srcversion(struct buffer *b, struct module *mod)
}
}
+static void add_suserelease(struct buffer *b, struct module *mod)
+{
+#ifdef SUSE_PRODUCT_SHORTNAME
+ buf_printf(b, "\n");
+ buf_printf(b, "MODULE_INFO(suserelease, \"%s\");\n",
+ SUSE_PRODUCT_SHORTNAME);
+#endif
+}
static void write_if_changed(struct buffer *b, const char *fname)
{
char *tmp;
@@ -2763,6 +2772,7 @@ int main(int argc, char **argv)
add_depends(&buf, mod);
add_moddevtable(&buf, mod);
add_srcversion(&buf, mod);
+ add_suserelease(&buf, mod);
sprintf(fname, "%s.mod.c", mod->name);
write_if_changed(&buf, fname);