public inbox for linux-kbuild@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH] kbuild: generate modules.builtin
@ 2009-05-26 15:25 Michal Marek
  2009-05-27 21:26 ` Kay Sievers
       [not found] ` <20090703144547.GA20980@sepie.suse.cz>
  0 siblings, 2 replies; 10+ messages in thread
From: Michal Marek @ 2009-05-26 15:25 UTC (permalink / raw)
  To: Sam Ravnborg; +Cc: linux-kbuild, linux-kernel

To make it easier for tools like mkinitrd to detect whether a needed
module is missing or whether it is compiled into the kernel, install a
modules.builtin file listing all modules built into the kernel. This is
done by generating an alternate config file with all tristate =y options
set to =Y and reading the makefiles with this config included. The built
in modules then appear in obj-Y.

Known issues (found when comparing results with allyesconfig and
allmodconfig):
 * ALSA makefiles do some substitutions on the CONFIG_*
   variables sometimes, which breaks the logic if the alsa modules are
   built-in. Patch sent to alsa-devel.
 * samples/kobject/*.o could be compiled built-in, but doesn't show up
   in modules.builtin (and not even in vmlinux.o). Patch sent to Greg to
   make it module-only.
 * net/{8021q/vlan_core,ethernet/pe2,ipv6/inet6_hashtables}.o are always
   built-in, even though the corresponding config option is tristate:
   obj-$(subst m,y,$(CONFIG_IPX)) += pe2.o
   The result is that modules.builtin can contain three built-in
   "modules" that can't possibly exist as modules. No fix for this so far,
   as it is not a big issue IMO.

Signed-off-by: Michal Marek <mmarek@suse.cz>
---
 .gitignore                  |    1 +
 Makefile                    |   12 ++++++++--
 scripts/Kbuild.include      |    6 +++++
 scripts/Makefile.lib        |    5 +++-
 scripts/Makefile.modbuiltin |   48 +++++++++++++++++++++++++++++++++++++++++++
 scripts/kconfig/confdata.c  |   48 ++++++++++++++++++++++++++++++++++++------
 6 files changed, 109 insertions(+), 11 deletions(-)
 create mode 100644 scripts/Makefile.modbuiltin

diff --git a/.gitignore b/.gitignore
index 51bd99d..7479069 100644
--- a/.gitignore
+++ b/.gitignore
@@ -22,6 +22,7 @@
 *.lst
 *.symtypes
 *.order
+modules.builtin
 *.elf
 *.bin
 *.gz
diff --git a/Makefile b/Makefile
index b57e1f5..d2265ba 100644
--- a/Makefile
+++ b/Makefile
@@ -878,6 +878,9 @@ $(sort $(vmlinux-init) $(vmlinux-main)) $(vmlinux-lds): $(vmlinux-dirs) ;
 PHONY += $(vmlinux-dirs)
 $(vmlinux-dirs): prepare scripts
 	$(Q)$(MAKE) $(build)=$@
+ifdef CONFIG_MODULES
+	$(Q)$(MAKE) $(modbuiltin)=$@
+endif
 
 # Build the kernel release string
 #
@@ -1133,6 +1136,7 @@ all: modules
 PHONY += modules
 modules: $(vmlinux-dirs) $(if $(KBUILD_BUILTIN),vmlinux)
 	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.order) > $(objtree)/modules.order
+	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.builtin) > $(objtree)/modules.builtin
 	@$(kecho) '  Building modules, stage 2.';
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modpost
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.fwinst obj=firmware __fw_modbuild
@@ -1161,7 +1165,7 @@ _modinst_:
 		rm -f $(MODLIB)/build ; \
 		ln -s $(objtree) $(MODLIB)/build ; \
 	fi
-	@cp -f $(objtree)/modules.order $(MODLIB)/
+	@cp -f $(objtree)/modules.{order,builtin} $(MODLIB)/
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modinst
 
 # This depmod is only for convenience to give the initial
@@ -1224,7 +1228,8 @@ clean: archclean $(clean-dirs)
 		\( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \
 		-o -name '.*.d' -o -name '.*.tmp' -o -name '*.mod.c' \
 		-o -name '*.symtypes' -o -name 'modules.order' \
-		-o -name 'Module.markers' -o -name '.tmp_*.o.*' \) \
+		-o -name 'modules.builtin' -o -name 'Module.markers' \
+		-o -name '.tmp_*.o.*' \) \
 		-type f -print | xargs rm -f
 
 # mrproper - Delete all generated files, including .config
@@ -1423,7 +1428,8 @@ $(clean-dirs):
 clean:	rm-dirs := $(MODVERDIR)
 clean: rm-files := $(KBUILD_EXTMOD)/Module.symvers \
                    $(KBUILD_EXTMOD)/Module.markers \
-                   $(KBUILD_EXTMOD)/modules.order
+                   $(KBUILD_EXTMOD)/modules.order \
+                   $(KBUILD_EXTMOD)/modules.builtin
 clean: $(clean-dirs)
 	$(call cmd,rmdirs)
 	$(call cmd,rmfiles)
diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include
index c29be8f..1cded3b 100644
--- a/scripts/Kbuild.include
+++ b/scripts/Kbuild.include
@@ -143,6 +143,12 @@ ld-option = $(call try-run,\
 # $(Q)$(MAKE) $(build)=dir
 build := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.build obj
 
+###
+# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.modbuiltin obj=
+# Usage:
+# $(Q)$(MAKE) $(modbuiltin)=dir
+modbuiltin := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.modbuiltin obj
+
 # Prefix -I with $(srctree) if it is not an absolute path.
 # skip if -I has no parameter
 addtree = $(if $(patsubst -I%,%,$(1)), \
diff --git a/scripts/Makefile.lib b/scripts/Makefile.lib
index cba61ca..427375e 100644
--- a/scripts/Makefile.lib
+++ b/scripts/Makefile.lib
@@ -37,6 +37,8 @@ modorder	:= $(patsubst %/,%/modules.order, $(filter %/, $(obj-y)) $(obj-m:.o=.ko
 
 __subdir-y	:= $(patsubst %/,%,$(filter %/, $(obj-y)))
 subdir-y	+= $(__subdir-y)
+__subdir-Y	:= $(patsubst %/,%,$(filter %/, $(obj-Y)))
+subdir-Y	+= $(__subdir-Y)
 __subdir-m	:= $(patsubst %/,%,$(filter %/, $(obj-m)))
 subdir-m	+= $(__subdir-m)
 obj-y		:= $(patsubst %/, %/built-in.o, $(obj-y))
@@ -44,7 +46,7 @@ obj-m		:= $(filter-out %/, $(obj-m))
 
 # Subdirectories we need to descend into
 
-subdir-ym	:= $(sort $(subdir-y) $(subdir-m))
+subdir-ym	:= $(sort $(subdir-y) $(subdir-Y) $(subdir-m))
 
 # if $(foo-objs) exists, foo.o is a composite object 
 multi-used-y := $(sort $(foreach m,$(obj-y), $(if $(strip $($(m:.o=-objs)) $($(m:.o=-y))), $(m))))
@@ -76,6 +78,7 @@ always		:= $(addprefix $(obj)/,$(always))
 targets		:= $(addprefix $(obj)/,$(targets))
 modorder	:= $(addprefix $(obj)/,$(modorder))
 obj-y		:= $(addprefix $(obj)/,$(obj-y))
+obj-Y		:= $(addprefix $(obj)/,$(obj-Y))
 obj-m		:= $(addprefix $(obj)/,$(obj-m))
 lib-y		:= $(addprefix $(obj)/,$(lib-y))
 subdir-obj-y	:= $(addprefix $(obj)/,$(subdir-obj-y))
diff --git a/scripts/Makefile.modbuiltin b/scripts/Makefile.modbuiltin
new file mode 100644
index 0000000..55e1885
--- /dev/null
+++ b/scripts/Makefile.modbuiltin
@@ -0,0 +1,48 @@
+# ==========================================================================
+# Generating modules.builtin
+# ==========================================================================
+
+src := $(obj)
+
+PHONY := __modbuiltin
+__modbuiltin:
+
+# Read auto2.conf which sets tristate variables to 'Y' instead of 'y'
+# That way, we get the list of built-in modules in obj-Y
+-include include/config/auto2.conf
+
+include scripts/Kbuild.include
+
+# The filename Kbuild has precedence over Makefile
+kbuild-dir := $(if $(filter /%,$(src)),$(src),$(srctree)/$(src))
+kbuild-file := $(if $(wildcard $(kbuild-dir)/Kbuild),$(kbuild-dir)/Kbuild,$(kbuild-dir)/Makefile)
+include $(kbuild-file)
+
+include scripts/Makefile.lib
+
+modbuiltin-subdirs := $(patsubst %,%/modules.builtin, $(subdir-ym))
+modbuiltin-mods    := $(filter %.ko, $(obj-Y:.o=.ko))
+modbuiltin-target  := $(obj)/modules.builtin
+
+__modbuiltin: $(modbuiltin-target) $(subdir-ym)
+	@:
+
+modbuiltin-cmds =						\
+	for m in $(modbuiltin-mods); do echo kernel/$$m; done;	\
+	cat /dev/null $(modbuiltin-subdirs);
+
+$(modbuiltin-target): $(subdir-ym)
+	$(Q)($(modbuiltin-cmds)) > $@
+
+# Descending
+# ---------------------------------------------------------------------------
+
+PHONY += $(subdir-ym)
+$(subdir-ym):
+	$(Q)$(MAKE) $(modbuiltin)=$@
+
+
+# Declare the contents of the .PHONY variable as phony.  We keep that
+# information in a variable se we can use it in if_changed and friends.
+
+.PHONY: $(PHONY)
diff --git a/scripts/kconfig/confdata.c b/scripts/kconfig/confdata.c
index 273d738..4982aa2 100644
--- a/scripts/kconfig/confdata.c
+++ b/scripts/kconfig/confdata.c
@@ -666,12 +666,27 @@ out:
 	return res;
 }
 
+int fprintf2(FILE *f1, FILE *f2, const char *fmt, ...)
+{
+	va_list ap;
+	int res;
+
+	va_start(ap, fmt);
+	vfprintf(f1, fmt, ap);
+	va_end(ap);
+	va_start(ap, fmt);
+	res = vfprintf(f2, fmt, ap);
+	va_end(ap);
+
+	return res;
+}
+
 int conf_write_autoconf(void)
 {
 	struct symbol *sym;
 	const char *str;
 	char *name;
-	FILE *out, *out_h;
+	FILE *out, *out2, *out_h;
 	time_t now;
 	int i, l;
 
@@ -686,16 +701,23 @@ int conf_write_autoconf(void)
 	if (!out)
 		return 1;
 
+	out2 = fopen(".tmpconfig2", "w");
+	if (!out2) {
+		fclose(out);
+		return 1;
+	}
+
 	out_h = fopen(".tmpconfig.h", "w");
 	if (!out_h) {
 		fclose(out);
+		fclose(out2);
 		return 1;
 	}
 
 	sym = sym_lookup("KERNELVERSION", 0);
 	sym_calc_value(sym);
 	time(&now);
-	fprintf(out, "#\n"
+	fprintf2(out, out2, "#\n"
 		     "# Automatically generated make config: don't edit\n"
 		     "# Linux kernel version: %s\n"
 		     "# %s"
@@ -720,45 +742,51 @@ int conf_write_autoconf(void)
 			case no:
 				break;
 			case mod:
-				fprintf(out, "CONFIG_%s=m\n", sym->name);
+				fprintf2(out, out2, "CONFIG_%s=m\n",
+						sym->name);
 				fprintf(out_h, "#define CONFIG_%s_MODULE 1\n", sym->name);
 				break;
 			case yes:
 				fprintf(out, "CONFIG_%s=y\n", sym->name);
+				fprintf(out2, "CONFIG_%s=%c\n", sym->name,
+					sym->type == S_BOOLEAN ? 'y' : 'Y');
 				fprintf(out_h, "#define CONFIG_%s 1\n", sym->name);
 				break;
 			}
 			break;
 		case S_STRING:
 			str = sym_get_string_value(sym);
-			fprintf(out, "CONFIG_%s=\"", sym->name);
+			fprintf2(out, out2, "CONFIG_%s=\"", sym->name);
 			fprintf(out_h, "#define CONFIG_%s \"", sym->name);
 			while (1) {
 				l = strcspn(str, "\"\\");
 				if (l) {
 					fwrite(str, l, 1, out);
+					fwrite(str, l, 1, out2);
 					fwrite(str, l, 1, out_h);
 					str += l;
 				}
 				if (!*str)
 					break;
-				fprintf(out, "\\%c", *str);
+				fprintf2(out, out2, "\\%c", *str);
 				fprintf(out_h, "\\%c", *str);
 				str++;
 			}
 			fputs("\"\n", out);
+			fputs("\"\n", out2);
 			fputs("\"\n", out_h);
 			break;
 		case S_HEX:
 			str = sym_get_string_value(sym);
 			if (str[0] != '0' || (str[1] != 'x' && str[1] != 'X')) {
-				fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
+				fprintf2(out, out2, "CONFIG_%s=%s\n",
+						sym->name, str);
 				fprintf(out_h, "#define CONFIG_%s 0x%s\n", sym->name, str);
 				break;
 			}
 		case S_INT:
 			str = sym_get_string_value(sym);
-			fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
+			fprintf2(out, out2, "CONFIG_%s=%s\n", sym->name, str);
 			fprintf(out_h, "#define CONFIG_%s %s\n", sym->name, str);
 			break;
 		default:
@@ -766,6 +794,7 @@ int conf_write_autoconf(void)
 		}
 	}
 	fclose(out);
+	fclose(out2);
 	fclose(out_h);
 
 	name = getenv("KCONFIG_AUTOHEADER");
@@ -773,6 +802,11 @@ int conf_write_autoconf(void)
 		name = "include/linux/autoconf.h";
 	if (rename(".tmpconfig.h", name))
 		return 1;
+	name = getenv("KCONFIG_AUTOCONFIG2");
+	if (!name)
+		name = "include/config/auto2.conf";
+	if (rename(".tmpconfig2", name))
+		return 1;
 	name = getenv("KCONFIG_AUTOCONFIG");
 	if (!name)
 		name = "include/config/auto.conf";
-- 
1.6.3

^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-05-26 15:25 [PATCH] kbuild: generate modules.builtin Michal Marek
@ 2009-05-27 21:26 ` Kay Sievers
  2009-05-27 21:38   ` Scott James Remnant
       [not found] ` <20090703144547.GA20980@sepie.suse.cz>
  1 sibling, 1 reply; 10+ messages in thread
From: Kay Sievers @ 2009-05-27 21:26 UTC (permalink / raw)
  To: Michal Marek; +Cc: Sam Ravnborg, linux-kbuild, linux-kernel

On Tue, May 26, 2009 at 17:25, Michal Marek <mmarek@suse.cz> wrote:
> To make it easier for tools like mkinitrd to detect whether a needed
> module is missing or whether it is compiled into the kernel, install a
> modules.builtin file listing all modules built into the kernel. This is
> done by generating an alternate config file with all tristate =y options
> set to =Y and reading the makefiles with this config included. The built
> in modules then appear in obj-Y.

That looks very useful.

We like to have that for modprobe not to throw an error if a "module"
is already in the kernel, because it is compiled in. Only modules with
parameters show up in /sys/modules/ and they are already handled fine.

Thanks,
Kay

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-05-27 21:26 ` Kay Sievers
@ 2009-05-27 21:38   ` Scott James Remnant
  0 siblings, 0 replies; 10+ messages in thread
From: Scott James Remnant @ 2009-05-27 21:38 UTC (permalink / raw)
  To: Kay Sievers; +Cc: Michal Marek, Sam Ravnborg, linux-kbuild, linux-kernel

[-- Attachment #1: Type: text/plain, Size: 954 bytes --]

On Wed, 2009-05-27 at 23:26 +0200, Kay Sievers wrote:

> On Tue, May 26, 2009 at 17:25, Michal Marek <mmarek@suse.cz> wrote:
> > To make it easier for tools like mkinitrd to detect whether a needed
> > module is missing or whether it is compiled into the kernel, install a
> > modules.builtin file listing all modules built into the kernel. This is
> > done by generating an alternate config file with all tristate =y options
> > set to =Y and reading the makefiles with this config included. The built
> > in modules then appear in obj-Y.
> 
> That looks very useful.
> 
> We like to have that for modprobe not to throw an error if a "module"
> is already in the kernel, because it is compiled in. Only modules with
> parameters show up in /sys/modules/ and they are already handled fine.
> 
Agree, this helps us support both distro kernels with some built-ins and
modular kernels.

Scott
-- 
Scott James Remnant
scott@ubuntu.com

[-- Attachment #2: This is a digitally signed message part --]
[-- Type: application/pgp-signature, Size: 197 bytes --]

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
       [not found] ` <20090703144547.GA20980@sepie.suse.cz>
@ 2009-07-15 16:39   ` Scott James Remnant
  2009-07-15 16:46     ` Kay Sievers
  0 siblings, 1 reply; 10+ messages in thread
From: Scott James Remnant @ 2009-07-15 16:39 UTC (permalink / raw)
  To: Michal Marek, linux-modules; +Cc: Sam Ravnborg, linux-kbuild, linux-kernel

[-- Attachment #1: Type: text/plain, Size: 12479 bytes --]

Still would definitely like - adding linux-modules to the Cc

On Fri, 2009-07-03 at 16:45 +0200, Michal Marek wrote:

> On Tue, May 26, 2009 at 05:25:40PM +0200, Michal Marek wrote:
> > Known issues (found when comparing results with allyesconfig and
> > allmodconfig):
> >  * ALSA makefiles do some substitutions on the CONFIG_*
> >    variables sometimes, which breaks the logic if the alsa modules are
> >    built-in. Patch sent to alsa-devel.
> >  * samples/kobject/*.o could be compiled built-in, but doesn't show up
> >    in modules.builtin (and not even in vmlinux.o). Patch sent to Greg to
> >    make it module-only.
> 
> These two are merged already.
> 
> 
> >  * net/{8021q/vlan_core,ethernet/pe2,ipv6/inet6_hashtables}.o are always
> >    built-in, even though the corresponding config option is tristate:
> >    obj-$(subst m,y,$(CONFIG_IPX)) += pe2.o
> >    The result is that modules.builtin can contain three built-in
> >    "modules" that can't possibly exist as modules. No fix for this so far,
> >    as it is not a big issue IMO.
> 
> I hope this one is not a problem.
> 
> I rebased the patch on top of current kbuild-next.git. What do you think
> about it? Do you agree on the modules.builtin file name and format? I'd
> like to add support for this to module-init-tools.
> 
> 
> Subject: [PATCH] kbuild: generate modules.builtin
> 
> To make it easier for tools like mkinitrd to detect whether a needed
> module is missing or whether it is compiled into the kernel, install a
> modules.builtin file listing all modules built into the kernel. This is
> done by generating an alternate config file with all tristate =y options
> set to =Y and reading the makefiles with this config included. The built
> in modules then appear in obj-Y.
> 
> Signed-off-by: Michal Marek <mmarek@suse.cz>
> ---
>  .gitignore                  |    1 +
>  Makefile                    |   14 +++++++++---
>  scripts/Kbuild.include      |    6 +++++
>  scripts/Makefile.lib        |    5 +++-
>  scripts/Makefile.modbuiltin |   48 +++++++++++++++++++++++++++++++++++++++++++
>  scripts/kconfig/confdata.c  |   48 ++++++++++++++++++++++++++++++++++++------
>  6 files changed, 110 insertions(+), 12 deletions(-)
>  create mode 100644 scripts/Makefile.modbuiltin
> 
> diff --git a/.gitignore b/.gitignore
> index cecb3b0..d8c1e79 100644
> --- a/.gitignore
> +++ b/.gitignore
> @@ -22,6 +22,7 @@
>  *.lst
>  *.symtypes
>  *.order
> +modules.builtin
>  *.elf
>  *.bin
>  *.gz
> diff --git a/Makefile b/Makefile
> index 46e1c9d..c59e167 100644
> --- a/Makefile
> +++ b/Makefile
> @@ -871,6 +871,9 @@ $(sort $(vmlinux-init) $(vmlinux-main)) $(vmlinux-lds): $(vmlinux-dirs) ;
>  PHONY += $(vmlinux-dirs)
>  $(vmlinux-dirs): prepare scripts
>  	$(Q)$(MAKE) $(build)=$@
> +ifdef CONFIG_MODULES
> +	$(Q)$(MAKE) $(modbuiltin)=$@
> +endif
>  
>  # Build the kernel release string
>  #
> @@ -1126,6 +1129,7 @@ all: modules
>  PHONY += modules
>  modules: $(vmlinux-dirs) $(if $(KBUILD_BUILTIN),vmlinux)
>  	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.order) > $(objtree)/modules.order
> +	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.builtin) > $(objtree)/modules.builtin
>  	@$(kecho) '  Building modules, stage 2.';
>  	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modpost
>  	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.fwinst obj=firmware __fw_modbuild
> @@ -1154,7 +1158,7 @@ _modinst_:
>  		rm -f $(MODLIB)/build ; \
>  		ln -s $(objtree) $(MODLIB)/build ; \
>  	fi
> -	@cp -f $(objtree)/modules.order $(MODLIB)/
> +	@cp -f $(objtree)/modules.{order,builtin} $(MODLIB)/
>  	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modinst
>  
>  # This depmod is only for convenience to give the initial
> @@ -1217,8 +1221,9 @@ clean: archclean $(clean-dirs)
>  		\( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \
>  		-o -name '.*.d' -o -name '.*.tmp' -o -name '*.mod.c' \
>  		-o -name '*.symtypes' -o -name 'modules.order' \
> -		-o -name 'Module.markers' -o -name '.tmp_*.o.*' \
> -		-o -name '*.gcno' \) -type f -print | xargs rm -f
> +		-o -name 'modules.builtin' -o -name 'Module.markers' \
> +		-o -name '.tmp_*.o.*' -o -name '*.gcno' \) \
> +		-type f -print | xargs rm -f
>  
>  # mrproper - Delete all generated files, including .config
>  #
> @@ -1416,7 +1421,8 @@ $(clean-dirs):
>  clean:	rm-dirs := $(MODVERDIR)
>  clean: rm-files := $(KBUILD_EXTMOD)/Module.symvers \
>                     $(KBUILD_EXTMOD)/Module.markers \
> -                   $(KBUILD_EXTMOD)/modules.order
> +                   $(KBUILD_EXTMOD)/modules.order \
> +                   $(KBUILD_EXTMOD)/modules.builtin
>  clean: $(clean-dirs)
>  	$(call cmd,rmdirs)
>  	$(call cmd,rmfiles)
> diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include
> index c29be8f..1cded3b 100644
> --- a/scripts/Kbuild.include
> +++ b/scripts/Kbuild.include
> @@ -143,6 +143,12 @@ ld-option = $(call try-run,\
>  # $(Q)$(MAKE) $(build)=dir
>  build := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.build obj
>  
> +###
> +# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.modbuiltin obj=
> +# Usage:
> +# $(Q)$(MAKE) $(modbuiltin)=dir
> +modbuiltin := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.modbuiltin obj
> +
>  # Prefix -I with $(srctree) if it is not an absolute path.
>  # skip if -I has no parameter
>  addtree = $(if $(patsubst -I%,%,$(1)), \
> diff --git a/scripts/Makefile.lib b/scripts/Makefile.lib
> index 7a77787..3525b29 100644
> --- a/scripts/Makefile.lib
> +++ b/scripts/Makefile.lib
> @@ -37,6 +37,8 @@ modorder	:= $(patsubst %/,%/modules.order, $(filter %/, $(obj-y)) $(obj-m:.o=.ko
>  
>  __subdir-y	:= $(patsubst %/,%,$(filter %/, $(obj-y)))
>  subdir-y	+= $(__subdir-y)
> +__subdir-Y	:= $(patsubst %/,%,$(filter %/, $(obj-Y)))
> +subdir-Y	+= $(__subdir-Y)
>  __subdir-m	:= $(patsubst %/,%,$(filter %/, $(obj-m)))
>  subdir-m	+= $(__subdir-m)
>  obj-y		:= $(patsubst %/, %/built-in.o, $(obj-y))
> @@ -44,7 +46,7 @@ obj-m		:= $(filter-out %/, $(obj-m))
>  
>  # Subdirectories we need to descend into
>  
> -subdir-ym	:= $(sort $(subdir-y) $(subdir-m))
> +subdir-ym	:= $(sort $(subdir-y) $(subdir-Y) $(subdir-m))
>  
>  # if $(foo-objs) exists, foo.o is a composite object 
>  multi-used-y := $(sort $(foreach m,$(obj-y), $(if $(strip $($(m:.o=-objs)) $($(m:.o=-y))), $(m))))
> @@ -76,6 +78,7 @@ always		:= $(addprefix $(obj)/,$(always))
>  targets		:= $(addprefix $(obj)/,$(targets))
>  modorder	:= $(addprefix $(obj)/,$(modorder))
>  obj-y		:= $(addprefix $(obj)/,$(obj-y))
> +obj-Y		:= $(addprefix $(obj)/,$(obj-Y))
>  obj-m		:= $(addprefix $(obj)/,$(obj-m))
>  lib-y		:= $(addprefix $(obj)/,$(lib-y))
>  subdir-obj-y	:= $(addprefix $(obj)/,$(subdir-obj-y))
> diff --git a/scripts/Makefile.modbuiltin b/scripts/Makefile.modbuiltin
> new file mode 100644
> index 0000000..55e1885
> --- /dev/null
> +++ b/scripts/Makefile.modbuiltin
> @@ -0,0 +1,48 @@
> +# ==========================================================================
> +# Generating modules.builtin
> +# ==========================================================================
> +
> +src := $(obj)
> +
> +PHONY := __modbuiltin
> +__modbuiltin:
> +
> +# Read auto2.conf which sets tristate variables to 'Y' instead of 'y'
> +# That way, we get the list of built-in modules in obj-Y
> +-include include/config/auto2.conf
> +
> +include scripts/Kbuild.include
> +
> +# The filename Kbuild has precedence over Makefile
> +kbuild-dir := $(if $(filter /%,$(src)),$(src),$(srctree)/$(src))
> +kbuild-file := $(if $(wildcard $(kbuild-dir)/Kbuild),$(kbuild-dir)/Kbuild,$(kbuild-dir)/Makefile)
> +include $(kbuild-file)
> +
> +include scripts/Makefile.lib
> +
> +modbuiltin-subdirs := $(patsubst %,%/modules.builtin, $(subdir-ym))
> +modbuiltin-mods    := $(filter %.ko, $(obj-Y:.o=.ko))
> +modbuiltin-target  := $(obj)/modules.builtin
> +
> +__modbuiltin: $(modbuiltin-target) $(subdir-ym)
> +	@:
> +
> +modbuiltin-cmds =						\
> +	for m in $(modbuiltin-mods); do echo kernel/$$m; done;	\
> +	cat /dev/null $(modbuiltin-subdirs);
> +
> +$(modbuiltin-target): $(subdir-ym)
> +	$(Q)($(modbuiltin-cmds)) > $@
> +
> +# Descending
> +# ---------------------------------------------------------------------------
> +
> +PHONY += $(subdir-ym)
> +$(subdir-ym):
> +	$(Q)$(MAKE) $(modbuiltin)=$@
> +
> +
> +# Declare the contents of the .PHONY variable as phony.  We keep that
> +# information in a variable se we can use it in if_changed and friends.
> +
> +.PHONY: $(PHONY)
> diff --git a/scripts/kconfig/confdata.c b/scripts/kconfig/confdata.c
> index a04da34..8e2c166 100644
> --- a/scripts/kconfig/confdata.c
> +++ b/scripts/kconfig/confdata.c
> @@ -672,12 +672,27 @@ out:
>  	return res;
>  }
>  
> +int fprintf2(FILE *f1, FILE *f2, const char *fmt, ...)
> +{
> +	va_list ap;
> +	int res;
> +
> +	va_start(ap, fmt);
> +	vfprintf(f1, fmt, ap);
> +	va_end(ap);
> +	va_start(ap, fmt);
> +	res = vfprintf(f2, fmt, ap);
> +	va_end(ap);
> +
> +	return res;
> +}
> +
>  int conf_write_autoconf(void)
>  {
>  	struct symbol *sym;
>  	const char *str;
>  	const char *name;
> -	FILE *out, *out_h;
> +	FILE *out, *out2, *out_h;
>  	time_t now;
>  	int i, l;
>  
> @@ -692,16 +707,23 @@ int conf_write_autoconf(void)
>  	if (!out)
>  		return 1;
>  
> +	out2 = fopen(".tmpconfig2", "w");
> +	if (!out2) {
> +		fclose(out);
> +		return 1;
> +	}
> +
>  	out_h = fopen(".tmpconfig.h", "w");
>  	if (!out_h) {
>  		fclose(out);
> +		fclose(out2);
>  		return 1;
>  	}
>  
>  	sym = sym_lookup("KERNELVERSION", 0);
>  	sym_calc_value(sym);
>  	time(&now);
> -	fprintf(out, "#\n"
> +	fprintf2(out, out2, "#\n"
>  		     "# Automatically generated make config: don't edit\n"
>  		     "# Linux kernel version: %s\n"
>  		     "# %s"
> @@ -726,45 +748,51 @@ int conf_write_autoconf(void)
>  			case no:
>  				break;
>  			case mod:
> -				fprintf(out, "CONFIG_%s=m\n", sym->name);
> +				fprintf2(out, out2, "CONFIG_%s=m\n",
> +						sym->name);
>  				fprintf(out_h, "#define CONFIG_%s_MODULE 1\n", sym->name);
>  				break;
>  			case yes:
>  				fprintf(out, "CONFIG_%s=y\n", sym->name);
> +				fprintf(out2, "CONFIG_%s=%c\n", sym->name,
> +					sym->type == S_BOOLEAN ? 'y' : 'Y');
>  				fprintf(out_h, "#define CONFIG_%s 1\n", sym->name);
>  				break;
>  			}
>  			break;
>  		case S_STRING:
>  			str = sym_get_string_value(sym);
> -			fprintf(out, "CONFIG_%s=\"", sym->name);
> +			fprintf2(out, out2, "CONFIG_%s=\"", sym->name);
>  			fprintf(out_h, "#define CONFIG_%s \"", sym->name);
>  			while (1) {
>  				l = strcspn(str, "\"\\");
>  				if (l) {
>  					fwrite(str, l, 1, out);
> +					fwrite(str, l, 1, out2);
>  					fwrite(str, l, 1, out_h);
>  					str += l;
>  				}
>  				if (!*str)
>  					break;
> -				fprintf(out, "\\%c", *str);
> +				fprintf2(out, out2, "\\%c", *str);
>  				fprintf(out_h, "\\%c", *str);
>  				str++;
>  			}
>  			fputs("\"\n", out);
> +			fputs("\"\n", out2);
>  			fputs("\"\n", out_h);
>  			break;
>  		case S_HEX:
>  			str = sym_get_string_value(sym);
>  			if (str[0] != '0' || (str[1] != 'x' && str[1] != 'X')) {
> -				fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
> +				fprintf2(out, out2, "CONFIG_%s=%s\n",
> +						sym->name, str);
>  				fprintf(out_h, "#define CONFIG_%s 0x%s\n", sym->name, str);
>  				break;
>  			}
>  		case S_INT:
>  			str = sym_get_string_value(sym);
> -			fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
> +			fprintf2(out, out2, "CONFIG_%s=%s\n", sym->name, str);
>  			fprintf(out_h, "#define CONFIG_%s %s\n", sym->name, str);
>  			break;
>  		default:
> @@ -772,6 +800,7 @@ int conf_write_autoconf(void)
>  		}
>  	}
>  	fclose(out);
> +	fclose(out2);
>  	fclose(out_h);
>  
>  	name = getenv("KCONFIG_AUTOHEADER");
> @@ -779,6 +808,11 @@ int conf_write_autoconf(void)
>  		name = "include/linux/autoconf.h";
>  	if (rename(".tmpconfig.h", name))
>  		return 1;
> +	name = getenv("KCONFIG_AUTOCONFIG2");
> +	if (!name)
> +		name = "include/config/auto2.conf";
> +	if (rename(".tmpconfig2", name))
> +		return 1;
>  	name = conf_get_autoconfig_name();
>  	/*
>  	 * This must be the last step, kbuild has a dependency on auto.conf
-- 
Scott James Remnant
scott@ubuntu.com

[-- Attachment #2: This is a digitally signed message part --]
[-- Type: application/pgp-signature, Size: 197 bytes --]

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-07-15 16:39   ` Scott James Remnant
@ 2009-07-15 16:46     ` Kay Sievers
  2009-07-15 18:04       ` Andreas Robinson
  0 siblings, 1 reply; 10+ messages in thread
From: Kay Sievers @ 2009-07-15 16:46 UTC (permalink / raw)
  To: Scott James Remnant
  Cc: Michal Marek, linux-modules, Sam Ravnborg, linux-kbuild,
	linux-kernel

Sam, any objections, or a chance to take this through your tree? It
solves an old problem with module-init-tools and we would like to
teach m-i-t about it, which means it should be in -next at least.

Thanks,
Kay

On Wed, Jul 15, 2009 at 18:39, Scott James Remnant<scott@ubuntu.com> wrote:
> Still would definitely like - adding linux-modules to the Cc
>
> On Fri, 2009-07-03 at 16:45 +0200, Michal Marek wrote:
>
>> On Tue, May 26, 2009 at 05:25:40PM +0200, Michal Marek wrote:
>> > Known issues (found when comparing results with allyesconfig and
>> > allmodconfig):
>> >  * ALSA makefiles do some substitutions on the CONFIG_*
>> >    variables sometimes, which breaks the logic if the alsa modules are
>> >    built-in. Patch sent to alsa-devel.
>> >  * samples/kobject/*.o could be compiled built-in, but doesn't show up
>> >    in modules.builtin (and not even in vmlinux.o). Patch sent to Greg to
>> >    make it module-only.
>>
>> These two are merged already.
>>
>>
>> >  * net/{8021q/vlan_core,ethernet/pe2,ipv6/inet6_hashtables}.o are always
>> >    built-in, even though the corresponding config option is tristate:
>> >    obj-$(subst m,y,$(CONFIG_IPX)) += pe2.o
>> >    The result is that modules.builtin can contain three built-in
>> >    "modules" that can't possibly exist as modules. No fix for this so far,
>> >    as it is not a big issue IMO.
>>
>> I hope this one is not a problem.
>>
>> I rebased the patch on top of current kbuild-next.git. What do you think
>> about it? Do you agree on the modules.builtin file name and format? I'd
>> like to add support for this to module-init-tools.
>>
>>
>> Subject: [PATCH] kbuild: generate modules.builtin
>>
>> To make it easier for tools like mkinitrd to detect whether a needed
>> module is missing or whether it is compiled into the kernel, install a
>> modules.builtin file listing all modules built into the kernel. This is
>> done by generating an alternate config file with all tristate =y options
>> set to =Y and reading the makefiles with this config included. The built
>> in modules then appear in obj-Y.
>>
>> Signed-off-by: Michal Marek <mmarek@suse.cz>
>> ---
>>  .gitignore                  |    1 +
>>  Makefile                    |   14 +++++++++---
>>  scripts/Kbuild.include      |    6 +++++
>>  scripts/Makefile.lib        |    5 +++-
>>  scripts/Makefile.modbuiltin |   48 +++++++++++++++++++++++++++++++++++++++++++
>>  scripts/kconfig/confdata.c  |   48 ++++++++++++++++++++++++++++++++++++------
>>  6 files changed, 110 insertions(+), 12 deletions(-)
>>  create mode 100644 scripts/Makefile.modbuiltin
>>
>> diff --git a/.gitignore b/.gitignore
>> index cecb3b0..d8c1e79 100644
>> --- a/.gitignore
>> +++ b/.gitignore
>> @@ -22,6 +22,7 @@
>>  *.lst
>>  *.symtypes
>>  *.order
>> +modules.builtin
>>  *.elf
>>  *.bin
>>  *.gz
>> diff --git a/Makefile b/Makefile
>> index 46e1c9d..c59e167 100644
>> --- a/Makefile
>> +++ b/Makefile
>> @@ -871,6 +871,9 @@ $(sort $(vmlinux-init) $(vmlinux-main)) $(vmlinux-lds): $(vmlinux-dirs) ;
>>  PHONY += $(vmlinux-dirs)
>>  $(vmlinux-dirs): prepare scripts
>>       $(Q)$(MAKE) $(build)=$@
>> +ifdef CONFIG_MODULES
>> +     $(Q)$(MAKE) $(modbuiltin)=$@
>> +endif
>>
>>  # Build the kernel release string
>>  #
>> @@ -1126,6 +1129,7 @@ all: modules
>>  PHONY += modules
>>  modules: $(vmlinux-dirs) $(if $(KBUILD_BUILTIN),vmlinux)
>>       $(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.order) > $(objtree)/modules.order
>> +     $(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.builtin) > $(objtree)/modules.builtin
>>       @$(kecho) '  Building modules, stage 2.';
>>       $(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modpost
>>       $(Q)$(MAKE) -f $(srctree)/scripts/Makefile.fwinst obj=firmware __fw_modbuild
>> @@ -1154,7 +1158,7 @@ _modinst_:
>>               rm -f $(MODLIB)/build ; \
>>               ln -s $(objtree) $(MODLIB)/build ; \
>>       fi
>> -     @cp -f $(objtree)/modules.order $(MODLIB)/
>> +     @cp -f $(objtree)/modules.{order,builtin} $(MODLIB)/
>>       $(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modinst
>>
>>  # This depmod is only for convenience to give the initial
>> @@ -1217,8 +1221,9 @@ clean: archclean $(clean-dirs)
>>               \( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \
>>               -o -name '.*.d' -o -name '.*.tmp' -o -name '*.mod.c' \
>>               -o -name '*.symtypes' -o -name 'modules.order' \
>> -             -o -name 'Module.markers' -o -name '.tmp_*.o.*' \
>> -             -o -name '*.gcno' \) -type f -print | xargs rm -f
>> +             -o -name 'modules.builtin' -o -name 'Module.markers' \
>> +             -o -name '.tmp_*.o.*' -o -name '*.gcno' \) \
>> +             -type f -print | xargs rm -f
>>
>>  # mrproper - Delete all generated files, including .config
>>  #
>> @@ -1416,7 +1421,8 @@ $(clean-dirs):
>>  clean:       rm-dirs := $(MODVERDIR)
>>  clean: rm-files := $(KBUILD_EXTMOD)/Module.symvers \
>>                     $(KBUILD_EXTMOD)/Module.markers \
>> -                   $(KBUILD_EXTMOD)/modules.order
>> +                   $(KBUILD_EXTMOD)/modules.order \
>> +                   $(KBUILD_EXTMOD)/modules.builtin
>>  clean: $(clean-dirs)
>>       $(call cmd,rmdirs)
>>       $(call cmd,rmfiles)
>> diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include
>> index c29be8f..1cded3b 100644
>> --- a/scripts/Kbuild.include
>> +++ b/scripts/Kbuild.include
>> @@ -143,6 +143,12 @@ ld-option = $(call try-run,\
>>  # $(Q)$(MAKE) $(build)=dir
>>  build := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.build obj
>>
>> +###
>> +# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.modbuiltin obj=
>> +# Usage:
>> +# $(Q)$(MAKE) $(modbuiltin)=dir
>> +modbuiltin := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.modbuiltin obj
>> +
>>  # Prefix -I with $(srctree) if it is not an absolute path.
>>  # skip if -I has no parameter
>>  addtree = $(if $(patsubst -I%,%,$(1)), \
>> diff --git a/scripts/Makefile.lib b/scripts/Makefile.lib
>> index 7a77787..3525b29 100644
>> --- a/scripts/Makefile.lib
>> +++ b/scripts/Makefile.lib
>> @@ -37,6 +37,8 @@ modorder    := $(patsubst %/,%/modules.order, $(filter %/, $(obj-y)) $(obj-m:.o=.ko
>>
>>  __subdir-y   := $(patsubst %/,%,$(filter %/, $(obj-y)))
>>  subdir-y     += $(__subdir-y)
>> +__subdir-Y   := $(patsubst %/,%,$(filter %/, $(obj-Y)))
>> +subdir-Y     += $(__subdir-Y)
>>  __subdir-m   := $(patsubst %/,%,$(filter %/, $(obj-m)))
>>  subdir-m     += $(__subdir-m)
>>  obj-y                := $(patsubst %/, %/built-in.o, $(obj-y))
>> @@ -44,7 +46,7 @@ obj-m               := $(filter-out %/, $(obj-m))
>>
>>  # Subdirectories we need to descend into
>>
>> -subdir-ym    := $(sort $(subdir-y) $(subdir-m))
>> +subdir-ym    := $(sort $(subdir-y) $(subdir-Y) $(subdir-m))
>>
>>  # if $(foo-objs) exists, foo.o is a composite object
>>  multi-used-y := $(sort $(foreach m,$(obj-y), $(if $(strip $($(m:.o=-objs)) $($(m:.o=-y))), $(m))))
>> @@ -76,6 +78,7 @@ always              := $(addprefix $(obj)/,$(always))
>>  targets              := $(addprefix $(obj)/,$(targets))
>>  modorder     := $(addprefix $(obj)/,$(modorder))
>>  obj-y                := $(addprefix $(obj)/,$(obj-y))
>> +obj-Y                := $(addprefix $(obj)/,$(obj-Y))
>>  obj-m                := $(addprefix $(obj)/,$(obj-m))
>>  lib-y                := $(addprefix $(obj)/,$(lib-y))
>>  subdir-obj-y := $(addprefix $(obj)/,$(subdir-obj-y))
>> diff --git a/scripts/Makefile.modbuiltin b/scripts/Makefile.modbuiltin
>> new file mode 100644
>> index 0000000..55e1885
>> --- /dev/null
>> +++ b/scripts/Makefile.modbuiltin
>> @@ -0,0 +1,48 @@
>> +# ==========================================================================
>> +# Generating modules.builtin
>> +# ==========================================================================
>> +
>> +src := $(obj)
>> +
>> +PHONY := __modbuiltin
>> +__modbuiltin:
>> +
>> +# Read auto2.conf which sets tristate variables to 'Y' instead of 'y'
>> +# That way, we get the list of built-in modules in obj-Y
>> +-include include/config/auto2.conf
>> +
>> +include scripts/Kbuild.include
>> +
>> +# The filename Kbuild has precedence over Makefile
>> +kbuild-dir := $(if $(filter /%,$(src)),$(src),$(srctree)/$(src))
>> +kbuild-file := $(if $(wildcard $(kbuild-dir)/Kbuild),$(kbuild-dir)/Kbuild,$(kbuild-dir)/Makefile)
>> +include $(kbuild-file)
>> +
>> +include scripts/Makefile.lib
>> +
>> +modbuiltin-subdirs := $(patsubst %,%/modules.builtin, $(subdir-ym))
>> +modbuiltin-mods    := $(filter %.ko, $(obj-Y:.o=.ko))
>> +modbuiltin-target  := $(obj)/modules.builtin
>> +
>> +__modbuiltin: $(modbuiltin-target) $(subdir-ym)
>> +     @:
>> +
>> +modbuiltin-cmds =                                            \
>> +     for m in $(modbuiltin-mods); do echo kernel/$$m; done;  \
>> +     cat /dev/null $(modbuiltin-subdirs);
>> +
>> +$(modbuiltin-target): $(subdir-ym)
>> +     $(Q)($(modbuiltin-cmds)) > $@
>> +
>> +# Descending
>> +# ---------------------------------------------------------------------------
>> +
>> +PHONY += $(subdir-ym)
>> +$(subdir-ym):
>> +     $(Q)$(MAKE) $(modbuiltin)=$@
>> +
>> +
>> +# Declare the contents of the .PHONY variable as phony.  We keep that
>> +# information in a variable se we can use it in if_changed and friends.
>> +
>> +.PHONY: $(PHONY)
>> diff --git a/scripts/kconfig/confdata.c b/scripts/kconfig/confdata.c
>> index a04da34..8e2c166 100644
>> --- a/scripts/kconfig/confdata.c
>> +++ b/scripts/kconfig/confdata.c
>> @@ -672,12 +672,27 @@ out:
>>       return res;
>>  }
>>
>> +int fprintf2(FILE *f1, FILE *f2, const char *fmt, ...)
>> +{
>> +     va_list ap;
>> +     int res;
>> +
>> +     va_start(ap, fmt);
>> +     vfprintf(f1, fmt, ap);
>> +     va_end(ap);
>> +     va_start(ap, fmt);
>> +     res = vfprintf(f2, fmt, ap);
>> +     va_end(ap);
>> +
>> +     return res;
>> +}
>> +
>>  int conf_write_autoconf(void)
>>  {
>>       struct symbol *sym;
>>       const char *str;
>>       const char *name;
>> -     FILE *out, *out_h;
>> +     FILE *out, *out2, *out_h;
>>       time_t now;
>>       int i, l;
>>
>> @@ -692,16 +707,23 @@ int conf_write_autoconf(void)
>>       if (!out)
>>               return 1;
>>
>> +     out2 = fopen(".tmpconfig2", "w");
>> +     if (!out2) {
>> +             fclose(out);
>> +             return 1;
>> +     }
>> +
>>       out_h = fopen(".tmpconfig.h", "w");
>>       if (!out_h) {
>>               fclose(out);
>> +             fclose(out2);
>>               return 1;
>>       }
>>
>>       sym = sym_lookup("KERNELVERSION", 0);
>>       sym_calc_value(sym);
>>       time(&now);
>> -     fprintf(out, "#\n"
>> +     fprintf2(out, out2, "#\n"
>>                    "# Automatically generated make config: don't edit\n"
>>                    "# Linux kernel version: %s\n"
>>                    "# %s"
>> @@ -726,45 +748,51 @@ int conf_write_autoconf(void)
>>                       case no:
>>                               break;
>>                       case mod:
>> -                             fprintf(out, "CONFIG_%s=m\n", sym->name);
>> +                             fprintf2(out, out2, "CONFIG_%s=m\n",
>> +                                             sym->name);
>>                               fprintf(out_h, "#define CONFIG_%s_MODULE 1\n", sym->name);
>>                               break;
>>                       case yes:
>>                               fprintf(out, "CONFIG_%s=y\n", sym->name);
>> +                             fprintf(out2, "CONFIG_%s=%c\n", sym->name,
>> +                                     sym->type == S_BOOLEAN ? 'y' : 'Y');
>>                               fprintf(out_h, "#define CONFIG_%s 1\n", sym->name);
>>                               break;
>>                       }
>>                       break;
>>               case S_STRING:
>>                       str = sym_get_string_value(sym);
>> -                     fprintf(out, "CONFIG_%s=\"", sym->name);
>> +                     fprintf2(out, out2, "CONFIG_%s=\"", sym->name);
>>                       fprintf(out_h, "#define CONFIG_%s \"", sym->name);
>>                       while (1) {
>>                               l = strcspn(str, "\"\\");
>>                               if (l) {
>>                                       fwrite(str, l, 1, out);
>> +                                     fwrite(str, l, 1, out2);
>>                                       fwrite(str, l, 1, out_h);
>>                                       str += l;
>>                               }
>>                               if (!*str)
>>                                       break;
>> -                             fprintf(out, "\\%c", *str);
>> +                             fprintf2(out, out2, "\\%c", *str);
>>                               fprintf(out_h, "\\%c", *str);
>>                               str++;
>>                       }
>>                       fputs("\"\n", out);
>> +                     fputs("\"\n", out2);
>>                       fputs("\"\n", out_h);
>>                       break;
>>               case S_HEX:
>>                       str = sym_get_string_value(sym);
>>                       if (str[0] != '0' || (str[1] != 'x' && str[1] != 'X')) {
>> -                             fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
>> +                             fprintf2(out, out2, "CONFIG_%s=%s\n",
>> +                                             sym->name, str);
>>                               fprintf(out_h, "#define CONFIG_%s 0x%s\n", sym->name, str);
>>                               break;
>>                       }
>>               case S_INT:
>>                       str = sym_get_string_value(sym);
>> -                     fprintf(out, "CONFIG_%s=%s\n", sym->name, str);
>> +                     fprintf2(out, out2, "CONFIG_%s=%s\n", sym->name, str);
>>                       fprintf(out_h, "#define CONFIG_%s %s\n", sym->name, str);
>>                       break;
>>               default:
>> @@ -772,6 +800,7 @@ int conf_write_autoconf(void)
>>               }
>>       }
>>       fclose(out);
>> +     fclose(out2);
>>       fclose(out_h);
>>
>>       name = getenv("KCONFIG_AUTOHEADER");
>> @@ -779,6 +808,11 @@ int conf_write_autoconf(void)
>>               name = "include/linux/autoconf.h";
>>       if (rename(".tmpconfig.h", name))
>>               return 1;
>> +     name = getenv("KCONFIG_AUTOCONFIG2");
>> +     if (!name)
>> +             name = "include/config/auto2.conf";
>> +     if (rename(".tmpconfig2", name))
>> +             return 1;
>>       name = conf_get_autoconfig_name();
>>       /*
>>        * This must be the last step, kbuild has a dependency on auto.conf
> --
> Scott James Remnant
> scott@ubuntu.com
>

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-07-15 16:46     ` Kay Sievers
@ 2009-07-15 18:04       ` Andreas Robinson
  2009-07-15 19:08         ` Michal Marek
  0 siblings, 1 reply; 10+ messages in thread
From: Andreas Robinson @ 2009-07-15 18:04 UTC (permalink / raw)
  To: Kay Sievers
  Cc: Scott James Remnant, Michal Marek, linux-modules, Sam Ravnborg,
	linux-kbuild, linux-kernel

[-- Attachment #1: Type: text/plain, Size: 201 bytes --]

Guys,

is this patch what you need on the m-i-t end?

(Sorry for sending it as an attachment. I'm restricted to webmail at
the moment and can't prevent gmail from adding line breaks.)

Cheers,
Andreas

[-- Attachment #2: check_modules_builtin.patch --]
[-- Type: text/x-patch, Size: 2543 bytes --]

From d60a4a56f5d484a6076c606a111510ce40a4ccd8 Mon Sep 17 00:00:00 2001
From: Andreas Robinson <andr345@gmail.com>
Date: Wed, 15 Jul 2009 19:48:59 +0200
Subject: [PATCH] modprobe: warn when trying to insert a built-in module

The previous behaviour was to fail with "module foo not found".

Signed-off-by: Andreas Robinson <andr345@gmail.com>
---
 modprobe.c |   34 ++++++++++++++++++++++++++++++++--
 1 files changed, 32 insertions(+), 2 deletions(-)

diff --git a/modprobe.c b/modprobe.c
index 21a3111..a0943fe 100644
--- a/modprobe.c
+++ b/modprobe.c
@@ -1049,6 +1049,29 @@ static char *gather_options(char *argv[])
 	return optstring;
 }
 
+/* Check whether a module is built into the kernel */
+static int is_builtin(const char *modname, const char *dirname)
+{
+	char *filename;
+	FILE *file;
+	char *line;
+	int found = 0;
+
+	nofail_asprintf(&filename, "%s/modules.builtin", dirname);
+	file = fopen(filename, "r");
+	if (file) {
+		while ((line = getline_wrapped(file, NULL)) != NULL && !found) {
+			char *p = line;
+			char *builtin = underscores(strsep_skipspace(&p, "\t "));
+			found = streq(modname, builtin);
+			free(line);
+		}
+		fclose(file);
+	}
+	free(filename);
+	return found;
+}
+
 /* Do an install/remove command: replace $CMDLINE_OPTS if it's specified. */
 static void do_command(const char *modname,
 		       const char *command,
@@ -1256,6 +1279,7 @@ static int handle_module(const char *modname,
 			  struct module_options *modoptions,
 			  struct module_command *commands,
 			  const char *cmdline_opts,
+			  const char *dirname,
 			  errfn_t error,
 			  modprobe_flags_t flags)
 {
@@ -1271,6 +1295,11 @@ static int handle_module(const char *modname,
 			return 0;
 		}
 
+		if (is_builtin(modname, dirname)) {
+			warn("Module %s is built into the kernel.\n", modname);
+			return 0;
+		}
+
 		if (!quiet)
 			error("Module %s not found.\n", modname);
 		return 1;
@@ -1350,7 +1379,7 @@ int do_modprobe(char *modname,
 			read_depends(dirname, aliases->module, &list);
 			failed |= handle_module(aliases->module,
 				&list, newname, opts, modoptions,
-				commands, cmdline_opts, err, flags);
+				commands, cmdline_opts, dirname, err, flags);
 
 			aliases = aliases->next;
 			INIT_LIST_HEAD(&list);
@@ -1361,7 +1390,8 @@ int do_modprobe(char *modname,
 			return failed;
 
 		failed |= handle_module(modname, &list, newname, cmdline_opts,
-			modoptions, commands, cmdline_opts, error, flags);
+			modoptions, commands, cmdline_opts, dirname, error,
+			flags);
 	}
 	return failed;
 }
-- 
1.6.0.4


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-07-15 18:04       ` Andreas Robinson
@ 2009-07-15 19:08         ` Michal Marek
  2009-07-15 20:12           ` Andreas Robinson
  0 siblings, 1 reply; 10+ messages in thread
From: Michal Marek @ 2009-07-15 19:08 UTC (permalink / raw)
  To: Andreas Robinson
  Cc: Kay Sievers, Scott James Remnant, linux-modules, Sam Ravnborg,
	linux-kbuild, linux-kernel

Andreas Robinson napsal(a):
> Guys,
> 
> is this patch what you need on the m-i-t end?

I already have patches here (it's not against Jon's master, but it
should apply):
http://repo.or.cz/w/mit.git?a=commit;h=45c29de1b54478a63352a3f13c570a964903f54f
http://repo.or.cz/w/mit.git?a=commit;h=0e72912a1e0b486225f7052c8d40e28b07ff4495

The idea is that modprobe should just do nothing and exit successfully,
so that scripts don't break nor start printing warnings if the kernel
config changes. I meant to send it to linux-modules once there is
agreement about the modules.builtin file format.

Michal

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-07-15 19:08         ` Michal Marek
@ 2009-07-15 20:12           ` Andreas Robinson
  2009-07-15 20:16             ` Michal Marek
  0 siblings, 1 reply; 10+ messages in thread
From: Andreas Robinson @ 2009-07-15 20:12 UTC (permalink / raw)
  To: Michal Marek
  Cc: Kay Sievers, Scott James Remnant, linux-modules, Sam Ravnborg,
	linux-kbuild, linux-kernel

On Wed, Jul 15, 2009 at 9:08 PM, Michal Marek<mmarek@suse.cz> wrote:
> Andreas Robinson napsal(a):
>> Guys,
>>
>> is this patch what you need on the m-i-t end?
>
> I already have patches here (it's not against Jon's master, but it
> should apply):
> http://repo.or.cz/w/mit.git?a=commit;h=45c29de1b54478a63352a3f13c570a964903f54f
> http://repo.or.cz/w/mit.git?a=commit;h=0e72912a1e0b486225f7052c8d40e28b07ff4495

Ah, of course!

> The idea is that modprobe should just do nothing and exit successfully,
> so that scripts don't break nor start printing warnings if the kernel
> config changes. I meant to send it to linux-modules once there is
> agreement about the modules.builtin file format.

Ok, that makes sense.

I think there's a small chance of confusion though, when a user tries
to insert a module and it doesn't show up with lsmod. Perhaps you can
add an info() message? Then the user can figure out what is happening
with the --verbose option.

Andreas

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH] kbuild: generate modules.builtin
  2009-07-15 20:12           ` Andreas Robinson
@ 2009-07-15 20:16             ` Michal Marek
  0 siblings, 0 replies; 10+ messages in thread
From: Michal Marek @ 2009-07-15 20:16 UTC (permalink / raw)
  To: Andreas Robinson
  Cc: Kay Sievers, Scott James Remnant, linux-modules, Sam Ravnborg,
	linux-kbuild, linux-kernel

Andreas Robinson napsal(a):
> On Wed, Jul 15, 2009 at 9:08 PM, Michal Marek<mmarek@suse.cz> wrote:
>> The idea is that modprobe should just do nothing and exit successfully,
>> so that scripts don't break nor start printing warnings if the kernel
>> config changes. I meant to send it to linux-modules once there is
>> agreement about the modules.builtin file format.
> 
> Ok, that makes sense.
> 
> I think there's a small chance of confusion though, when a user tries
> to insert a module and it doesn't show up with lsmod. Perhaps you can
> add an info() message? Then the user can figure out what is happening
> with the --verbose option.

Good idea, will do that.

Michal

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH] kbuild: generate modules.builtin
@ 2009-09-25 15:13 Michal Marek
  0 siblings, 0 replies; 10+ messages in thread
From: Michal Marek @ 2009-09-25 15:13 UTC (permalink / raw)
  To: Sam Ravnborg; +Cc: Steven Rostedt, akpm, linux-kbuild

To make it easier for module-init-tools and scripts like mkinitrd to
distinguish builtin and missing modules, install a modules.builtin file
listing all builtin modules. This is done by generating an additional
config file (tristate.conf) with tristate options set to uppercase 'Y'
or 'M'. If we source that config file, the builtin modules appear in
obj-Y.

Signed-off-by: Michal Marek <mmarek@suse.cz>
---
 .gitignore                       |    1 +
 Documentation/kbuild/kbuild.txt  |   14 +++++++++
 Documentation/kbuild/kconfig.txt |    5 +++
 Makefile                         |   17 ++++++++---
 scripts/Kbuild.include           |    6 ++++
 scripts/Makefile.modbuiltin      |   55 ++++++++++++++++++++++++++++++++++++++
 scripts/kconfig/confdata.c       |   21 ++++++++++++++-
 7 files changed, 113 insertions(+), 6 deletions(-)
 create mode 100644 scripts/Makefile.modbuiltin

diff --git a/.gitignore b/.gitignore
index b93fb7e..5835867 100644
--- a/.gitignore
+++ b/.gitignore
@@ -22,6 +22,7 @@
 *.lst
 *.symtypes
 *.order
+modules.builtin
 *.elf
 *.bin
 *.gz
diff --git a/Documentation/kbuild/kbuild.txt b/Documentation/kbuild/kbuild.txt
index bb3bf38..6f8c1ca 100644
--- a/Documentation/kbuild/kbuild.txt
+++ b/Documentation/kbuild/kbuild.txt
@@ -1,3 +1,17 @@
+Output files
+
+modules.order
+--------------------------------------------------
+This file records the order in which modules appear in Makefiles. This
+is used by modprobe to deterministically resolve aliases that match
+multiple modules.
+
+modules.builtin
+--------------------------------------------------
+This file lists all modules that are built into the kernel. This is used
+by modprobe to not fail when trying to load something builtin.
+
+
 Environment variables
 
 KCPPFLAGS
diff --git a/Documentation/kbuild/kconfig.txt b/Documentation/kbuild/kconfig.txt
index 849b5e5..40f0797 100644
--- a/Documentation/kbuild/kconfig.txt
+++ b/Documentation/kbuild/kconfig.txt
@@ -103,6 +103,11 @@ KCONFIG_AUTOCONFIG
 This environment variable can be set to specify the path & name of the
 "auto.conf" file.  Its default value is "include/config/auto.conf".
 
+KCONFIG_TRISTATE
+--------------------------------------------------
+This environment variable can be set to specify the path & name of the
+"tristate.conf" file.  Its default value is "include/config/tristate.conf".
+
 KCONFIG_AUTOHEADER
 --------------------------------------------------
 This environment variable can be set to specify the path & name of the
diff --git a/Makefile b/Makefile
index f908acc..2e7d1cc 100644
--- a/Makefile
+++ b/Makefile
@@ -506,7 +506,7 @@ ifeq ($(KBUILD_EXTMOD),)
 # Carefully list dependencies so we do not try to build scripts twice
 # in parallel
 PHONY += scripts
-scripts: scripts_basic include/config/auto.conf
+scripts: scripts_basic include/config/auto.conf include/config/tristate.conf
 	$(Q)$(MAKE) $(build)=$(@)
 
 # Objects we will link into vmlinux / subdirs we need to visit
@@ -533,7 +533,7 @@ $(KCONFIG_CONFIG) include/config/auto.conf.cmd: ;
 # with it and forgot to run make oldconfig.
 # if auto.conf.cmd is missing then we are probably in a cleaned tree so
 # we execute the config step to be sure to catch updated Kconfig files
-include/config/auto.conf: $(KCONFIG_CONFIG) include/config/auto.conf.cmd
+include/config/%.conf: $(KCONFIG_CONFIG) include/config/auto.conf.cmd
 	$(Q)$(MAKE) -f $(srctree)/Makefile silentoldconfig
 else
 # external modules needs include/linux/autoconf.h and include/config/auto.conf
@@ -918,6 +918,9 @@ $(sort $(vmlinux-init) $(vmlinux-main)) $(vmlinux-lds): $(vmlinux-dirs) ;
 PHONY += $(vmlinux-dirs)
 $(vmlinux-dirs): prepare scripts
 	$(Q)$(MAKE) $(build)=$@
+ifdef CONFIG_MODULES
+	$(Q)$(MAKE) $(modbuiltin)=$@
+endif
 
 # Build the kernel release string
 #
@@ -1168,6 +1171,7 @@ all: modules
 PHONY += modules
 modules: $(vmlinux-dirs) $(if $(KBUILD_BUILTIN),vmlinux)
 	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.order) > $(objtree)/modules.order
+	$(Q)$(AWK) '!x[$$0]++' $(vmlinux-dirs:%=$(objtree)/%/modules.builtin) > $(objtree)/modules.builtin
 	@$(kecho) '  Building modules, stage 2.';
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modpost
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.fwinst obj=firmware __fw_modbuild
@@ -1197,6 +1201,7 @@ _modinst_:
 		ln -s $(objtree) $(MODLIB)/build ; \
 	fi
 	@cp -f $(objtree)/modules.order $(MODLIB)/
+	@cp -f $(objtree)/modules.builtin $(MODLIB)/
 	$(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modinst
 
 # This depmod is only for convenience to give the initial
@@ -1259,8 +1264,9 @@ clean: archclean $(clean-dirs)
 		\( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \
 		-o -name '.*.d' -o -name '.*.tmp' -o -name '*.mod.c' \
 		-o -name '*.symtypes' -o -name 'modules.order' \
-		-o -name 'Module.markers' -o -name '.tmp_*.o.*' \
-		-o -name '*.gcno' \) -type f -print | xargs rm -f
+		-o -name 'modules.builtin' -o -name 'Module.markers' \
+		-o -name '.tmp_*.o.*' -o -name '*.gcno' \) \
+		-type f -print | xargs rm -f
 
 # mrproper - Delete all generated files, including .config
 #
@@ -1458,7 +1464,8 @@ $(clean-dirs):
 clean:	rm-dirs := $(MODVERDIR)
 clean: rm-files := $(KBUILD_EXTMOD)/Module.symvers \
                    $(KBUILD_EXTMOD)/Module.markers \
-                   $(KBUILD_EXTMOD)/modules.order
+                   $(KBUILD_EXTMOD)/modules.order \
+                   $(KBUILD_EXTMOD)/modules.builtin
 clean: $(clean-dirs)
 	$(call cmd,rmdirs)
 	$(call cmd,rmfiles)
diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include
index 4f9c190..dd641e1 100644
--- a/scripts/Kbuild.include
+++ b/scripts/Kbuild.include
@@ -149,6 +149,12 @@ ld-option = $(call try-run,\
 # $(Q)$(MAKE) $(build)=dir
 build := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.build obj
 
+###
+# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.modbuiltin obj=
+# Usage:
+# $(Q)$(MAKE) $(modbuiltin)=dir
+modbuiltin := -f $(if $(KBUILD_SRC),$(srctree)/)scripts/Makefile.modbuiltin obj
+
 # Prefix -I with $(srctree) if it is not an absolute path.
 # skip if -I has no parameter
 addtree = $(if $(patsubst -I%,%,$(1)), \
diff --git a/scripts/Makefile.modbuiltin b/scripts/Makefile.modbuiltin
new file mode 100644
index 0000000..102a276
--- /dev/null
+++ b/scripts/Makefile.modbuiltin
@@ -0,0 +1,55 @@
+# ==========================================================================
+# Generating modules.builtin
+# ==========================================================================
+
+src := $(obj)
+
+PHONY := __modbuiltin
+__modbuiltin:
+
+-include include/config/auto.conf
+# tristate.conf sets tristate variables to uppercase 'Y' or 'M'
+# That way, we get the list of built-in modules in obj-Y
+-include include/config/tristate.conf
+
+include scripts/Kbuild.include
+
+# The filename Kbuild has precedence over Makefile
+kbuild-dir := $(if $(filter /%,$(src)),$(src),$(srctree)/$(src))
+kbuild-file := $(if $(wildcard $(kbuild-dir)/Kbuild),$(kbuild-dir)/Kbuild,$(kbuild-dir)/Makefile)
+include $(kbuild-file)
+
+include scripts/Makefile.lib
+__subdir-Y     := $(patsubst %/,%,$(filter %/, $(obj-Y)))
+subdir-Y       += $(__subdir-Y)
+subdir-ym      := $(sort $(subdir-y) $(subdir-Y) $(subdir-m))
+subdir-ym      := $(addprefix $(obj)/,$(subdir-ym))
+obj-Y          := $(addprefix $(obj)/,$(obj-Y))
+
+modbuiltin-subdirs := $(patsubst %,%/modules.builtin, $(subdir-ym))
+modbuiltin-mods    := $(filter %.ko, $(obj-Y:.o=.ko))
+modbuiltin-target  := $(obj)/modules.builtin
+
+__modbuiltin: $(modbuiltin-target) $(subdir-ym)
+	@:
+
+$(modbuiltin-target): $(subdir-ym) FORCE
+	$(Q)(for m in $(modbuiltin-mods); do echo kernel/$$m; done;	\
+	cat /dev/null $(modbuiltin-subdirs)) > $@
+
+PHONY += FORCE
+
+FORCE:
+
+# Descending
+# ---------------------------------------------------------------------------
+
+PHONY += $(subdir-ym)
+$(subdir-ym):
+	$(Q)$(MAKE) $(modbuiltin)=$@
+
+
+# Declare the contents of the .PHONY variable as phony.  We keep that
+# information in a variable se we can use it in if_changed and friends.
+
+.PHONY: $(PHONY)
diff --git a/scripts/kconfig/confdata.c b/scripts/kconfig/confdata.c
index b55e72f..94721f2 100644
--- a/scripts/kconfig/confdata.c
+++ b/scripts/kconfig/confdata.c
@@ -677,7 +677,7 @@ int conf_write_autoconf(void)
 	struct symbol *sym;
 	const char *str;
 	const char *name;
-	FILE *out, *out_h;
+	FILE *out, *tristate, *out_h;
 	time_t now;
 	int i, l;
 
@@ -692,9 +692,16 @@ int conf_write_autoconf(void)
 	if (!out)
 		return 1;
 
+	tristate = fopen(".tmpconfig_tristate", "w");
+	if (!tristate) {
+		fclose(out);
+		return 1;
+	}
+
 	out_h = fopen(".tmpconfig.h", "w");
 	if (!out_h) {
 		fclose(out);
+		fclose(tristate);
 		return 1;
 	}
 
@@ -707,6 +714,9 @@ int conf_write_autoconf(void)
 		     "# %s"
 		     "#\n",
 		     sym_get_string_value(sym), ctime(&now));
+	fprintf(tristate, "#\n"
+	                  "# Automatically generated - do not edit\n"
+	                  "\n");
 	fprintf(out_h, "/*\n"
 		       " * Automatically generated C config: don't edit\n"
 		       " * Linux kernel version: %s\n"
@@ -727,10 +737,13 @@ int conf_write_autoconf(void)
 				break;
 			case mod:
 				fprintf(out, "CONFIG_%s=m\n", sym->name);
+				fprintf(tristate, "CONFIG_%s=M\n", sym->name);
 				fprintf(out_h, "#define CONFIG_%s_MODULE 1\n", sym->name);
 				break;
 			case yes:
 				fprintf(out, "CONFIG_%s=y\n", sym->name);
+				fprintf(tristate, "CONFIG_%s=%c\n", sym->name,
+					sym->type == S_BOOLEAN ? 'y' : 'Y');
 				fprintf(out_h, "#define CONFIG_%s 1\n", sym->name);
 				break;
 			}
@@ -772,6 +785,7 @@ int conf_write_autoconf(void)
 		}
 	}
 	fclose(out);
+	fclose(tristate);
 	fclose(out_h);
 
 	name = getenv("KCONFIG_AUTOHEADER");
@@ -779,6 +793,11 @@ int conf_write_autoconf(void)
 		name = "include/linux/autoconf.h";
 	if (rename(".tmpconfig.h", name))
 		return 1;
+	name = getenv("KCONFIG_TRISTATE");
+	if (!name)
+		name = "include/config/tristate.conf";
+	if (rename(".tmpconfig_tristate", name))
+		return 1;
 	name = conf_get_autoconfig_name();
 	/*
 	 * This must be the last step, kbuild has a dependency on auto.conf
-- 
1.6.3.3


^ permalink raw reply related	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2009-09-25 15:14 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-05-26 15:25 [PATCH] kbuild: generate modules.builtin Michal Marek
2009-05-27 21:26 ` Kay Sievers
2009-05-27 21:38   ` Scott James Remnant
     [not found] ` <20090703144547.GA20980@sepie.suse.cz>
2009-07-15 16:39   ` Scott James Remnant
2009-07-15 16:46     ` Kay Sievers
2009-07-15 18:04       ` Andreas Robinson
2009-07-15 19:08         ` Michal Marek
2009-07-15 20:12           ` Andreas Robinson
2009-07-15 20:16             ` Michal Marek
  -- strict thread matches above, loose matches on Subject: below --
2009-09-25 15:13 Michal Marek

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox