The module class provides what is needed to compile a Linux Kernel module
but since the Makefile is always the same for simple modules that have
their sources in one directory level, I thought of creating new class wrapper
to automatically prepare the Makefile.
Also, using variable flag feature, a recipe can provide multiple modules
and can be handled the same way as PACKAGECONFIG is used to enabled/disable
features.

Signed-off-by: Talel BELHAJSALEM <[email protected]>
---
 .../recipes-kernel/hello-mod/hello-mod_0.1.bb |  11 +-
 meta/classes-recipe/simple-module.bbclass     | 116 ++++++++++++++++++
 2 files changed, 120 insertions(+), 7 deletions(-)
 create mode 100644 meta/classes-recipe/simple-module.bbclass

diff --git a/meta-skeleton/recipes-kernel/hello-mod/hello-mod_0.1.bb 
b/meta-skeleton/recipes-kernel/hello-mod/hello-mod_0.1.bb
index a2fb212a68..f191b08be5 100644
--- a/meta-skeleton/recipes-kernel/hello-mod/hello-mod_0.1.bb
+++ b/meta-skeleton/recipes-kernel/hello-mod/hello-mod_0.1.bb
@@ -3,16 +3,13 @@ DESCRIPTION = "${SUMMARY}"
 LICENSE = "GPL-2.0-only"
 LIC_FILES_CHKSUM = "file://COPYING;md5=12f884d2ae1ff87c09e5b7ccc2c4ca7e"
 
-inherit module
+inherit simple-module
 
-SRC_URI = "file://Makefile \
-           file://hello.c \
+SRC_URI = "file://hello.c \
            file://COPYING \
           "
 
 S = "${WORKDIR}"
 
-# The inherit of module.bbclass will automatically name module packages with
-# "kernel-module-" prefix as required by the oe-core build environment.
-
-RPROVIDES:${PN} += "kernel-module-hello"
+MODULE_SRC = "hello"
+MODULE_SRC[hello] = ""
\ No newline at end of file
diff --git a/meta/classes-recipe/simple-module.bbclass 
b/meta/classes-recipe/simple-module.bbclass
new file mode 100644
index 0000000000..a837dec848
--- /dev/null
+++ b/meta/classes-recipe/simple-module.bbclass
@@ -0,0 +1,116 @@
+#
+# Copyright OpenEmbedded Contributors
+#
+# SPDX-License-Identifier: MIT
+#
+
+# Class to generate Makefile for Linux Kernel modules
+#
+# The aim of this class is to provide a way to gain time
+# when creating recipes for Linux Kernel modules
+#
+# Required variable:
+#   MODULE_SRC
+#
+# This variable itself counts on flags to know what files
+# to use for .ko generation and their .o dependencies
+#
+# Usage:
+#   If you have the following module structure:
+#       |-- module.c
+#       |-- dep1.c
+#       `-- dep2.c
+#   then you set:
+#   MODULE_SRC[module] = "dep1 dep2"
+#
+# This will generate:
+#   obj-m += module.o
+#   module-objs += dep1.o dep2.o
+#
+# This class supports multiple modules as well
+# each module will be added to obj-m and if it has dependencies
+# an -objs variable will be created.
+#
+# A module can be enabled or disabled by adding or removing
+# the module name from MODULE_SRC
+#
+# Limitations:
+#   - All modules source files should exist in the same folder level
+
+inherit module
+
+python do_prepare_makefile() {
+
+    if not (d.getVar('MODULE_SRC') or "").split():
+        bb.warn("You inherited easy-module but did not set drivers in 
MODULE_SRC")
+
+    kernel_modules = (d.getVar('MODULE_SRC') or "").split()
+
+    if kernel_modules:
+        kernel_modules_flags = d.getVarFlags('MODULE_SRC') or []
+
+        objs_data = {}
+        for k_module in kernel_modules:
+
+            # Check if all enabled drivers have corresponding flag
+            if not k_module in kernel_modules_flags:
+                bb.fatal(f"Driver {k_module} is enabled but does not have a 
flag entry")
+
+            k_module_file = f"{k_module}.c"
+            if not os.path.isfile(k_module_file):
+                bb.fatal(f"Source file {k_module_file} is not found")
+
+            k_module_o = f"{k_module}.o"
+            objs_data[k_module] = []
+
+            k_module_deps = (d.getVarFlag('MODULE_SRC', k_module) or 
"").split()
+            for dep in k_module_deps:
+                dep_file = f"{dep}.c"
+                dep_o = f"{dep}.o"
+
+                if not os.path.isfile(dep_file):
+                    bb.fatal(f"Dependency file {dep_file} for the 
{k_module_file} is not found")
+
+                objs_data[k_module].append(dep_o)
+
+        with open('Makefile', 'w') as mf:
+            # Main modules
+            mf.write(
+                f"""
+# This Makefile is generated automatically by easy-module class
+obj-m += {' '.join([objm + '.o' for objm in objs_data.keys()])}
+""")
+
+            # Modules dependencies
+            for k_module, deps in objs_data.items():
+                if deps:
+                    mf.write(
+                        f"""
+{k_module}-objs += {' '.join([dep for dep in deps])}
+""")
+
+            # Rest of Makefile
+            mf.write(
+                """
+SRC := $(shell pwd)
+
+all:
+\t$(MAKE) -C $(KERNEL_SRC) M=$(SRC)
+
+modules_install:
+\t$(MAKE) -C $(KERNEL_SRC) M=$(SRC) modules_install
+
+clean:
+\trm -f *.o *~ core .depend .*.cmd *.ko *.mod.c
+\trm -f Module.markers Module.symvers modules.order
+\trm -rf .tmp_versions Modules.symvers
+""")
+}
+
+RPROVIDES:${PN} += "kernel-module-${PN}"
+
+export SRC = "${B}"
+
+do_prepare_makefile[docs] = "Automate Makefile preparation for simple Kernel 
modules"
+do_prepare_makefile[dirs] = "${B}"
+addtask do_prepare_makefile before do_configure after do_patch
\ No newline at end of file
-- 
2.25.1

-=-=-=-=-=-=-=-=-=-=-=-
Links: You receive all messages sent to this group.
View/Reply Online (#189756): 
https://lists.openembedded.org/g/openembedded-core/message/189756
Mute This Topic: https://lists.openembedded.org/mt/102233042/21656
Group Owner: [email protected]
Unsubscribe: https://lists.openembedded.org/g/openembedded-core/unsub 
[[email protected]]
-=-=-=-=-=-=-=-=-=-=-=-

Reply via email to