Dear Graeme Russ, > Signed-off-by: Graeme Russ <graeme.r...@gmail.com> > --- > Makefile | 34 ++- > common/Makefile | 2 + > config.mk | 2 + > doc/README.INIT_FUNC | 65 +++ > include/init_func.h | 37 ++ > tools/Makefile | 6 + > tools/mkinitseq.c | 1512 > ++++++++++++++++++++++++++++++++++++++++++++++++++ 7 files changed, 1657 > insertions(+), 1 deletions(-) > create mode 100644 doc/README.INIT_FUNC > create mode 100644 include/init_func.h > create mode 100644 tools/mkinitseq.c >
[...] > --- /dev/null > +++ b/doc/README.INIT_FUNC > @@ -0,0 +1,65 @@ > +The INIT_FUNC macro allows initialisation functions (i.e. functions which > are +executed before the main loop) to be easily added to the init > sequence + > + > +Specifying an Initialisation Function and is Dependencies > +--------------------------------------------------------- > +The format of the INIT_FUNC macro is: > + > +INIT_FUNC(fn, grp, man_reqs, pre_reqs, pst_reqs) > + > +fn is the name of the init function to call. This function must have the > +following prototype: > + > +int foo(void); What if I want to pass some data to such a func ? Clearly, I can think of this being doable, but extra hard. > + > +Each init function must return 0 to indicate success - any other return > value +indicates failure and the init sequence will stop > + > +grp is the name of the group that the init function belongs to. grp may be > +the same as fn for any individual init function, but between init > functions, +fn and grp must be unique. > + > +The purpose of groups is to allow functions to be grouped together so > other +functions can specify the group as a whole as a dependency rather > than having +to list every function in the group in the dependency list > + > +man_reqs is a space seperated list of functions or groups that MUST exist > and +MUST run BEFORE fn > + > +pre_reqs is a space seperated list of functions or groups that MAY exist > and +(if they do) MUST run BEFORE fn > + > +pst_reqs is a space seperated list of functions or groups that MAY exist > and +(if they do) MUST run AFTER fn What's the point? Can't you create a kind of proxy object that the pst_reqs will have as a pre_req ? Maybe you should create this: INIT_FUNC(fn, grp, prereqs, postreqs) and for each function from prereqs and postreqs, specify per-function attributes via the GCC __attribute__(()) directive, like if the function must run before something or may run before something etc? > + > +Skipping or Replacing a Function or Group > +----------------------------------------- > +Occassionally, a board may provide a completely seperate implementation > for +an initialisation function that is provided in the common arch, SoC > or +common code. > + > +SKIP_INIT(fn_or_group) > + > +After the initialisation function dependencies are calculated, all > functions +and groups listed in any SKIP_INITs are removed - This may > result in +dependent functions being removed - It is up to the board code > developer +to ensure suitable replacements are in place > + > +REPLACE_INIT(old_fn_or_group, new_fn_or_group) > + > +Like SKIP_INIT but replaces on function with another (or one group with > +another) > + > +Example: In the SoC code yoy may have Yoy :) > + > +INIT_FUNC(init_cpu_f, RESET, , , ); > + > +In the board code, you may want a slightly tweaked version, so you might > +have: > + > +int my_new_init_cpu_f(void) > +{ > + ... > +} > +REPLACE_INIT(init_cpu_f, my_new_init_cpu_f); > diff --git a/include/init_func.h b/include/init_func.h > new file mode 100644 > index 0000000..e4366b8 > --- /dev/null > +++ b/include/init_func.h > @@ -0,0 +1,37 @@ > +#ifndef __INIT_FUNC_H__ > +#define __INIT_FUNC_H__ > + > +/* > + * The requirements for any new initalization function is simple: it is > + * a function with no parameters which returns an integer return code, > + * where 0 means "continue" and != 0 means "fatal error, hang the system" > + */ > +typedef int (init_fnc_t) (void); > + > +extern init_fnc_t *init_sequence_f[]; > +extern init_fnc_t *init_sequence_f_r[]; > +extern init_fnc_t *init_sequence_r[]; > + > +#ifdef CONFIG_INIT_FUNC > +#include <linux/compiler.h> > + > +#define INIT_FUNC(fn, grp, man_reqs, pre_reqs, pst_reqs) \ > + static const char __init_func_ ## fn[] __used \ > + __attribute__((__section__(".initfuncs"))) = \ > + "(f:" #fn ":" #grp ":" #man_reqs " | " #pre_reqs " | " #pst_reqs ")\n"; > + > +#define SKIP_INIT(fn_or_group) \ > + static const char __skip_init_ ## fn_or_group[] __used \ > + __attribute__((__section__(".initfuncs"))) = \ > + "(s:" #fn_or_group ")\n"; > + > +#define REPLACE_INIT(old_fn_or_group, new_fn_or_group) \ > + static const char __replace_init_ ## old_fn_or_group[] __used \ > + __attribute__((__section__(".initfuncs"))) = \ > + "(r:" #old_fn_or_group ":" #new_fn_or_group ")\n"; > +#else > +#define INIT_FUNC(fn, group, man_reqs, pre_reqs, post_reqs) > +#define SKIP_INIT(fn_or_group) > +#define REPLACE_INIT(old_fn_or_group, new_fn_or_group) > +#endif > +#endif /* !__INIT_FUNC_H__ */ > diff --git a/tools/Makefile b/tools/Makefile > index 8993fdd..e6ba6ef 100644 > --- a/tools/Makefile > +++ b/tools/Makefile > @@ -68,6 +68,7 @@ BIN_FILES-$(CONFIG_CMD_LOADS) += img2srec$(SFX) > BIN_FILES-$(CONFIG_XWAY_SWAP_BYTES) += xway-swap-bytes$(SFX) > BIN_FILES-y += mkenvimage$(SFX) > BIN_FILES-y += mkimage$(SFX) > +BIN_FILES-$(CONFIG_INIT_FUNC) += mkinitseq$(SFX) > BIN_FILES-$(CONFIG_SMDK5250) += mksmdk5250spl$(SFX) > BIN_FILES-$(CONFIG_MX28) += mxsboot$(SFX) > BIN_FILES-$(CONFIG_NETCONSOLE) += ncb$(SFX) > @@ -95,6 +96,7 @@ NOPED_OBJ_FILES-y += imximage.o > NOPED_OBJ_FILES-y += omapimage.o > NOPED_OBJ_FILES-y += mkenvimage.o > NOPED_OBJ_FILES-y += mkimage.o > +NOPED_OBJ_FILES-$(CONFIG_INIT_FUNC) += mkinitseq.o > OBJ_FILES-$(CONFIG_SMDK5250) += mkexynosspl.o > OBJ_FILES-$(CONFIG_MX28) += mxsboot.o > OBJ_FILES-$(CONFIG_NETCONSOLE) += ncb.o > @@ -215,6 +217,10 @@ $(obj)mkimage$(SFX): $(obj)aisimage.o \ > $(HOSTCC) $(HOSTCFLAGS) $(HOSTLDFLAGS) -o $@ $^ > $(HOSTSTRIP) $@ > > +$(obj)mkinitseq$(SFX): $(obj)mkinitseq.o > + $(HOSTCC) $(HOSTCFLAGS) $(HOSTLDFLAGS) -o $@ $^ > + $(HOSTSTRIP) $@ > + > $(obj)mk$(BOARD)spl$(SFX): $(obj)mkexynosspl.o > $(HOSTCC) $(HOSTCFLAGS) $(HOSTLDFLAGS) -o $@ $^ > $(HOSTSTRIP) $@ > diff --git a/tools/mkinitseq.c b/tools/mkinitseq.c > new file mode 100644 > index 0000000..b150de4 > --- /dev/null > +++ b/tools/mkinitseq.c > @@ -0,0 +1,1512 @@ Ok, this is the worst part. I think this could be reimplemented in shell ;-) > +/* > + * (C) Copyright 2012 > + * Graeme Russ <graeme.r...@gmail.com> > + * > + * This program is free software; you can redistribute it and/or > + * modify it under the terms of the GNU General Public License as > + * published by the Free Software Foundation; either version 2 of > + * the License, or (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License > + * along with this program; if not, write to the Free Software > + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, > + * MA 02111-1307 USA > + */ > + > +/** > + * container_of - cast a member of a structure out to the containing > structure + * @ptr: the pointer to the member. > + * @type: the type of the container struct this is embedded in. > + * @member: the name of the member within the struct. > + * > + */ > +#define container_of(ptr, type, member) ({ \ > + const typeof( ((type *)0)->member ) *__mptr = (ptr); \ > + (type *)( (char *)__mptr - offsetof(type,member) );}) Don't we already have this defined in uboot ? [...] _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot