OpenWrt Forum Archive

Topic: Include kernel module from feed to image build

The content of this topic has been archived on 21 Apr 2018. There are no obvious gaps in this topic, but there may still be some posts missing at the end.

Greetings.
I write modules for OpenWRT and got a problem in including kernel module into system image.
I have written two modules at the moment, included in one feed. One is kernel module and the other is LuCI module.

Both modules are seen in menuconfig and are built ok when I call make. LuCI module is ok, it's built and installed into image without problems. But the kernel module is built properly, but is not included in the system image.

I see the module is not presented in
build_dir/<target_build_root>linux-<architecture>/packages/ipkg-<architecture>
subdirectory of target. Instead, it is put in the feed's subdirectory
build_dir/<target_build_root>/$(PKG_SOURCE_SUBDIR)
I take it, this is the cause of the problem, it's not included in ipkg list for kernel modules.

My question is what should I set in my Makefile (maybe for PKG_SOURCE_SUBDIR) to include my module into the image? I could add ipkg directory to PKG_SOURCE_SUBDIR directly, but I'm not sure if this is right idea, all the more the path for ipkg contains architecture part and I don't want any hardcoded dependencies in Makefile.

You did not share the Makefile that doesn't work...
Maybe the installation step is somehow faulty (AUTOLOAD). Or the compilation command...
And have you defined it as a KernelPackage ? and included the kernel.mk ?

For example, this is a kernel module defined in my build in a feed, and it installs nicely to the firmware image.

perus@ub1604:/Openwrt/trunk/feeds/packages/net/kmod-sched-cake$ cat Makefile 
#
# Copyright (C) 2015-2016 OpenWrt.org
#
# This is free software, licensed under the GNU General Public License v2.
# See /LICENSE for more information.
#

include $(TOPDIR)/rules.mk
include $(INCLUDE_DIR)/kernel.mk

PKG_NAME:=sched-cake
PKG_VERSION:=2016-git
PKG_RELEASE:=17

PKG_SOURCE_PROTO:=git
PKG_SOURCE_URL:=git://github.com/dtaht/sch_cake
PKG_SOURCE_VERSION:=df40fa23fbbed9f652e201058fc730f37ae7513c
PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION)-$(PKG_RELEASE).tar.gz
PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)
PKG_BUILD_ID:=$(PKG_SOURCE_VERSION)

include $(INCLUDE_DIR)/package.mk

define KernelPackage/sched-cake
  SUBMENU:=Network Support
  TITLE:=Cake fq_codel derived shaper
  URL:=https://github.com/dtaht/sch_cake
  FILES:=$(PKG_BUILD_DIR)/sch_cake.ko
  VERSION:=$(LINUX_VERSION)-$(LINUX_RELEASE)
  AUTOLOAD:=$(call AutoLoad,75,sch_cake)
endef

include $(INCLUDE_DIR)/kernel-defaults.mk

define KernelPackage/sched-cake/description
  Common Applications Kept Enhanced fq_codel derived shaper
endef

define Build/Compile
    $(MAKE) $(KERNEL_MAKEOPTS) SUBDIRS="$(PKG_BUILD_DIR)" modules
endef

$(eval $(call KernelPackage,sched-cake))

EDIT:
the compilation log shows that the binary was compiled in staging_dir/target-mips_34kc_musl-1.1.14/root-ar71xx/tmp-kmod-sched-cake , but that directory is deleted after the package has been compiled, installed and *.ipk copied to bin/ar71xx/...

(Last edited by hnyman on 1 Jun 2016, 11:24)

Here's the Makefile (I removed extra operations for copying config and prerm files that are not actual from install section).

include $(TOPDIR)/rules.mk
include $(INCLUDE_DIR)/kernel.mk

PKG_NAME:=module-name

PKG_VERSION:=1.0.0
PKG_RELEASE:=0

PKG_SOURCE_SUBDIR:=$(PKG_NAME)-$(PKG_VERSION)

MODULE_FILES=$(PKG_BUILD_DIR)/$(PKG_NAME).ko

include $(INCLUDE_DIR)/package.mk

MODULE_HEADER:=$(PKG_NAME).h

define KernelPackage/$(PKG_NAME)
  SUBMENU:=Module Name
  TITLE:=Module description
  CATEGORY:=MyCategory
  MAINTAINER:=My name, bla-bla-bla
  URL:=http://some.url
  FILES:=$(MODULE_FILES)
  VERSION:=$(LINUX_VERSION)-$(LINUX_RELEASE)_$(PKG_VERSION)-$(PKG_RELEASE)
  AUTOLOAD:=$(call AutoLoad,55,$(PKG_NAME))
endef

define KernelPackage/$(PKG_NAME)/description
 Package description, bla-bla-bla
endef

MAKE_ARGS:= \
    KERNELPATH="$(LINUX_DIR)"  $(TARGET_CONFIGURE_OPTS) \
    LDOPTS="--no-warn-mismatch " ARCH="$(LINUX_KARCH)"

# Directory that kernel headers are included from (during compilation)
KERNEL_HEADERS_DIR=$(STAGING_DIR)/usr/include

define Build/Prepare
    $(CP) ./src/* $(PKG_BUILD_DIR)
endef

define Build/Configure
endef

define Build/Compile
    echo $(MAKE_ARGS)
    $(MAKE) -C $(PKG_BUILD_DIR) $(MAKE_ARGS) modules
endef

define KernelPackage/$(PKG_NAME)/install
    $(INSTALL_DIR) $(KERNEL_HEADERS_DIR)
    $(CP) ./src/$(MODULE_HEADER) $(KERNEL_HEADERS_DIR)
endef

define Build/Clean
    $(RM) $(KERNEL_HEADERS_DIR)/$(MODULE_HEADER)
endef

$(eval $(call KernelPackage,$(PKG_NAME)))

The module builds, the image is placed into
bin/<arch>/packages/feed_name/kmod-<package_name>_<kernel_version>_<package-version>_<arch>.ipk

But it does not get into binary system image.

P.S. I omitted feed params in Makefile, since for a while I include it to feeds as src-cpy and path to relative local directory.

(Last edited by iron_bug on 1 Jun 2016, 13:49)

Ok, it seems I fixed it. included kernel-defaults.mk and compiled kernel module with * option in OpenWRT configurator. It works now.
I thought that "*" meant compiling module directly into kernel, like usually linux kernel compilation works. But it turned out it was not kernel-like settings.

Yeah,
'*' in menuconfig means build and include the package in firmware ('=y' in .config)
'M' means just build the package as an installable *.ipk but do NOT include in firmware ('=m' in .config)

(Last edited by hnyman on 1 Jun 2016, 14:51)

The discussion might have continued from here.