[HEADS UP] Kernel modules don't work properly in FreeBSD 8.1-RC1

Andriy Gapon avg at icyb.net.ua
Wed Jun 23 06:47:59 UTC 2010


on 23/06/2010 03:38 Hans Petter Selasky said the following:
> Hi,
> 
> I'm creating a new thread on this issue.
> 
> On Tue, Jun 22, 2010 at 04:39:17PM -0400, Ryan Stone wrote:
>> I saw similar behaviour a couple of years ago when I switched from
>> using gcc 4.0.2 to gcc 4.3.0 to compile some out-of-tree KLD modules.
>> The problem ended up being a change in the linker script used by GNU
>> ld for linking kernel modules.  It used to always put some magic
>> symbols used by the linker to implement things like sysinits into the
>> module.  It was changed to only provide those symbols, which
>> apparently means that the linker would discard those symbols if
>> nothing referenced them(and nothing did reference them).  I had to
>> work around it by adding the following to my link line:
>>
>> -u __start_set_sysinit_set -u __start_set_sysuninit_set \
>> -u __start_set_sysctl_set -u __start_set_modmetadata_set \
>> -u __stop_set_sysinit_set -u __stop_set_sysuninit_set \
>> -u __stop_set_sysctl_set -u __stop_set_modmetadata_set
> 
> It appears many kmods are broken because the linker is stripping away static 
> data declared with the section attribute in FreeBSD 8.1-RC1.
> 
> <cite>
> 
> I added those lines to the LDFLAGS in Makefile.kmod in the cuse4bsd port
> made the module and the result loads and creates the /dev/cuse file.
> 
> Here's a diff relative to
> /usr/ports/multimedia/cuse4bsd-kmod/work/cuse4bsd-kmod-0.1.11 just so
> it's clear what I did.
> 
> 
> --- Makefile.kmod.orig  2010-02-11 03:28:02.000000000 -0800
> +++ Makefile.kmod       2010-06-22 14:02:52.000000000 -0700
> @@ -30,4 +30,10 @@
>  KMOD=  cuse4bsd
>  SRCS=  cuse4bsd_kmod.c device_if.h bus_if.h vnode_if.h
>  
> +LDFLAGS += -u __start_set_sysinit_set -u __start_set_sysuninit_set \
> + -u __start_set_sysctl_set -u __start_set_modmetadata_set \
> + -u __stop_set_sysinit_set -u __stop_set_sysuninit_set \
> + -u __stop_set_sysctl_set -u __stop_set_modmetadata_set
> +
> +
>  .include <bsd.kmod.mk>
> 
> Running nm -o on the two modules, the difference seems to be that the -u
> results in some additional absolute symbols being defined:
> 
> Bad module:
> $ nm -o /boot/modules/cuse4bsd.ko| grep sys
> /boot/modules/cuse4bsd.ko:0000275c r
> __set_sysinit_set_sym_cuse_kern_init_sys_init
> /boot/modules/cuse4bsd.ko:00002758 r 
> __set_sysuninit_set_sym_cuse_kern_uninit_sys_uninit
> /boot/modules/cuse4bsd.ko:00003194 d cuse_kern_init_sys_init
> /boot/modules/cuse4bsd.ko:00003184 d cuse_kern_uninit_sys_uninit

I am not sure if this analysis is correct.
I tested on head and stable/8 and my nm output is exactly like above ("bad
module"), still the module loads fine and creates /dev/cuse.

I don't think there were any recent changes related to build infrastructure or
linker in 8.1.

Please consider other possibilities.

> Good module:
> 
> $ nm -o ./cuse4bsd.ko  | grep sys
> ./cuse4bsd.ko:000028cc r __set_sysinit_set_sym_cuse_kern_init_sys_init
> ./cuse4bsd.ko:000028c8 r __set_sysuninit_set_sym_cuse_kern_uninit_sys_uninit
> ./cuse4bsd.ko:         U __start_set_sysctl_set
> ./cuse4bsd.ko:000028cc A __start_set_sysinit_set
> ./cuse4bsd.ko:000028c8 A __start_set_sysuninit_set
> ./cuse4bsd.ko:         U __stop_set_sysctl_set
> ./cuse4bsd.ko:000028d0 A __stop_set_sysinit_set
> ./cuse4bsd.ko:000028cc A __stop_set_sysuninit_set
> ./cuse4bsd.ko:00003194 d cuse_kern_init_sys_init
> ./cuse4bsd.ko:00003184 d cuse_kern_uninit_sys_uninit
> 
> </cite>

-- 
Andriy Gapon


More information about the freebsd-hackers mailing list