Module: xenomai-3
Branch: master
Commit: 83b0f18930290ae1aacf561a25b0daf224b6e00b
URL:    
http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=83b0f18930290ae1aacf561a25b0daf224b6e00b

Author: Philippe Gerum <r...@xenomai.org>
Date:   Sat May  9 16:10:36 2015 +0200

lib: share the common setup and bootstrap code

Make pure POSIX applications and Copperplate-based ones share the same
auto-init mechanism. This means that all applications now
automatically recognize a set of base common options, which is
currently:

--cpu-affinity=<cpuset>, --[no-]sanity, --quiet[=level], --silent and
--version.

Applications which do not want Xenomai to interpose on the main()
routine transparently for handling these options and bootstrapping the
service libraries may disable this feature by passing the
--no-auto-init switch to xeno-config when collecting the linker
flags. In this configuration, the system must be bootstrapped manually
by a call to xenomai_init() from the application code though.

This change is C++ friendly, since it also enables the Xenomai high
level services (e.g. VxWorks, pSOS) before the static constructors
run, by default.

---

 config/apirev                                      |    2 +-
 configure.ac                                       |    8 +-
 demo/alchemy/Makefile.am                           |    4 +-
 demo/alchemy/cobalt/Makefile.am                    |    1 +
 demo/posix/Makefile.am                             |    9 +-
 demo/posix/cobalt/Makefile.am                      |    2 +-
 doc/asciidoc/man1/autotune.adoc                    |    5 +-
 include/Makefile.am                                |    6 +-
 include/boilerplate/ancillaries.h                  |   25 ++-
 include/boilerplate/debug.h                        |    4 +-
 include/boilerplate/setup.h                        |   52 ++++--
 include/cobalt/sys/cobalt.h                        |   10 --
 include/copperplate/Makefile.am                    |    1 -
 include/copperplate/cluster.h                      |    1 -
 include/copperplate/registry.h                     |    1 -
 include/smokey/smokey.h                            |    6 +-
 include/xenomai/Makefile.am                        |    4 +
 include/{copperplate => xenomai}/init.h            |   19 +-
 lib/Makefile.am                                    |    2 +
 lib/alchemy/Makefile.am                            |    1 -
 lib/alchemy/init.c                                 |    9 +-
 lib/alchemy/init.h                                 |   23 ---
 lib/analogy/Makefile.am                            |    5 -
 lib/boilerplate/Makefile.am                        |    5 +-
 lib/boilerplate/ancillaries.c                      |  102 +++++++----
 lib/boilerplate/debug.c                            |    4 +-
 lib/boilerplate/init/Makefile.am                   |   18 ++
 lib/boilerplate/init/bootstrap.c                   |  106 +++++++++++
 lib/boilerplate/setup.c                            |  185 +++++++++++--------
 lib/{copperplate/main.c => boilerplate/wrappers.c} |   13 +-
 lib/cobalt/Makefile.am                             |    1 -
 lib/cobalt/arch/arm/features.c                     |   19 +-
 lib/cobalt/arch/nios2/features.c                   |   13 +-
 lib/cobalt/arch/sh/features.c                      |   13 +-
 lib/cobalt/arch/x86/features.c                     |    7 +-
 lib/cobalt/assert_context.c                        |    3 +-
 lib/cobalt/current.c                               |   28 ++-
 lib/cobalt/init.c                                  |  189 ++++++++++----------
 lib/cobalt/init.h                                  |   32 ----
 lib/cobalt/internal.h                              |    5 +-
 lib/cobalt/mutex.c                                 |   20 ++-
 lib/cobalt/printf.c                                |   41 ++---
 lib/cobalt/thread.c                                |   11 --
 lib/cobalt/umm.c                                   |   29 ++-
 lib/copperplate/Makefile.am                        |    8 +-
 lib/copperplate/heapobj-pshared.c                  |    2 +-
 lib/copperplate/heapobj-tlsf.c                     |    2 +-
 lib/copperplate/init.c                             |   29 ++-
 lib/copperplate/internal.c                         |    5 +-
 lib/copperplate/internal.h                         |    8 +-
 lib/copperplate/regd/Makefile.am                   |   15 +-
 lib/copperplate/regd/regd.c                        |   31 +++-
 lib/copperplate/registry.c                         |    2 +-
 lib/copperplate/traceobj.c                         |    2 +-
 lib/mercury/Makefile.am                            |    9 +
 lib/psos/Makefile.am                               |    1 -
 lib/psos/init.c                                    |   11 +-
 lib/psos/init.h                                    |   23 ---
 lib/psos/pt.c                                      |    1 -
 lib/psos/queue.c                                   |    1 -
 lib/psos/rn.c                                      |    1 -
 lib/psos/sem.c                                     |    1 -
 lib/psos/task.c                                    |    1 -
 lib/smokey/init.c                                  |   24 +--
 lib/trank/Makefile.am                              |    1 -
 lib/trank/init.c                                   |   12 +-
 lib/trank/init.h                                   |   23 ---
 lib/trank/internal.c                               |   16 +-
 lib/trank/internal.h                               |    2 +-
 lib/vxworks/Makefile.am                            |    1 -
 lib/vxworks/init.c                                 |    9 +-
 lib/vxworks/init.h                                 |   23 ---
 lib/vxworks/memPartLib.c                           |    1 -
 lib/vxworks/semLib.c                               |    1 -
 lib/vxworks/taskLib.c                              |    1 -
 lib/vxworks/tickLib.c                              |    1 -
 scripts/wrap-link.sh                               |    6 +-
 scripts/xeno-config-cobalt.in                      |    6 +-
 scripts/xeno-config-mercury.in                     |   10 +-
 testsuite/clocktest/Makefile.am                    |    2 +-
 testsuite/latency/Makefile.am                      |   13 +-
 testsuite/regression/posix/Makefile.am             |    2 +-
 testsuite/smokey/Makefile.am                       |    7 +-
 testsuite/switchtest/Makefile.am                   |    8 +-
 utils/analogy/Makefile.am                          |   36 ++--
 utils/autotune/Makefile.am                         |    2 +-
 utils/autotune/autotune.c                          |   39 ++--
 utils/can/Makefile.am                              |    2 +-
 utils/corectl/Makefile.am                          |    2 +-
 utils/hdb/Makefile.am                              |   10 +-
 90 files changed, 741 insertions(+), 716 deletions(-)

diff --git a/config/apirev b/config/apirev
index b4de394..48082f7 100644
--- a/config/apirev
+++ b/config/apirev
@@ -1 +1 @@
-11
+12
diff --git a/configure.ac b/configure.ac
index e161c36..89f89ef 100644
--- a/configure.ac
+++ b/configure.ac
@@ -864,9 +864,12 @@ dnl in-tree executables which require POSIX symbol 
wrapping.
    AC_SUBST([CONFIG_STATUS_DEPENDENCIES], ["$cobalt_wrappers"])
 fi
 
-XENO_AUTOINIT_LDFLAGS="-Wl,--wrap=main 
-Wl,--dynamic-list=$topdir/scripts/dynlist.ld"
+XENO_AUTOINIT_LDFLAGS='$(top_builddir)/lib/boilerplate/init/bootstrap.o'" 
-Wl,--wrap=main -Wl,--dynamic-list=$topdir/scripts/dynlist.ld"
 AC_SUBST(XENO_AUTOINIT_LDFLAGS)
 
+XENO_CORE_LIB=$rtcore_type/lib${rtcore_type}.la
+AC_SUBST(XENO_CORE_LIB)
+
 dnl
 dnl Build the Makefiles
 dnl
@@ -905,6 +908,7 @@ AC_CONFIG_FILES([ \
        scripts/xeno \
        lib/Makefile \
        lib/boilerplate/Makefile \
+       lib/boilerplate/init/Makefile \
        lib/cobalt/Makefile \
        lib/cobalt/arch/Makefile \
        lib/cobalt/arch/arm/Makefile \
@@ -931,6 +935,7 @@ AC_CONFIG_FILES([ \
        lib/cobalt/arch/sh/include/Makefile \
        lib/cobalt/arch/sh/include/asm/Makefile \
        lib/cobalt/arch/sh/include/asm/xenomai/Makefile \
+       lib/mercury/Makefile \
        lib/copperplate/Makefile \
        lib/copperplate/regd/Makefile \
        lib/alchemy/Makefile \
@@ -999,6 +1004,7 @@ AC_CONFIG_FILES([ \
        include/trank/posix/Makefile \
        include/trank/native/Makefile \
        include/trank/rtdm/Makefile \
+       include/xenomai/Makefile \
        doc/Makefile \
        doc/doxygen/Makefile \
        doc/doxygen/xeno3prm-common.conf \
diff --git a/demo/alchemy/Makefile.am b/demo/alchemy/Makefile.am
index beb3644..e6cda07 100644
--- a/demo/alchemy/Makefile.am
+++ b/demo/alchemy/Makefile.am
@@ -2,9 +2,7 @@ demodir = @XENO_DEMO_DIR@
 
 demo_PROGRAMS = altency
 
-core_libs =
 if XENO_COBALT
-core_libs += ../../lib/cobalt/libcobalt.la
 SUBDIRS = cobalt
 endif
 
@@ -15,7 +13,7 @@ cppflags =                            \
 ldadd =                                        \
        ../../lib/alchemy/libalchemy.la         \
        ../../lib/copperplate/libcopperplate.la \
-       $(core_libs)                            \
+       ../../lib/@XENO_CORE_LIB@               \
         @XENO_USER_LDADD@
 
 altency_SOURCES = altency.c
diff --git a/demo/alchemy/cobalt/Makefile.am b/demo/alchemy/cobalt/Makefile.am
index c9b79c0..dad5c32 100644
--- a/demo/alchemy/cobalt/Makefile.am
+++ b/demo/alchemy/cobalt/Makefile.am
@@ -12,6 +12,7 @@ ldadd =                                               \
        ../../../lib/alchemy/libalchemy.la              \
        ../../../lib/copperplate/libcopperplate.la      \
        ../../../lib/cobalt/libcobalt.la                \
+       @XENO_AUTOINIT_LDFLAGS@                         \
        $(XENO_POSIX_WRAPPERS)                          \
         @XENO_USER_LDADD@                              \
        -lpthread -lrt
diff --git a/demo/posix/Makefile.am b/demo/posix/Makefile.am
index dca7e90..613ebf6 100644
--- a/demo/posix/Makefile.am
+++ b/demo/posix/Makefile.am
@@ -1,24 +1,21 @@
 demodir = @XENO_DEMO_DIR@
 
 CCLD = $(top_srcdir)/scripts/wrap-link.sh $(CC)
-core_libs =
 
 if XENO_COBALT
 SUBDIRS = cobalt
-core_libs += ../../lib/cobalt/libcobalt.la
 endif
 
-demo_PROGRAMS =        \
-       can-rtt
+demo_PROGRAMS = can-rtt
 
 cppflags =                     \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-ldflags = $(XENO_POSIX_WRAPPERS)
+ldflags = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 ldadd =                                        \
-       $(core_libs)                            \
+       ../../lib/@XENO_CORE_LIB@               \
         @XENO_USER_LDADD@                      \
        -lpthread -lrt
 
diff --git a/demo/posix/cobalt/Makefile.am b/demo/posix/cobalt/Makefile.am
index c0e2d80..2eec916 100644
--- a/demo/posix/cobalt/Makefile.am
+++ b/demo/posix/cobalt/Makefile.am
@@ -15,7 +15,7 @@ cppflags =                    \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-ldflags = $(XENO_POSIX_WRAPPERS)
+ldflags = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 ldadd =                                        \
        ../../../lib/cobalt/libcobalt.la        \
diff --git a/doc/asciidoc/man1/autotune.adoc b/doc/asciidoc/man1/autotune.adoc
index 28fd751..4cf6860 100644
--- a/doc/asciidoc/man1/autotune.adoc
+++ b/doc/asciidoc/man1/autotune.adoc
@@ -104,8 +104,9 @@ to eliminate irregular delays which tend to appear on fully 
idle
 systems.  Therefore, keeping the load generation enabled most often
 leads to a more accurate estimation.
 
-*--quiet*::
-Tame down verbosity of the auto-tuner.
+*--quiet[=level]*::
+Tame down verbosity of the auto-tuner. --quiet[=2] means fully quiet,
+quiet=1 means almost quiet.
 
 *--help*::
 Display a short help.
diff --git a/include/Makefile.am b/include/Makefile.am
index 28672ab..a84e728 100644
--- a/include/Makefile.am
+++ b/include/Makefile.am
@@ -9,7 +9,8 @@ SUBDIRS =               \
        alchemy         \
        psos            \
        trank           \
-       vxworks
+       vxworks         \
+       xenomai
 
 if XENO_COBALT
 SUBDIRS +=             \
@@ -29,4 +30,5 @@ DIST_SUBDIRS =                \
        rtdm            \
        smokey          \
        trank           \
-       vxworks
+       vxworks         \
+       xenomai
diff --git a/include/boilerplate/ancillaries.h 
b/include/boilerplate/ancillaries.h
index 5532a83..47a025e 100644
--- a/include/boilerplate/ancillaries.h
+++ b/include/boilerplate/ancillaries.h
@@ -26,8 +26,6 @@
 #include <boilerplate/compiler.h>
 #include <boilerplate/atomic.h>
 
-extern struct timespec __init_date;
-
 extern pthread_mutex_t __printlock;
 
 struct error_frame;
@@ -58,7 +56,13 @@ void __namecpy_requires_character_array_as_destination(void);
                __dst[sizeof(__dst) - 1] = '\0';                        \
                __dst;                                                  \
         })
-       
+
+#define early_panic(__fmt, __args...)          \
+       __early_panic(__func__, __fmt, ##__args)
+
+#define panic(__fmt, __args...)                        \
+       __panic(__func__, __fmt, ##__args)
+
 #ifdef __cplusplus
 extern "C" {
 #endif
@@ -69,12 +73,15 @@ void __printout(const char *name,
                const char *header,
                const char *fmt, va_list ap);
 
-void __noreturn __panic(const char *name,
-                       const char *fmt, va_list ap);
+void __noreturn __early_panic(const char *fn,
+                             const char *fmt, ...);
 
-void early_panic(const char *fmt, ...);
+void __noreturn ___panic(const char *fn,
+                        const char *name,
+                        const char *fmt, va_list ap);
 
-void __noreturn panic(const char *fmt, ...);
+void __noreturn __panic(const char *fn,
+                       const char *fmt, ...);
 
 void __warning(const char *name,
               const char *fmt, va_list ap);
@@ -90,6 +97,8 @@ void early_notice(const char *fmt, ...);
 
 void notice(const char *fmt, ...);
 
+void __boilerplate_init(void);
+
 const char *symerror(int errnum);
 
 char *generate_name(char *buf, const char *radix,
@@ -97,8 +106,6 @@ char *generate_name(char *buf, const char *radix,
 
 void error_hook(struct error_frame *ef);
 
-void boilerplate_init(void);
-
 int get_static_cpu_count(void);
 
 pid_t get_thread_pid(void);
diff --git a/include/boilerplate/debug.h b/include/boilerplate/debug.h
index 556396c..eae510c 100644
--- a/include/boilerplate/debug.h
+++ b/include/boilerplate/debug.h
@@ -67,7 +67,7 @@ void __debug(const char *name, const char *fmt, ...);
 
 char *__get_error_buf(size_t *sizep);
 
-int debug_init(void);
+void debug_init(void);
 
 #ifdef __cplusplus
 }
@@ -118,7 +118,7 @@ struct backtrace_data {
                __buf;                          \
        })
 
-#define debug_init()   ({ 0; })
+#define debug_init()   do { } while (0)
 
 #endif /* !CONFIG_XENO_DEBUG */
 
diff --git a/include/boilerplate/setup.h b/include/boilerplate/setup.h
index 73452d1..5345c0d 100644
--- a/include/boilerplate/setup.h
+++ b/include/boilerplate/setup.h
@@ -19,52 +19,82 @@
 #define _BOILERPLATE_SETUP_H
 
 #include <boilerplate/list.h>
+#include <boilerplate/wrappers.h>
 #include <sched.h>
 
 struct base_setup_data {
        cpu_set_t cpu_affinity;
        int no_mlock;
        int no_sanity;
-       int silent_mode;
+       int quiet_mode;
        const char *arg0;
 };
 
 struct option;
 
-struct skin_descriptor {
+struct setup_descriptor {
        const char *name;
        int (*init)(void);
        const struct option *options;
        int (*parse_option)(int optnum, const char *optarg);
        void (*help)(void);
        struct {
+               int id;
                int opt_start;
                int opt_end;
                struct pvholder next;
        } __reserved;
 };
 
-#define DECLARE_SKIN(__name, __priority)               \
-static __attribute__ ((constructor(__priority)))       \
-void __declare_ ## __name(void)                                \
+/*
+ * We have three pre-defined constructor priorities:
+ *
+ * - One for setup calls (__setup_ctor), which are guaranteed to run
+ * prior to the bootstrap code. You should use setup calls for
+ * implementing initialization hooks which depend on a particular call
+ * order. Each Xenomai interface layer is initialized via a dedicated
+ * setup call.
+ *
+ * - A second priority is assigned to early init calls (__early_ctor),
+ * which are also guaranteed to run prior to the bootstrap
+ * code. Whether such early code runs before OR after any setup code
+ * is __UNSPECIFIED__. By design, such code may not invoke any Xenomai
+ * service, and generally speaking, should have no dependencies on
+ * anything else.
+ *
+ * - The last priority level is used for the bootstrap code
+ * (__bootstrap_ctor), which is guaranteed to run after any
+ * setup/early code.
+ *
+ * The guarantees on the init order don't go beyond what is stated
+ * here, do NOT assume more than this.
+ */
+#define __setup_ctor           __attribute__ ((constructor(200)))
+#define __early_ctor           __attribute__ ((constructor(210)))
+#define __bootstrap_ctor       __attribute__ ((constructor(220)))
+
+#define __setup_call(__name, __id)                     \
+static __setup_ctor void __declare_ ## __name(void)    \
 {                                                      \
-       __register_skin(&(__name));                     \
+       __register_setup_call(&(__name), __id);         \
 }
 
+#define core_setup_call(__name)                __setup_call(__name, 0)
+#define boilerplate_setup_call(__name) __setup_call(__name, 1)
+#define copperplate_setup_call(__name) __setup_call(__name, 2)
+#define interface_setup_call(__name)   __setup_call(__name, 3)
+#define post_setup_call(__name)                __setup_call(__name, 4)
+
 #ifdef __cplusplus
 extern "C" {
 #endif
 
-void __register_skin(struct skin_descriptor *p);
-       
-void xenomai_init(int *argcp, char *const **argvp);
+void __register_setup_call(struct setup_descriptor *p, int id);
 
 extern pid_t __node_id;
 
 extern struct base_setup_data __base_setup_data;
 
-extern const char *xenomai_version_string;
-
 #ifdef __cplusplus
 }
 #endif
diff --git a/include/cobalt/sys/cobalt.h b/include/cobalt/sys/cobalt.h
index f124ca6..fd43086 100644
--- a/include/cobalt/sys/cobalt.h
+++ b/include/cobalt/sys/cobalt.h
@@ -38,12 +38,6 @@
 #include <cobalt/uapi/cond.h>
 #include <cobalt/uapi/sem.h>
 
-#define report_error(fmt, args...) \
-       __STD(fprintf(stderr, "Xenomai/cobalt: %s(): " fmt "\n", __func__, 
##args))
-
-#define report_error_cont(fmt, args...) \
-       __STD(fprintf(stderr, "                " fmt "\n", ##args))
-
 #define cobalt_commit_memory(p) __cobalt_commit_memory(p, sizeof(*p))
 
 struct cobalt_tsd_hook {
@@ -135,10 +129,6 @@ int cobalt_sched_weighted_prio(int policy,
 
 void cobalt_register_tsd_hook(struct cobalt_tsd_hook *th);
 
-void __libcobalt_init(void);
-
-extern int __cobalt_defer_init;
-
 extern int __cobalt_no_shadow;
 
 extern int __cobalt_control_bind;
diff --git a/include/copperplate/Makefile.am b/include/copperplate/Makefile.am
index 4b16fa7..2cd3079 100644
--- a/include/copperplate/Makefile.am
+++ b/include/copperplate/Makefile.am
@@ -6,7 +6,6 @@ includesub_HEADERS =            \
        debug.h                 \
        eventobj.h              \
        heapobj.h               \
-       init.h                  \
        reference.h             \
        registry.h              \
        semobj.h                \
diff --git a/include/copperplate/cluster.h b/include/copperplate/cluster.h
index 9c76cbc..af7dfee 100644
--- a/include/copperplate/cluster.h
+++ b/include/copperplate/cluster.h
@@ -20,7 +20,6 @@
 #define _COPPERPLATE_CLUSTER_H
 
 #include <boilerplate/hash.h>
-#include <copperplate/init.h>
 #include <copperplate/syncobj.h>
 
 #ifdef CONFIG_XENO_PSHARED
diff --git a/include/copperplate/registry.h b/include/copperplate/registry.h
index 8e423dc..c94c902 100644
--- a/include/copperplate/registry.h
+++ b/include/copperplate/registry.h
@@ -25,7 +25,6 @@
 #include <boilerplate/list.h>
 #include <boilerplate/hash.h>
 #include <boilerplate/obstack.h>
-#include <copperplate/init.h>
 
 struct fsobj;
 
diff --git a/include/smokey/smokey.h b/include/smokey/smokey.h
index c5133fc..55c67aa 100644
--- a/include/smokey/smokey.h
+++ b/include/smokey/smokey.h
@@ -21,6 +21,7 @@
 #include <boilerplate/list.h>
 #include <boilerplate/libc.h>
 #include <copperplate/clockobj.h>
+#include <xenomai/init.h>
 
 #define SMOKEY_INT(__name) {           \
         .name = # __name,              \
@@ -71,8 +72,6 @@ struct smokey_test {
 #define for_each_smokey_test(__pos)    \
        pvlist_for_each_entry((__pos), &smokey_test_list, __reserved.next)
 
-#define __SMOKEYPLUG_CTOR_PRIO  310
-
 #define __smokey_arg_count(__args)     \
        (sizeof(__args) / sizeof(__args[0]))
 
@@ -86,8 +85,7 @@ struct smokey_test {
                .description = (__desc),                                \
                .run = run_ ## __plugin,                                \
        };                                                              \
-       void smokey_plugin_ ## __plugin(void);                          \
-       __attribute__((constructor(__SMOKEYPLUG_CTOR_PRIO)))            \
+       __early_ctor void smokey_plugin_ ## __plugin(void);             \
        void smokey_plugin_ ## __plugin(void)                           \
        {                                                               \
                smokey_register_plugin(&(__plugin));                    \
diff --git a/include/xenomai/Makefile.am b/include/xenomai/Makefile.am
new file mode 100644
index 0000000..b5f941d
--- /dev/null
+++ b/include/xenomai/Makefile.am
@@ -0,0 +1,4 @@
+includesubdir = $(includedir)/xenomai
+
+includesub_HEADERS =   \
+       init.h
diff --git a/include/copperplate/init.h b/include/xenomai/init.h
similarity index 75%
rename from include/copperplate/init.h
rename to include/xenomai/init.h
index 66b471c..7ff469a 100644
--- a/include/copperplate/init.h
+++ b/include/xenomai/init.h
@@ -15,26 +15,23 @@
  * License along with this library; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
  */
+#ifndef _XENOMAI_XENOMAI_INIT_H
+#define _XENOMAI_XENOMAI_INIT_H
 
-#ifndef _COPPERPLATE_INIT_H
-#define _COPPERPLATE_INIT_H
-
-#include <stdarg.h>
-#include <sched.h>
-#include <boilerplate/trace.h>
-#include <boilerplate/ancillaries.h>
 #include <boilerplate/setup.h>
 
-#define __LIBCOPPERPLATE_CTOR_PRIO  250
-
 #ifdef __cplusplus
 extern "C" {
 #endif
 
-int copperplate_main(int argc, char *const argv[]);
+void xenomai_init(int *argcp, char *const **argvp);
+
+int xenomai_main(int argc, char *const argv[]);
+
+extern const char *xenomai_version_string;
 
 #ifdef __cplusplus
 }
 #endif
 
-#endif /* _COPPERPLATE_INIT_H */
+#endif /* _XENOMAI_XENOMAI_INIT_H */
diff --git a/lib/Makefile.am b/lib/Makefile.am
index 9b6621f..4e778b1 100644
--- a/lib/Makefile.am
+++ b/lib/Makefile.am
@@ -5,6 +5,8 @@ SUBDIRS +=      \
        cobalt  \
        analogy \
        trank
+else
+SUBDIRS += mercury
 endif
 
 SUBDIRS +=             \
diff --git a/lib/alchemy/Makefile.am b/lib/alchemy/Makefile.am
index 788a4bb..5362695 100644
--- a/lib/alchemy/Makefile.am
+++ b/lib/alchemy/Makefile.am
@@ -4,7 +4,6 @@ libalchemy_la_LDFLAGS = @XENO_LIB_LDFLAGS@ -version-info 0:0:0
 
 libalchemy_la_SOURCES =        \
        init.c          \
-       init.h          \
        internal.c      \
        internal.h      \
        reference.h     \
diff --git a/lib/alchemy/init.c b/lib/alchemy/init.c
index 65ede3c..14eb4d1 100644
--- a/lib/alchemy/init.c
+++ b/lib/alchemy/init.c
@@ -21,8 +21,7 @@
 #include <stdlib.h>
 #include <unistd.h>
 #include <getopt.h>
-#include <copperplate/init.h>
-#include "init.h"
+#include <xenomai/init.h>
 #include "timer.h"
 #include "task.h"
 #include "sem.h"
@@ -78,7 +77,7 @@ static int alchemy_parse_option(int optnum, const char 
*optarg)
 
 static void alchemy_help(void)
 {
-        fprintf(stderr, "--alchemy-clock-resolution=<ns>  tick value (default 
1ns, tickless)\n");
+        fprintf(stderr, "--alchemy-clock-resolution=<ns> tick value (default 
1ns, tickless)\n");
 }
 
 #ifdef CONFIG_XENO_COBALT
@@ -132,7 +131,7 @@ static int alchemy_init(void)
        return 0;
 }
 
-static struct skin_descriptor alchemy_skin = {
+static struct setup_descriptor alchemy_skin = {
        .name = "alchemy",
        .init = alchemy_init,
        .options = alchemy_options,
@@ -140,4 +139,4 @@ static struct skin_descriptor alchemy_skin = {
        .help = alchemy_help,
 };
 
-DECLARE_SKIN(alchemy_skin, __LIBALCHEMY_CTOR_PRIO);
+interface_setup_call(alchemy_skin);
diff --git a/lib/alchemy/init.h b/lib/alchemy/init.h
deleted file mode 100644
index d3cf5f3..0000000
--- a/lib/alchemy/init.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2014 Philippe Gerum <r...@xenomai.org>.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
-
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
- */
-#ifndef _ALCHEMY_INIT_H
-#define _ALCHEMY_INIT_H
-
-#define __LIBALCHEMY_CTOR_PRIO  300
-
-#endif /* _ALCHEMY_INIT_H */
diff --git a/lib/analogy/Makefile.am b/lib/analogy/Makefile.am
index b93d7c1..21b8fb4 100644
--- a/lib/analogy/Makefile.am
+++ b/lib/analogy/Makefile.am
@@ -19,8 +19,3 @@ libanalogy_la_CPPFLAGS =              \
        @XENO_USER_CFLAGS@              \
        -I$(top_srcdir)/include         \
        -I$(top_srcdir)/lib/boilerplate 
-
-libanalogy_la_LIBADD = \
-       ../boilerplate/libboilerplate.la        \
-       -lm
-
diff --git a/lib/boilerplate/Makefile.am b/lib/boilerplate/Makefile.am
index c8496c9..27b5dcb 100644
--- a/lib/boilerplate/Makefile.am
+++ b/lib/boilerplate/Makefile.am
@@ -8,7 +8,8 @@ libboilerplate_la_SOURCES =     \
        hash.c                  \
        obstack.c               \
        setup.c                 \
-       time.c
+       time.c                  \
+       wrappers.c
 
 if XENO_DEBUG
 libboilerplate_la_SOURCES += debug.c
@@ -83,6 +84,8 @@ libtlsf_la_CPPFLAGS =                                 \
        -I$(top_srcdir)/include                         \
        -DTLSF_USE_LOCKS=1 -DUSE_MMAP=1 -DTLSF_STATISTIC=1
 
+SUBDIRS = init
+
 EXTRA_DIST += tlsf/README
 
 SPARSE = sparse
diff --git a/lib/boilerplate/ancillaries.c b/lib/boilerplate/ancillaries.c
index 42a595c..244e6f6 100644
--- a/lib/boilerplate/ancillaries.c
+++ b/lib/boilerplate/ancillaries.c
@@ -29,30 +29,24 @@
 #include "boilerplate/lock.h"
 #include "boilerplate/time.h"
 #include "boilerplate/scope.h"
+#include "boilerplate/setup.h"
+#include "boilerplate/debug.h"
 #include "boilerplate/ancillaries.h"
+#include "xenomai/init.h"
 
 pthread_mutex_t __printlock;
 
-struct timespec __init_date;
+static struct timespec init_date;
 
-void __printout(const char *name, const char *header,
-               const char *fmt, va_list ap)
+static int init_done;
+
+static void __do_printout(const char *name, const char *header,
+                         unsigned int ms, unsigned int us,
+                         const char *fmt, va_list ap)
 {
-       unsigned long long ms, us, ns;
-       struct timespec now, delta;
        FILE *fp = stderr;
 
-       __RT(clock_gettime(CLOCK_MONOTONIC, &now));
-       timespec_sub(&delta, &now, &__init_date);
-       ns = delta.tv_sec * 1000000000ULL;
-       ns += delta.tv_nsec;
-       ms = ns / 1000000ULL;
-       us = (ns % 1000000ULL) / 1000ULL;
-
-       SIGSAFE_LOCK_ENTRY(&__printlock);
-
-       fprintf(fp, "%4d\"%.3d.%.3d| ",
-               (int)ms / 1000, (int)ms % 1000, (int)us);
+       fprintf(fp, "%4u\"%.3u.%.3u| ", ms / 1000, ms % 1000, us);
 
        if (header)
                fputs(header, fp);
@@ -61,7 +55,34 @@ void __printout(const char *name, const char *header,
        vfprintf(fp, fmt, ap);
        fputc('\n', fp);
        fflush(fp);
+}
+
+void __printout(const char *name, const char *header,
+               const char *fmt, va_list ap)
+{
+       struct timespec now, delta;
+       unsigned long long ns;
+       unsigned int ms, us;
 
+       /*
+        * Catch early printouts, when the init sequence is not
+        * completed yet. In such event, we don't care for serializing
+        * output, since we must be running over the main thread
+        * uncontended.
+        */
+       if (!init_done) {
+               __do_printout(name, header, 0, 0, fmt, ap);
+               return;
+       }
+       
+       __RT(clock_gettime(CLOCK_MONOTONIC, &now));
+       timespec_sub(&delta, &now, &init_date);
+       ns = delta.tv_sec * 1000000000ULL;
+       ns += delta.tv_nsec;
+       ms = ns / 1000000ULL;
+       us = (ns % 1000000ULL) / 1000ULL;
+       SIGSAFE_LOCK_ENTRY(&__printlock);
+       __do_printout(name, header, ms, us, fmt, ap);
        SIGSAFE_LOCK_EXIT(&__printlock);
 }
 
@@ -75,9 +96,14 @@ void __notice(const char *name, const char *fmt, va_list ap)
        __printout(name, NULL, fmt, ap);
 }
 
-void __panic(const char *name, const char *fmt, va_list ap)
+void ___panic(const char *fn, const char *name,
+            const char *fmt, va_list ap)
 {
-       __printout(name, "BUG: ", fmt, ap);
+       char *p;
+
+       if (asprintf(&p, "BUG in %s(): ", fn) < 0)
+               p = "BUG: ";
+       __printout(name, p, fmt, ap);
        exit(1);
 }
 
@@ -153,17 +179,17 @@ void __run_cleanup_block(struct cleanup_block *cb)
        cb->handler(cb->arg);
 }
 
-void early_panic(const char *fmt, ...)
+void __early_panic(const char *fn, const char *fmt, ...)
 {
        va_list ap;
 
        va_start(ap, fmt);
-       __panic(NULL, fmt, ap);
+       ___panic(fn, NULL, fmt, ap);
        va_end(ap);
 }
 
-void panic(const char *fmt, ...)
-__attribute__((alias("early_panic"), weak));
+void __panic(const char *fn, const char *fmt, ...)
+__attribute__((alias("__early_panic"), weak));
 
 void early_warning(const char *fmt, ...)
 {
@@ -267,26 +293,30 @@ pid_t get_thread_pid(void)
        return syscall(__NR_gettid);
 }
 
-static pthread_once_t init_once = PTHREAD_ONCE_INIT;
-
-static void reset_on_fork(void)
-{
-       init_once = PTHREAD_ONCE_INIT;
-}
+const char *config_strings[] = {
+#include "config-dump.h"
+       NULL,
+};
 
-static void __boilerplate_init(void)
+void __boilerplate_init(void)
 {
-       pthread_atfork(NULL, NULL, reset_on_fork);
-       __RT(clock_gettime(CLOCK_MONOTONIC, &__init_date));
+       __RT(clock_gettime(CLOCK_MONOTONIC, &init_date));
        __RT(pthread_mutex_init(&__printlock, NULL));
+       debug_init();
+       init_done = 1;
 }
 
-void boilerplate_init(void)
+static int boilerplate_init(void)
 {
-       pthread_once(&init_once, __boilerplate_init);
+       pthread_atfork(NULL, NULL, __boilerplate_init);
+       __boilerplate_init();
+
+       return 0;
 }
 
-const char *config_strings[] = {
-#include "config-dump.h"
-       NULL,
+static struct setup_descriptor boilerplate_interface = {
+       .name = "boilerplate",
+       .init = boilerplate_init,
 };
+
+boilerplate_setup_call(boilerplate_interface);
diff --git a/lib/boilerplate/debug.c b/lib/boilerplate/debug.c
index d9c82b5..54e3cbd 100644
--- a/lib/boilerplate/debug.c
+++ b/lib/boilerplate/debug.c
@@ -175,8 +175,8 @@ char *__get_error_buf(size_t *sizep)
        return btd->eundef;
 }
 
-int debug_init(void)
+void debug_init(void)
 {
        __RT(pthread_mutex_init(&main_btd.lock, NULL));
-       return -pthread_key_create(&btkey, NULL);
+       pthread_key_create(&btkey, NULL);
 }
diff --git a/lib/boilerplate/init/Makefile.am b/lib/boilerplate/init/Makefile.am
new file mode 100644
index 0000000..7a58f54
--- /dev/null
+++ b/lib/boilerplate/init/Makefile.am
@@ -0,0 +1,18 @@
+noinst_LIBRARIES = libbootstrap.a
+
+libbootstrap_a_SOURCES = bootstrap.c
+
+libbootstrap_a_CPPFLAGS =              \
+       @XENO_USER_CFLAGS@              \
+       -I$(top_srcdir)/include         \
+       -I$(top_srcdir)/lib
+
+all-local: $(libbootstrap_a_OBJECTS)
+       cp $(libbootstrap_a_OBJECTS) bootstrap.o
+
+install-data-local:
+       $(mkinstalldirs) $(DESTDIR)$(libdir)/xenomai
+       $(INSTALL_DATA) $(libbootstrap_a_OBJECTS) 
$(DESTDIR)$(libdir)/xenomai/bootstrap.o
+
+uninstall-local:
+       $(RM) -r $(DESTDIR)$(libdir)/xenomai
diff --git a/lib/boilerplate/init/bootstrap.c b/lib/boilerplate/init/bootstrap.c
new file mode 100644
index 0000000..cee6843
--- /dev/null
+++ b/lib/boilerplate/init/bootstrap.c
@@ -0,0 +1,106 @@
+/*
+ * Copyright (C) 2013 Philippe Gerum <r...@xenomai.org>.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
+ */
+#include <sys/types.h>
+#include <unistd.h>
+#include <malloc.h>
+#include <string.h>
+#include <fcntl.h>
+#include <xenomai/init.h>
+
+static int early_argc;
+
+static char *const *early_argv;
+
+int __real_main(int argc, char *const argv[]);
+
+int __wrap_main(int argc, char *const argv[])
+__attribute__((alias("xenomai_main"), weak));
+
+int xenomai_main(int argc, char *const argv[])
+{
+       if (early_argc)
+               return __real_main(early_argc, early_argv);
+       
+       xenomai_init(&argc, &argv);
+
+       return __real_main(argc, argv);
+}
+
+__bootstrap_ctor static void xenomai_bootstrap(void)
+{
+       char *arglist, *argend, *p, **v, *const *argv;
+       ssize_t len, ret;
+       int fd, n, argc;
+
+       len = 1024;
+
+       for (;;) {
+               fd = __STD(open("/proc/self/cmdline", O_RDONLY));
+               if (fd < 0)
+                       return;
+
+               arglist = malloc(len);
+               if (arglist == NULL) {
+                       __STD(close(fd));
+                       return;
+               }
+
+               ret = __STD(read(fd, arglist, len));
+               __STD(close(fd));
+
+               if (ret < 0) {
+                       free(arglist);
+                       return;
+               }
+
+               if (ret < len)
+                       break;
+
+               free(arglist);
+               len <<= 1;
+       }
+
+       argend = arglist + ret;
+       p = arglist;
+       n = 0;
+       while (p < argend) {
+               n++;
+               p += strlen(p) + 1;
+       }
+
+       v = malloc((n + 1) * sizeof(char *));
+       if (v == NULL) {
+               free(arglist);
+               return;
+       }
+
+       p = arglist;
+       n = 0;
+       while (p < argend) {
+               v[n++] = p;
+               p += strlen(p) + 1;
+       }
+
+       v[n] = NULL;
+       argv = v;
+       argc = n;
+
+       xenomai_init(&argc, &argv);
+       early_argc = argc;
+       early_argv = argv;
+}
diff --git a/lib/boilerplate/setup.c b/lib/boilerplate/setup.c
index 1ea950a..efa1f3d 100644
--- a/lib/boilerplate/setup.c
+++ b/lib/boilerplate/setup.c
@@ -25,23 +25,26 @@
 #include <unistd.h>
 #include <memory.h>
 #include <malloc.h>
+#include <stdio.h>
 #include <assert.h>
 #include <xeno_config.h>
-#include <boilerplate/setup.h>
 #include <boilerplate/lock.h>
 #include <boilerplate/debug.h>
 #include <boilerplate/ancillaries.h>
+#include <xenomai/init.h>
 
 struct base_setup_data __base_setup_data = {
-       .no_mlock = 0,
        .no_sanity = !CONFIG_XENO_SANITY,
-       .silent_mode = 0,
+       .quiet_mode = 0,
        .arg0 = NULL,
+       .no_mlock = 0,
 };
 
 pid_t __node_id;
 
-static DEFINE_PRIVATE_LIST(skins);
+static int init_done;
+
+static DEFINE_PRIVATE_LIST(setup_list);
 
 static const struct option base_options[] = {
        {
@@ -49,21 +52,20 @@ static const struct option base_options[] = {
                .name = "help",
        },
        {
-#define no_mlock_opt   1
-               .name = "no-mlock",
-               .flag = &__base_setup_data.no_mlock,
-               .val = 1
-       },
-       {
-#define affinity_opt   2
+#define affinity_opt   1
                .name = "cpu-affinity",
                .has_arg = 1,
        },
        {
+#define quiet_opt      2
+               .name = "quiet",
+               .has_arg = 2,
+       },
+       {
 #define silent_opt     3
                .name = "silent",
-               .flag = &__base_setup_data.silent_mode,
-               .val = 1
+               .flag = &__base_setup_data.quiet_mode,
+               .val = 2,
        },
        {
 #define version_opt    4
@@ -85,6 +87,14 @@ static const struct option base_options[] = {
                .flag = &__base_setup_data.no_sanity,
        },
        {
+#define no_mlock_opt   8
+#ifdef CONFIG_XENO_MERCURY
+               .name = "no-mlock",
+               .flag = &__base_setup_data.no_mlock,
+               .val = 1
+#endif
+       },
+       {
                /* sentinel */
        }
 };
@@ -112,7 +122,7 @@ static int collect_cpu_affinity(const char *cpu_list)
                cpu = atoi(p);
                if (cpu >= CPU_SETSIZE) {
                        free(s);
-                       warning("invalid CPU number '%d'", cpu);
+                       early_warning("invalid CPU number '%d'", cpu);
                        return -EINVAL;
                }
                CPU_SET(cpu, &__base_setup_data.cpu_affinity);
@@ -134,7 +144,7 @@ static int collect_cpu_affinity(const char *cpu_list)
        ret = sched_setaffinity(0, sizeof(__base_setup_data.cpu_affinity),
                                &__base_setup_data.cpu_affinity);
        if (ret) {
-               warning("invalid CPU in affinity list '%s'", cpu_list);
+               early_warning("invalid CPU in affinity list '%s'", cpu_list);
                return -errno;
        }
 
@@ -200,16 +210,16 @@ static inline void pack_args(int *argcp, int *largcp, 
char **argv)
 
 static struct option *build_option_array(int *base_opt_startp)
 {
-       struct skin_descriptor *skin;
+       struct setup_descriptor *setup;
        struct option *options, *q;
        const struct option *p;
        int nopts;
 
        nopts = sizeof(base_options) / sizeof(base_options[0]);
 
-       if (!pvlist_empty(&skins)) {
-               pvlist_for_each_entry(skin, &skins, __reserved.next) {
-                       p = skin->options;
+       if (!pvlist_empty(&setup_list)) {
+               pvlist_for_each_entry(setup, &setup_list, __reserved.next) {
+                       p = setup->options;
                        if (p) {
                                while (p->name) {
                                        nopts++;
@@ -225,15 +235,15 @@ static struct option *build_option_array(int 
*base_opt_startp)
 
        q = options;
 
-       if (!pvlist_empty(&skins)) {
-               pvlist_for_each_entry(skin, &skins, __reserved.next) {
-                       p = skin->options;
+       if (!pvlist_empty(&setup_list)) {
+               pvlist_for_each_entry(setup, &setup_list, __reserved.next) {
+                       p = setup->options;
                        if (p) {
-                               skin->__reserved.opt_start = q - options;
+                               setup->__reserved.opt_start = q - options;
                                while (p->name)
                                        memcpy(q++, p++, sizeof(*q));
                        }
-                       skin->__reserved.opt_end = q - options;
+                       setup->__reserved.opt_end = q - options;
                }
        }
 
@@ -245,23 +255,27 @@ static struct option *build_option_array(int 
*base_opt_startp)
 
 static void usage(void)
 {
-       struct skin_descriptor *skin;
+       struct setup_descriptor *setup;
 
        print_version();
         fprintf(stderr, "usage: program <options>, where options may be:\n");
-        fprintf(stderr, "--no-mlock                       do not lock memory 
at init (Mercury only)\n");
-        fprintf(stderr, "--cpu-affinity=<cpu[,cpu]...>    set CPU affinity of 
threads\n");
-        fprintf(stderr, "--[no-]sanity                    disable/enable 
sanity checks\n");
-        fprintf(stderr, "--silent                         tame down 
verbosity\n");
-        fprintf(stderr, "--version                        get version 
information\n");
-        fprintf(stderr, "--dump-config                    dump configuration 
settings\n");
-
-       if (pvlist_empty(&skins))
+        fprintf(stderr, "--cpu-affinity=<cpu[,cpu]...> set CPU affinity of 
threads\n");
+        fprintf(stderr, "--[no-]sanity                 disable/enable sanity 
checks\n");
+        fprintf(stderr, "--quiet[=level]               tame down verbosity to 
desired level\n");
+        fprintf(stderr, "--silent                      same as --quiet\n");
+        fprintf(stderr, "--version                     get version 
information\n");
+        fprintf(stderr, "--dump-config                 dump configuration 
settings\n");
+#ifdef CONFIG_XENO_MERCURY
+        fprintf(stderr, "--no-mlock                    do not lock memory at 
init\n");
+#endif
+        fprintf(stderr, "--help                                display 
help\n");
+
+       if (pvlist_empty(&setup_list))
                return;
 
-       pvlist_for_each_entry(skin, &skins, __reserved.next) {
-               if (skin->help)
-                       skin->help();
+       pvlist_for_each_entry(setup, &setup_list, __reserved.next) {
+               if (setup->help)
+                       setup->help();
        }
 }
 
@@ -290,10 +304,9 @@ static int parse_base_options(int *argcp, char *const 
**argvp,
        /*
         * NOTE: since we pack the argument vector on the fly while
         * processing the options, optarg should be considered as
-        * volatile by skin option handlers; i.e. strdup() is required
-        * if the value has to be retained. Values from the user
-        * vector returned by xenomai_init() live in permanent memory
-        * though.
+        * volatile by option handlers; i.e. strdup() is required if
+        * the value has to be retained. Values from the user vector
+        * returned by xenomai_init() live in permanent memory though.
         */
 
        for (;;) {
@@ -310,10 +323,20 @@ static int parse_base_options(int *argcp, char *const 
**argvp,
                        if (ret)
                                return ret;
                        break;
+               case quiet_opt:
+                       __base_setup_data.quiet_mode = 2;
+                       if (optarg) {
+                               if (strcmp(optarg, "semi") == 0 ||
+                                   strcmp(optarg, "almost") == 0)
+                                       __base_setup_data.quiet_mode = 1;
+                               else
+                                       __base_setup_data.quiet_mode = 
atoi(optarg);
+                       }
+                       break;
+               case silent_opt:
                case no_mlock_opt:
                case no_sanity_opt:
                case sanity_opt:
-               case silent_opt:
                        break;
                case version_opt:
                        print_version();
@@ -356,10 +379,10 @@ static int parse_base_options(int *argcp, char *const 
**argvp,
        return 0;
 }
 
-static int parse_skin_options(int *argcp, int largc, char **uargv,
-                             const struct option *options)
+static int parse_setup_options(int *argcp, int largc, char **uargv,
+                              const struct option *options)
 {
-       struct skin_descriptor *skin;
+       struct setup_descriptor *setup;
        int lindex, n, c, ret;
 
        for (;;) {
@@ -369,14 +392,14 @@ static int parse_skin_options(int *argcp, int largc, char 
**uargv,
                        break;
                if (lindex == -1)
                        continue; /* Not handled here. */
-               pvlist_for_each_entry(skin, &skins, __reserved.next) {
-                       if (skin->parse_option == NULL)
+               pvlist_for_each_entry(setup, &setup_list, __reserved.next) {
+                       if (setup->parse_option == NULL)
                                continue;
-                       if (lindex < skin->__reserved.opt_start ||
-                           lindex >= skin->__reserved.opt_end)
+                       if (lindex < setup->__reserved.opt_start ||
+                           lindex >= setup->__reserved.opt_end)
                                continue;
-                       lindex -= skin->__reserved.opt_start;
-                       ret = skin->parse_option(lindex, optarg);
+                       lindex -= setup->__reserved.opt_start;
+                       ret = setup->parse_option(lindex, optarg);
                        if (ret == 0)
                                break;
                        return ret;
@@ -398,20 +421,17 @@ static int parse_skin_options(int *argcp, int largc, char 
**uargv,
 void xenomai_init(int *argcp, char *const **argvp)
 {
        int ret, largc, base_opt_start;
-       struct skin_descriptor *skin;
+       struct setup_descriptor *setup;
        struct option *options;
-       static int init_done;
        char **uargv = NULL;
        struct service svc;
 
        if (init_done) {
-               warning("duplicate call to %s() ignored", __func__);
-               warning("(xeno-config --no-auto-init disables implicit call)");
+               early_warning("duplicate call to %s() ignored", __func__);
+               early_warning("(xeno-config --no-auto-init disables implicit 
call)");
                return;
        }
 
-       boilerplate_init();
-
        /* Our node id. is the tid of the main thread. */
        __node_id = get_thread_pid();
 
@@ -422,8 +442,7 @@ void xenomai_init(int *argcp, char *const **argvp)
        CPU_ZERO(&__base_setup_data.cpu_affinity);
 
        /*
-        * Build the global option array, merging the base and
-        * per-skin option sets.
+        * Build the global option array, merging all option sets.
         */
        options = build_option_array(&base_opt_start);
        if (options == NULL) {
@@ -449,18 +468,12 @@ void xenomai_init(int *argcp, char *const **argvp)
        }
 #endif
 
-       ret = debug_init();
-       if (ret) {
-               warning("failed to initialize debugging features");
-               goto fail;
-       }
-
 #ifdef CONFIG_XENO_MERCURY
        if (__base_setup_data.no_mlock == 0) {
                ret = mlockall(MCL_CURRENT | MCL_FUTURE);
                if (ret) {
                        ret = -errno;
-                       warning("failed to lock memory");
+                       early_warning("failed to lock memory");
                        goto fail;
                }
        }
@@ -468,26 +481,28 @@ void xenomai_init(int *argcp, char *const **argvp)
 
        /*
         * Now that we have bootstrapped the core, we may call the
-        * skin handlers for parsing their own options, which in turn
+        * setup handlers for parsing their own options, which in turn
         * may create system objects on the fly.
         */
-       if (!pvlist_empty(&skins)) {
-               ret = parse_skin_options(argcp, largc, uargv, options);
+       if (!pvlist_empty(&setup_list)) {
+               ret = parse_setup_options(argcp, largc, uargv, options);
                if (ret)
                        goto fail;
 
                CANCEL_DEFER(svc);
 
-               pvlist_for_each_entry(skin, &skins, __reserved.next) {
-                       ret = skin->init();
-                       if (ret)
-                               break;
+               pvlist_for_each_entry(setup, &setup_list, __reserved.next) {
+                       if (setup->init) {
+                               ret = setup->init();
+                               if (ret)
+                                       break;
+                       }
                }
 
                CANCEL_RESTORE(svc);
 
                if (ret) {
-                       warning("skin %s won't initialize", skin->name);
+                       early_warning("setup call %s failed", setup->name);
                        goto fail;
                }
        }
@@ -495,8 +510,8 @@ void xenomai_init(int *argcp, char *const **argvp)
        free(options);
 
 #ifdef CONFIG_XENO_DEBUG
-       if (__base_setup_data.silent_mode == 0) {
-               warning("Xenomai compiled with %s debug enabled,\n"
+       if (__base_setup_data.quiet_mode == 0) {
+               early_warning("Xenomai compiled with %s debug enabled,\n"
                        "                              "
                        "%shigh latencies expected [--enable-debug=%s]",
 #ifdef CONFIG_XENO_DEBUG_FULL
@@ -521,7 +536,23 @@ fail:
        early_panic("initialization failed, %s", symerror(ret));
 }
 
-void __register_skin(struct skin_descriptor *p)
+void __register_setup_call(struct setup_descriptor *p, int id)
 {
-       pvlist_append(&p->__reserved.next, &skins);
+       struct setup_descriptor *pos;
+
+       /*
+        * Trap late registration due to wrong constructor priorities.
+        */
+       assert(!init_done);
+       p->__reserved.id = id;
+
+       if (!pvlist_empty(&setup_list)) {
+               pvlist_for_each_entry_reverse(pos, &setup_list, 
__reserved.next) {
+                       if (id >= pos->__reserved.id) {
+                               atpvh(&pos->__reserved.next, 
&p->__reserved.next);
+                               return;
+                       }
+               }
+       }
+       pvlist_prepend(&p->__reserved.next, &setup_list);
 }
diff --git a/lib/copperplate/main.c b/lib/boilerplate/wrappers.c
similarity index 78%
rename from lib/copperplate/main.c
rename to lib/boilerplate/wrappers.c
index f67a592..9d2490c 100644
--- a/lib/copperplate/main.c
+++ b/lib/boilerplate/wrappers.c
@@ -15,16 +15,13 @@
  * License along with this library; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
  */
-#include <copperplate/init.h>
+#include <boilerplate/compiler.h>
 
-int __real_main(int argc, char *const argv[]);
+int main(int argc, char *const argv[]);
 
-int __wrap_main(int argc, char *const argv[])
-__attribute__((alias("copperplate_main"), weak));
+int __real_main(int argc, char *const argv[]);
 
-int copperplate_main(int argc, char *const argv[])
+__weak int __real_main(int argc, char *const argv[])
 {
-       xenomai_init(&argc, &argv);
-
-       return __real_main(argc, argv);
+       return main(argc, argv);
 }
diff --git a/lib/cobalt/Makefile.am b/lib/cobalt/Makefile.am
index 12f321c..2bfc3e3 100644
--- a/lib/cobalt/Makefile.am
+++ b/lib/cobalt/Makefile.am
@@ -3,7 +3,6 @@ pkgconfigdir = $(libdir)/pkgconfig
 noinst_HEADERS =       \
        current.h       \
        umm.h           \
-       init.h          \
        internal.h
 
 lib_LTLIBRARIES = libcobalt.la
diff --git a/lib/cobalt/arch/arm/features.c b/lib/cobalt/arch/arm/features.c
index 83d2846..edabcf2 100644
--- a/lib/cobalt/arch/arm/features.c
+++ b/lib/cobalt/arch/arm/features.c
@@ -49,18 +49,13 @@ void cobalt_check_features(struct cobalt_featinfo *finfo)
 
        err = XENOMAI_SYSCALL2(sc_cobalt_archcall,
                               XENOMAI_SYSARCH_TSCINFO, &__xn_tscinfo.kinfo);
-       if (err) {
-               report_error("Your board/configuration does not "
-                            "allow TSC emulation in user-space: %s ",
+       if (err)
+               early_panic("missing TSC emulation: %s",
                             strerror(-err));
-               exit(EXIT_FAILURE);
-       }
 
        fd = __STD(open("/dev/mem", O_RDONLY | O_SYNC));
-       if (fd == -1) {
-               report_error("open(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (fd == -1)
+               early_panic("failed open(/dev/mem): %s", strerror(errno));
 
        page_size = sysconf(_SC_PAGESIZE);
 
@@ -72,10 +67,8 @@ void cobalt_check_features(struct cobalt_featinfo *finfo)
 
        addr = __STD(mmap(NULL, page_size, PROT_READ, MAP_SHARED,
                          fd, phys_addr & ~(page_size - 1)));
-       if (addr == MAP_FAILED) {
-               report_error("mmap(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (addr == MAP_FAILED)
+               early_panic("failed mmap(/dev/mem): %s", strerror(errno));
 
        __xn_tscinfo.kinfo.counter =
                ((volatile unsigned *)
diff --git a/lib/cobalt/arch/nios2/features.c b/lib/cobalt/arch/nios2/features.c
index b512041..e095373 100644
--- a/lib/cobalt/arch/nios2/features.c
+++ b/lib/cobalt/arch/nios2/features.c
@@ -39,18 +39,15 @@ void cobalt_check_features(struct cobalt_featinfo *finfo)
        int fd;
 
        fd = __STD(open("/dev/mem", O_RDWR | O_SYNC));
-       if (fd == -1) {
-               report_error("open(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (fd == -1)
+               early_panic("failed open(/dev/mem): %s", strerror(errno));
 
        pagesz = sysconf(_SC_PAGESIZE);
        p = __STD(mmap(NULL, pagesz, PROT_READ | PROT_WRITE, MAP_SHARED,
                       fd, pa & ~(pagesz - 1)));
-       if (p == MAP_FAILED) {
-               report_error("mmap(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (p == MAP_FAILED)
+               early_panic("failed mmap(/dev/mem): %s", strerror(errno));
+
        __STD(close(fd));
 
        __cobalt_nios2_hrclock = (volatile void *)(p + (pa & (pagesz - 1)));
diff --git a/lib/cobalt/arch/sh/features.c b/lib/cobalt/arch/sh/features.c
index ac7e8b7..a46a307 100644
--- a/lib/cobalt/arch/sh/features.c
+++ b/lib/cobalt/arch/sh/features.c
@@ -41,17 +41,14 @@ static volatile void *map_kmem(unsigned long pa, unsigned 
int pagesz)
        int fd;
 
        fd = __STD(open("/dev/mem", O_RDWR | O_SYNC));
-       if (fd == -1) {
-               report_error("open(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (fd == -1)
+               early_panic("failed open(/dev/mem): %s", strerror(errno));
 
        p = __STD(mmap(NULL, pagesz, PROT_READ | PROT_WRITE, MAP_SHARED,
                       fd, pa & ~(pagesz - 1)));
-       if (p == MAP_FAILED) {
-               report_error("mmap(/dev/mem): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (p == MAP_FAILED)
+               early_panic("failed mmap(/dev/mem): %s", strerror(errno));
+
        __STD(close(fd));
 
        return (volatile void *)(p + (pa & (pagesz - 1)));
diff --git a/lib/cobalt/arch/x86/features.c b/lib/cobalt/arch/x86/features.c
index 6deb7dd..4655b60 100644
--- a/lib/cobalt/arch/x86/features.c
+++ b/lib/cobalt/arch/x86/features.c
@@ -37,10 +37,9 @@ void cobalt_check_features(struct cobalt_featinfo *finfo)
                        return;
        }
 
-       report_error("--enable-x86-vsyscall requires NPTL, which does not 
match");
-       report_error_cont("your configuration. Please upgrade, or rebuild the");
-       report_error_cont("Xenomai libraries passing --disable-x86-vsyscall");
-       exit(1);
+       early_warning("--enable-x86-vsyscall requires NPTL, which does not 
match");
+       early_warning("your configuration. Please upgrade, or rebuild the");
+       early_panic("Xenomai libraries passing --disable-x86-vsyscall");
 #endif /* __i386__ && CONFIG_XENO_X86_VSYSCALL */
 }
 
diff --git a/lib/cobalt/assert_context.c b/lib/cobalt/assert_context.c
index 48690dc..da5f2b0 100644
--- a/lib/cobalt/assert_context.c
+++ b/lib/cobalt/assert_context.c
@@ -35,8 +35,7 @@ static void assert_nrt_inner(void)
 
        ret = cobalt_thread_stat(0, &stat);
        if (ret) {
-               report_error("cobalt_thread_stat() failed: %s",
-                       strerror(-ret));
+               warning("cobalt_thread_stat() failed: %s", strerror(-ret));
                return;
        }
 
diff --git a/lib/cobalt/current.c b/lib/cobalt/current.c
index a8bc330..06888b0 100644
--- a/lib/cobalt/current.c
+++ b/lib/cobalt/current.c
@@ -79,16 +79,17 @@ static inline void __cobalt_clear_tsd(void)
 
 static void init_current_keys(void)
 {
-       int err = pthread_key_create(&cobalt_current_key, NULL);
-       if (err)
-               goto error_exit;
-
-       err = pthread_key_create(&cobalt_current_window_key, NULL);
-       if (err) {
-         error_exit:
-               report_error("error creating TSD key: %s", strerror(err));
-               exit(EXIT_FAILURE);
-       }
+       int ret;
+
+       ret = pthread_key_create(&cobalt_current_key, NULL);
+       if (ret)
+               goto fail;
+
+       ret = pthread_key_create(&cobalt_current_window_key, NULL);
+       if (ret == 0)
+               return;
+fail:
+       early_panic("error creating TSD key: %s", strerror(ret));
 }
 
 #endif /* !HAVE_TLS */
@@ -125,11 +126,8 @@ void cobalt_set_tsd(__u32 u_winoff)
        int ret;
 
        ret = XENOMAI_SYSCALL1(sc_cobalt_get_current, &current);
-       if (ret) {
-               report_error("error retrieving current handle: %s",
-                            strerror(-ret));
-               exit(EXIT_FAILURE);
-       }
+       if (ret)
+               panic("cannot retrieve current handle: %s", strerror(-ret));
 
        __cobalt_set_tsd(current, u_winoff);
 
diff --git a/lib/cobalt/init.c b/lib/cobalt/init.c
index 443b86b..c9f0217 100644
--- a/lib/cobalt/init.c
+++ b/lib/cobalt/init.c
@@ -23,16 +23,17 @@
 #include <string.h>
 #include <errno.h>
 #include <signal.h>
+#include <getopt.h>
 #include <limits.h>
 #include <unistd.h>
 #include <semaphore.h>
-#include <boilerplate/ancillaries.h>
+#include <boilerplate/setup.h>
 #include <cobalt/uapi/kernel/heap.h>
 #include <cobalt/ticks.h>
 #include <asm/xenomai/syscall.h>
+#include <xenomai/init.h>
 #include "umm.h"
 #include "internal.h"
-#include "init.h"
 
 /**
  * @ingroup cobalt
@@ -43,8 +44,6 @@
  * Single Unix specification</a> over the Cobalt core.
  */
 
-__weak int __cobalt_defer_init = 0;
-
 __weak int __cobalt_no_shadow = 0;
 
 __weak int __cobalt_control_bind = 0;
@@ -53,11 +52,26 @@ __weak int __cobalt_main_prio = -1;
 
 struct sigaction __cobalt_orig_sigdebug;
 
-pthread_t __cobalt_main_ptid;
+static const struct option cobalt_options[] = {
+       {
+#define no_shadow_opt          0
+               .name = "no-shadow",
+               .flag = &__cobalt_no_shadow,
+               .val = 1
+       },
+       {
+#define main_prio_opt          1
+               .name = "main-prio",
+               .has_arg = 1,
+       },
+       {
+               /* sentinel */
+       }
+};
 
 static void sigill_handler(int sig)
 {
-       const char m[] = "no Xenomai support in kernel?\n";
+       const char m[] = "no Xenomai/cobalt support in kernel?\n";
        ssize_t rc __attribute__ ((unused));
        rc = write(2, m, sizeof(m) - 1);
        exit(EXIT_FAILURE);
@@ -70,16 +84,12 @@ static void low_init(void)
        struct cobalt_featinfo *f;
        int ret;
 
-       if (mlockall(MCL_CURRENT | MCL_FUTURE)) {
-               report_error("mlockall: %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (mlockall(MCL_CURRENT | MCL_FUTURE))
+               early_panic("mlockall: %s", strerror(errno));
 
        old_sigill_handler = signal(SIGILL, sigill_handler);
-       if (old_sigill_handler == SIG_ERR) {
-               report_error("signal(SIGILL): %s", strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (old_sigill_handler == SIG_ERR)
+               early_panic("signal(SIGILL): %s", strerror(errno));
 
        f = &breq.feat_ret;
        breq.feat_req = XENOMAI_FEAT_DEP;
@@ -94,20 +104,12 @@ static void low_init(void)
        case 0:
                break;
        case -EINVAL:
-               report_error("incompatible feature set");
-               report_error_cont("(userland requires \"%s\", kernel provides 
\"%s\", missing=\"%s\")",
-                                 f->feat_man_s, f->feat_all_s, f->feat_mis_s);
-               exit(EXIT_FAILURE);
-
+               early_panic("missing feature: %s", f->feat_mis_s);
        case -ENOEXEC:
-               report_error("incompatible ABI revision level");
-               report_error_cont("(user-space requires '%lu', kernel provides 
'%lu')",
-                       XENOMAI_ABI_REV, f->feat_abirev);
-               exit(EXIT_FAILURE);
-
+               early_panic("ABI mismatch: required r%lu, provided r%lu",
+                           XENOMAI_ABI_REV, f->feat_abirev);
        default:
-               report_error("binding failed: %s", strerror(-ret));
-               exit(EXIT_FAILURE);
+               early_panic("binding failed: %s", strerror(-ret));
        }
 
        cobalt_check_features(f);
@@ -116,27 +118,16 @@ static void low_init(void)
        cobalt_ticks_init(f->clock_freq);
 }
 
-static void __init_cobalt(void);
-
 static void cobalt_fork_handler(void)
 {
        cobalt_unmap_umm();
        cobalt_clear_tsd();
        cobalt_print_init_atfork();
-#ifdef HAVE_PTHREAD_ATFORK
-       /*
-        * Upon fork, in case the parent required init deferral, this
-        * is the forkee's responsibility to call __libcobalt_init()
-        * for bootstrapping the services the same way. On systems
-        * with no fork() support, clients are not supposed to, well,
-        * fork in the first place, so we don't take any provision for
-        * this event.
-        */
-       __init_cobalt();
-#endif
+       if (cobalt_init())
+               exit(EXIT_FAILURE);
 }
 
-void __libcobalt_init(void)
+static void __cobalt_init(void)
 {
        struct sigaction sa;
 
@@ -154,80 +145,52 @@ void __libcobalt_init(void)
         */
        pthread_atfork(NULL, NULL, cobalt_fork_handler);
 
-       if (sizeof(struct cobalt_mutex_shadow) > sizeof(pthread_mutex_t)) {
-               report_error("sizeof(pthread_mutex_t): %d <"
-                            " sizeof(cobalt_mutex_shadow): %d!",
-                            (int) sizeof(pthread_mutex_t),
-                            (int) sizeof(struct cobalt_mutex_shadow));
-               exit(EXIT_FAILURE);
-       }
-       if (sizeof(struct cobalt_cond_shadow) > sizeof(pthread_cond_t)) {
-               report_error("sizeof(pthread_cond_t): %d <"
-                            " sizeof(cobalt_cond_shadow): %d!",
-                            (int) sizeof(pthread_cond_t),
-                            (int) sizeof(struct cobalt_cond_shadow));
-               exit(EXIT_FAILURE);
-       }
-       if (sizeof(struct cobalt_sem_shadow) > sizeof(sem_t)) {
-               report_error("sizeof(sem_t): %d <"
-                            " sizeof(cobalt_sem_shadow): %d!",
-                            (int) sizeof(sem_t),
-                            (int) sizeof(struct cobalt_sem_shadow));
-               exit(EXIT_FAILURE);
-       }
+       if (sizeof(struct cobalt_mutex_shadow) > sizeof(pthread_mutex_t))
+               early_panic("sizeof(pthread_mutex_t): %Zd <"
+                           " sizeof(cobalt_mutex_shadow): %Zd!",
+                           sizeof(pthread_mutex_t),
+                           sizeof(struct cobalt_mutex_shadow));
+
+       if (sizeof(struct cobalt_cond_shadow) > sizeof(pthread_cond_t))
+               early_panic("sizeof(pthread_cond_t): %Zd <"
+                           " sizeof(cobalt_cond_shadow): %Zd!",
+                           sizeof(pthread_cond_t),
+                           sizeof(struct cobalt_cond_shadow));
+
+       if (sizeof(struct cobalt_sem_shadow) > sizeof(sem_t))
+               early_panic("sizeof(sem_t): %Zd <"
+                           " sizeof(cobalt_sem_shadow): %Zd!",
+                           sizeof(sem_t),
+                           sizeof(struct cobalt_sem_shadow));
 
        cobalt_thread_init();
        cobalt_print_init();
-       boilerplate_init();
 }
 
-static inline void dump_configuration(void)
+static inline void commit_stack_memory(void)
 {
-       int n;
-
-       for (n = 0; config_strings[n]; n++)
-               puts(config_strings[n]);
+       char stk[PTHREAD_STACK_MIN];
+       cobalt_commit_memory(stk);
 }
 
-static __libcobalt_ctor void __init_cobalt(void)
+int cobalt_init(void)
 {
        pthread_t ptid = pthread_self();
        struct sched_param parm;
        int policy, ret;
-       const char *p;
-
-       p = getenv("XENO_CONFIG_OUTPUT");
-       if (p && *p) {
-               dump_configuration();
-               _exit(0);
-       }
 
-#ifndef CONFIG_SMP
-       ret = get_static_cpu_count();
-       if (ret > 0)
-               report_error("running non-SMP libraries on SMP kernel?");
-#endif
-
-       __cobalt_main_ptid = ptid;
+       commit_stack_memory();  /* We only need this for the main thread */
        cobalt_default_mutexattr_init();
        cobalt_default_condattr_init();
-
-       if (__cobalt_defer_init)
-               return;
-
-       __libcobalt_init();
+       __cobalt_init();
 
        if (__cobalt_no_shadow)
-               return;
-
-       p = getenv("XENO_NOSHADOW");
-       if (p && *p)
-               return;
+               return 0;
 
        ret = __STD(pthread_getschedparam(ptid, &policy, &parm));
        if (ret) {
-               report_error("pthread_getschedparam: %s", strerror(ret));
-               exit(EXIT_FAILURE);
+               early_warning("pthread_getschedparam failed");
+               return ret;
        }
 
        /*
@@ -250,12 +213,46 @@ static __libcobalt_ctor void __init_cobalt(void)
 
        ret = __RT(pthread_setschedparam(ptid, policy, &parm));
        if (ret) {
-               report_error("pthread_setschedparam: %s", strerror(ret));
-               exit(EXIT_FAILURE);
+               early_warning("pthread_setschedparam failed");
+               return ret;
        }
+
+       return 0;
 }
 
 static void __attribute__((destructor)) __fini_cobalt(void)
 {
        cobalt_print_exit();
 }
+
+static int cobalt_parse_option(int optnum, const char *optarg)
+{
+       switch (optnum) {
+       case main_prio_opt:
+               __cobalt_main_prio = atoi(optarg);
+               break;
+       case no_shadow_opt:
+               break;
+       default:
+               /* Paranoid, can't happen. */
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+static void cobalt_help(void)
+{
+        fprintf(stderr, "--no-shadow                   do not shadow main 
thread\n");
+        fprintf(stderr, "--main-prio=<prio>            set main thread 
priority\n");
+}
+
+static struct setup_descriptor cobalt_interface = {
+       .name = "cobalt",
+       .init = cobalt_init,
+       .options = cobalt_options,
+       .parse_option = cobalt_parse_option,
+       .help = cobalt_help,
+};
+
+core_setup_call(cobalt_interface);
diff --git a/lib/cobalt/init.h b/lib/cobalt/init.h
deleted file mode 100644
index fda3d31..0000000
--- a/lib/cobalt/init.h
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (C) 2013 Philippe Gerum <r...@xenomai.org>.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
-
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
- */
-#ifndef _LIB_COBALT_INIT_H
-#define _LIB_COBALT_INIT_H
-
-/*
- * We give the Cobalt library constructor a high priority, so that
- * extension libraries may assume the core services are available when
- * their own constructor runs. Priorities 0-100 may be reserved by the
- * implementation on some platforms, and we may want to keep some
- * levels free for very high priority inits, so pick 200.
- */
-#define __LIBCOBALT_CTOR_PRIO  200
-
-#define __libcobalt_ctor  __attribute__ ((constructor(__LIBCOBALT_CTOR_PRIO)))
-
-#endif /* _LIB_COBALT_INIT_H */
diff --git a/lib/cobalt/internal.h b/lib/cobalt/internal.h
index f5f119e..26f1a7c 100644
--- a/lib/cobalt/internal.h
+++ b/lib/cobalt/internal.h
@@ -20,6 +20,7 @@
 
 #include <limits.h>
 #include <cobalt/sys/cobalt.h>
+#include <boilerplate/ancillaries.h>
 #include "current.h"
 
 #define COBALT_STACKSIZE_DEFAULT       (PTHREAD_STACK_MIN * 4)
@@ -58,12 +59,12 @@ void cobalt_default_mutexattr_init(void);
 
 void cobalt_default_condattr_init(void);
 
+int cobalt_init(void);
+
 struct cobalt_featinfo;
 
 void cobalt_check_features(struct cobalt_featinfo *finfo);
 
-extern pthread_t __cobalt_main_ptid;
-
 extern struct sigaction __cobalt_orig_sigdebug;
 
 #endif /* _LIB_COBALT_INTERNAL_H */
diff --git a/lib/cobalt/mutex.c b/lib/cobalt/mutex.c
index b84a582..46283cc 100644
--- a/lib/cobalt/mutex.c
+++ b/lib/cobalt/mutex.c
@@ -179,19 +179,23 @@ static int __attribute__((cold)) 
cobalt_mutex_autoinit(pthread_mutex_t *mutex)
        static pthread_mutex_t uninit_errorcheck_mutex =
                PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP;
        pthread_mutexattr_t mattr;
-       int err;
-
-       if (memcmp(mutex, &uninit_normal_mutex, sizeof(*mutex))
-               && memcmp(mutex, &uninit_recursive_mutex, sizeof(*mutex))
-               && memcmp(mutex, &uninit_errorcheck_mutex, sizeof(*mutex)))
+       int ret, type;
+
+       if (memcmp(mutex, &uninit_normal_mutex, sizeof(*mutex)) == 0)
+               type = PTHREAD_MUTEX_DEFAULT;
+       else if (memcmp(mutex, &uninit_recursive_mutex, sizeof(*mutex)) == 0)
+               type = PTHREAD_MUTEX_RECURSIVE_NP;
+       else if (memcmp(mutex, &uninit_errorcheck_mutex, sizeof(*mutex)) == 0)
+               type = PTHREAD_MUTEX_ERRORCHECK_NP;
+       else
                return EINVAL;
 
        pthread_mutexattr_init(&mattr);
-       pthread_mutexattr_settype(&mattr, mutex->__data.__kind);
-       err = __COBALT(pthread_mutex_init(mutex, &mattr));
+       pthread_mutexattr_settype(&mattr, type);
+       ret = __COBALT(pthread_mutex_init(mutex, &mattr));
        pthread_mutexattr_destroy(&mattr);
 
-       return err;
+       return ret;
 }
 
 /**
diff --git a/lib/cobalt/printf.c b/lib/cobalt/printf.c
index d9f3f8b..7c9f61b 100644
--- a/lib/cobalt/printf.c
+++ b/lib/cobalt/printf.c
@@ -712,10 +712,9 @@ void cobalt_print_init(void)
        if (value_str) {
                errno = 0;
                __cobalt_print_bufsz = strtol(value_str, NULL, 10);
-               if (errno || __cobalt_print_bufsz < RT_PRINT_LINE_BREAK) {
-                       report_error("invalid %s", RT_PRINT_BUFFER_ENV);
-                       exit(1);
-               }
+               if (errno || __cobalt_print_bufsz < RT_PRINT_LINE_BREAK)
+                       early_panic("invalid %s=%s",
+                                   RT_PRINT_BUFFER_ENV, value_str);
        }
 
        period = RT_PRINT_DEFAULT_PERIOD;
@@ -723,10 +722,9 @@ void cobalt_print_init(void)
        if (value_str) {
                errno = 0;
                period = strtoll(value_str, NULL, 10);
-               if (errno) {
-                       report_error("invalid %s", RT_PRINT_BUFFER_ENV);
-                       exit(1);
-               }
+               if (errno)
+                       early_panic("invalid %s=%s",
+                                   RT_PRINT_BUFFER_ENV, value_str);
        }
        print_period.tv_sec  = period / 1000;
        print_period.tv_nsec = (period % 1000) * 1000000;
@@ -741,10 +739,9 @@ void cobalt_print_init(void)
                if (value_str) {
                        errno = 0;
                        buffers_count = strtoul(value_str, NULL, 0);
-                       if (errno) {
-                               report_error("invalid %s", 
RT_PRINT_BUFFERS_COUNT_ENV);
-                               exit(1);
-                       }
+                       if (errno)
+                               early_panic("invalid %s=%s",
+                                           RT_PRINT_BUFFERS_COUNT_ENV, 
value_str);
                }
 
                pool_bitmap_len = (buffers_count + __WORDSIZE - 1)
@@ -753,18 +750,14 @@ void cobalt_print_init(void)
                        goto done;
 
                pool_bitmap = malloc(pool_bitmap_len * sizeof(*pool_bitmap));
-               if (!pool_bitmap) {
-                       report_error("error allocating rt_printf buffers");
-                       exit(1);
-               }
+               if (!pool_bitmap)
+                       early_panic("error allocating printf buffers");
 
                pool_buf_size = sizeof(struct print_buffer) + 
__cobalt_print_bufsz;
                pool_len = buffers_count * pool_buf_size;
                pool_start = (unsigned long)malloc(pool_len);
-               if (!pool_start) {
-                       report_error("error allocating rt_printf buffers");
-                       exit(1);
-               }
+               if (!pool_start)
+                       early_panic("error allocating printf buffers");
 
                for (i = 0; i < buffers_count / __WORDSIZE; i++)
                        atomic_long_set(&pool_bitmap[i], ~0UL);
@@ -957,9 +950,7 @@ COBALT_IMPL(int, __vfprintf_chk, (FILE *f, int flag, const 
char *fmt, va_list ap
                return __STD(__vfprintf_chk(f, flag, fmt, ap));
        }
 #else
-       report_error("must build with --enable-fortify to support");
-       report_error_cont("applications compiled with -D_FORTIFY_SOURCE");
-       exit(EXIT_FAILURE);
+       panic("--enable-fortify is required with applications enabling 
_FORTIFY_SOURCE");
 #endif
 }
 
@@ -1003,9 +994,7 @@ COBALT_IMPL(void, __vsyslog_chk, (int pri, int flag, const 
char *fmt, va_list ap
                __STD(__vsyslog_chk(pri, flag, fmt, ap));
        }
 #else
-       report_error("must build with --enable-fortify to support");
-       report_error_cont("applications compiled with -D_FORTIFY_SOURCE");
-       exit(EXIT_FAILURE);
+       panic("--enable-fortify is required with applications enabling 
_FORTIFY_SOURCE");
 #endif
 }
 
diff --git a/lib/cobalt/thread.c b/lib/cobalt/thread.c
index 016a490..57b5bcd 100644
--- a/lib/cobalt/thread.c
+++ b/lib/cobalt/thread.c
@@ -28,7 +28,6 @@
 #include <asm/xenomai/syscall.h>
 #include "current.h"
 #include "internal.h"
-#include <boilerplate/ancillaries.h>
 
 /**
  * @ingroup cobalt_api
@@ -49,14 +48,6 @@ static int linuxthreads;
 
 static int std_maxpri;
 
-static void commit_stack_memory(void)
-{
-       if (pthread_self() == __cobalt_main_ptid) {
-               char stk[PTHREAD_STACK_MIN];
-               cobalt_commit_memory(stk);
-       }
-}
-
 static int libc_setschedparam(pthread_t thread,
                              int policy, const struct sched_param_ex *param_ex)
 {
@@ -120,7 +111,6 @@ static void *cobalt_thread_trampoline(void *p)
        long ret;
 
        cobalt_sigshadow_install_once();
-       commit_stack_memory();
 
        personality = iargs->personality;
        param_ex = iargs->param_ex;
@@ -661,7 +651,6 @@ int pthread_setschedparam_ex(pthread_t thread,
                                &u_winoff, &promoted);
 
        if (ret == 0 && promoted) {
-               commit_stack_memory();
                cobalt_sigshadow_install_once();
                cobalt_set_tsd(u_winoff);
                cobalt_thread_harden();
diff --git a/lib/cobalt/umm.c b/lib/cobalt/umm.c
index 4a881a3..5772256 100644
--- a/lib/cobalt/umm.c
+++ b/lib/cobalt/umm.c
@@ -52,15 +52,15 @@ static void *__map_umm(const char *name, uint32_t *size_r)
 
        fd = __RT(open(name, O_RDWR));
        if (fd < 0) {
-               report_error("cannot open RTDM device %s: %s", name,
-                            strerror(errno));
+               early_warning("cannot open RTDM device %s: %s", name,
+                             strerror(errno));
                return MAP_FAILED;
        }
 
        ret = __RT(ioctl(fd, MEMDEV_RTIOC_STAT, &statbuf));
        if (ret) {
-               report_error("failed getting status of %s: %s",
-                            name, strerror(errno));
+               early_warning("failed getting status of %s: %s",
+                             name, strerror(errno));
                return MAP_FAILED;
        }
 
@@ -102,31 +102,28 @@ void cobalt_unmap_umm(void)
 }
 
 /*
- * Will be called once at library loading time, and when re-binding
- * after a fork.
+ * Will be called once on behalf of xenomai_init(), and when
+ * re-binding after a fork.
  */
 static void init_bind(void)
 {
        cobalt_umm_private = map_umm(COBALT_MEMDEV_PRIVATE, &private_size);
        if (cobalt_umm_private == MAP_FAILED) {
-               report_error("cannot map private umm area: %s",
-                            strerror(errno));
-               report_error_cont("(CONFIG_DEVTMPFS_MOUNT not enabled?)");
-               exit(EXIT_FAILURE);
+               early_warning("cannot map private umm area: %s",
+                             strerror(errno));
+               early_panic("(CONFIG_DEVTMPFS_MOUNT not enabled?)");
        }
 }
 
-/* Will be called only once, at library loading time. */
+/* Will be called only once, upon call to xenomai_init(). */
 static void init_loadup(__u32 vdso_offset)
 {
        uint32_t size;
 
        cobalt_umm_shared = map_umm(COBALT_MEMDEV_SHARED, &size);
-       if (cobalt_umm_shared == MAP_FAILED) {
-               report_error("cannot map shared umm area: %s",
-                            strerror(errno));
-               exit(EXIT_FAILURE);
-       }
+       if (cobalt_umm_shared == MAP_FAILED)
+               early_panic("cannot map shared umm area: %s",
+                           strerror(errno));
 
        cobalt_vdso = (struct xnvdso *)(cobalt_umm_shared + vdso_offset);
 }
diff --git a/lib/copperplate/Makefile.am b/lib/copperplate/Makefile.am
index 21ff51b..2ad5e1e 100644
--- a/lib/copperplate/Makefile.am
+++ b/lib/copperplate/Makefile.am
@@ -12,13 +12,11 @@ libcopperplate_la_SOURCES = \
        init.c          \
        internal.c      \
        internal.h      \
-       main.c          \
        syncobj.c       \
        semobj.c        \
        threadobj.c     \
        timerobj.c      \
-       traceobj.c      \
-       wrappers.c
+       traceobj.c
 
 libcopperplate_la_CPPFLAGS =           \
        @XENO_USER_CFLAGS@              \
@@ -26,10 +24,6 @@ libcopperplate_la_CPPFLAGS =         \
        -I$(top_srcdir)/include         \
        -I$(top_srcdir)/lib
 
-if XENO_MERCURY
-libcopperplate_la_LIBADD += ../boilerplate/libboilerplate.la
-endif
-
 if XENO_REGISTRY
 libcopperplate_la_LIBADD += libregistry.la
 noinst_LTLIBRARIES += libregistry.la
diff --git a/lib/copperplate/heapobj-pshared.c 
b/lib/copperplate/heapobj-pshared.c
index f810ec0..27255a3 100644
--- a/lib/copperplate/heapobj-pshared.c
+++ b/lib/copperplate/heapobj-pshared.c
@@ -40,7 +40,7 @@
 #include "boilerplate/lock.h"
 #include "copperplate/heapobj.h"
 #include "copperplate/debug.h"
-#include "copperplate/init.h"
+#include "xenomai/init.h"
 #include "internal.h"
 
 #define HOBJ_PAGE_SHIFT        9       /* 2^9 => 512 bytes */
diff --git a/lib/copperplate/heapobj-tlsf.c b/lib/copperplate/heapobj-tlsf.c
index e5d30a3..e573380 100644
--- a/lib/copperplate/heapobj-tlsf.c
+++ b/lib/copperplate/heapobj-tlsf.c
@@ -22,8 +22,8 @@
 #include "boilerplate/tlsf/tlsf.h"
 #include "copperplate/heapobj.h"
 #include "copperplate/debug.h"
-#include "copperplate/init.h"
 #include "copperplate/threadobj.h"
+#include "xenomai/init.h"
 #include "internal.h"
 
 #if __WORDSIZE == 32
diff --git a/lib/copperplate/init.c b/lib/copperplate/init.c
index fccb319..08e6a20 100644
--- a/lib/copperplate/init.c
+++ b/lib/copperplate/init.c
@@ -29,6 +29,7 @@
 #include "copperplate/clockobj.h"
 #include "copperplate/registry.h"
 #include "copperplate/timerobj.h"
+#include "xenomai/init.h"
 #include "internal.h"
 
 struct copperplate_setup_data __copperplate_setup_data = {
@@ -76,24 +77,20 @@ static const struct option copperplate_options[] = {
  * code only, such as sysregd. No code traversed should depend on
  * __copperplate_setup_data.
  */
-void copperplate_bootstrap_minimal(const char *arg0, char *mountpt,
-                                  int regflags)
+void copperplate_bootstrap_internal(const char *arg0, char *mountpt,
+                                   int regflags)
 {
        int ret;
 
-       boilerplate_init();
-
        __node_id = get_thread_pid();
 
-       ret = debug_init();
-       if (ret) {
-               warning("failed to initialize debugging features");
-               goto fail;
-       }
+       CPU_ZERO(&__base_setup_data.cpu_affinity);
+
+       __boilerplate_init();
 
        ret = heapobj_pkg_init_private();
        if (ret) {
-               warning("failed to initialize main private heap");
+               early_warning("failed to initialize main private heap");
                goto fail;
        }
 
@@ -209,13 +206,13 @@ static int copperplate_parse_option(int optnum, const 
char *optarg)
 
 static void copperplate_help(void)
 {
-       fprintf(stderr, "--mem-pool-size=<sizeK>          size of the main heap 
(kbytes)\n");
-        fprintf(stderr, "--no-registry                    suppress object 
registration\n");
-        fprintf(stderr, "--registry-root=<path>           root path of 
registry\n");
-        fprintf(stderr, "--session=<label>                label of shared 
multi-processing session\n");
+       fprintf(stderr, "--mem-pool-size=<sizeK>        size of the main heap 
(kbytes)\n");
+        fprintf(stderr, "--no-registry                 suppress object 
registration\n");
+        fprintf(stderr, "--registry-root=<path>                root path of 
registry\n");
+        fprintf(stderr, "--session=<label>             label of shared 
multi-processing session\n");
 }
 
-static struct skin_descriptor copperplate_interface = {
+static struct setup_descriptor copperplate_interface = {
        .name = "copperplate",
        .init = copperplate_init,
        .options = copperplate_options,
@@ -223,7 +220,7 @@ static struct skin_descriptor copperplate_interface = {
        .help = copperplate_help,
 };
 
-DECLARE_SKIN(copperplate_interface, __LIBCOPPERPLATE_CTOR_PRIO);
+copperplate_setup_call(copperplate_interface);
 
 /**
  * @{
diff --git a/lib/copperplate/internal.c b/lib/copperplate/internal.c
index 590c082..d202a41 100644
--- a/lib/copperplate/internal.c
+++ b/lib/copperplate/internal.c
@@ -29,7 +29,6 @@
 #include <boilerplate/ancillaries.h>
 #include <copperplate/clockobj.h>
 #include <copperplate/threadobj.h>
-#include <copperplate/init.h>
 #include "internal.h"
 
 static int thread_spawn_prologue(struct corethread_attributes *cta);
@@ -251,13 +250,13 @@ static int thread_spawn_epilogue(struct 
corethread_attributes *cta)
        return __bt(cta->__reserved.status);
 }
 
-void panic(const char *fmt, ...)
+void __panic(const char *fn, const char *fmt, ...)
 {
        struct threadobj *thobj = threadobj_current();
        va_list ap;
 
        va_start(ap, fmt);
-       __panic(thobj ? threadobj_get_name(thobj) : NULL, fmt, ap);
+       ___panic(fn, thobj ? threadobj_get_name(thobj) : NULL, fmt, ap);
 }
 
 void warning(const char *fmt, ...)
diff --git a/lib/copperplate/internal.h b/lib/copperplate/internal.h
index 582c4a1..5c464a5 100644
--- a/lib/copperplate/internal.h
+++ b/lib/copperplate/internal.h
@@ -87,9 +87,9 @@ struct corethread_attributes {
 
 extern struct copperplate_setup_data __copperplate_setup_data;
 
-static inline void copperplate_set_silent(void)
+static inline void copperplate_set_quiet(void)
 {
-       __base_setup_data.silent_mode = 1;
+       __base_setup_data.quiet_mode = 1;
 }
 
 #ifdef __cplusplus
@@ -106,8 +106,8 @@ int copperplate_create_thread(struct corethread_attributes 
*cta,
 int copperplate_renice_local_thread(pthread_t ptid, int policy,
                                    const struct sched_param_ex *param_ex);
 
-void copperplate_bootstrap_minimal(const char *arg0,
-                                  char *mountpt, int regflags);
+void copperplate_bootstrap_internal(const char *arg0,
+                                   char *mountpt, int regflags);
 
 #ifdef __cplusplus
 }
diff --git a/lib/copperplate/regd/Makefile.am b/lib/copperplate/regd/Makefile.am
index 5eb0c63..69c7e07 100644
--- a/lib/copperplate/regd/Makefile.am
+++ b/lib/copperplate/regd/Makefile.am
@@ -1,21 +1,16 @@
 sbin_PROGRAMS = sysregd
 
-if XENO_COBALT
-coredep_lib = ../../cobalt/libcobalt.la
-else
-coredep_lib =
-endif
-
-CPPFLAGS =                                             \
-       @XENO_USER_CFLAGS@                              \
-       @XENO_FUSE_CFLAGS@                              \
+CPPFLAGS =                     \
+       @XENO_USER_CFLAGS@      \
+       @XENO_FUSE_CFLAGS@      \
+       -I$(top_srcdir)/lib     \
        -I$(top_srcdir)/include
 
 LDFLAGS = $(XENO_POSIX_WRAPPERS)
 
 LDADD =                        \
        ../libcopperplate.la    \
-       $(coredep_lib)          \
+       ../../@XENO_CORE_LIB@   \
        @XENO_USER_LDADD@       \
        -lpthread -lrt
 
diff --git a/lib/copperplate/regd/regd.c b/lib/copperplate/regd/regd.c
index e544431..338a650 100644
--- a/lib/copperplate/regd/regd.c
+++ b/lib/copperplate/regd/regd.c
@@ -400,6 +400,30 @@ static void cleanup_handler(int sig)
        _exit(1);
 }
 
+#ifdef CONFIG_XENO_COBALT
+
+#include "cobalt/internal.h"
+
+/*
+ * Bootstrapping Cobalt is something which is normally done through
+ * xenomai_bootstrap(), as available from lib/xenomai/bootstrap.o for
+ * normal applications. But sysregd is a peculiar one, and we need to
+ * drive the init sequence specifically for it.
+ */
+static inline int bootstrap_core(void)
+{
+       return cobalt_init();
+}
+
+#else
+
+static inline int bootstrap_core(void)
+{
+       return 0;
+}
+
+#endif
+
 static void create_system_fs(const char *arg0, const char *rootdir, int flags)
 {
        struct sysreg_fsfile *f;
@@ -438,11 +462,14 @@ static void create_system_fs(const char *arg0, const char 
*rootdir, int flags)
 bootstrap:
        atexit(delete_system_fs);
 
-       CPU_ZERO(&__base_setup_data.cpu_affinity);
+       ret = bootstrap_core();
+       if (ret)
+               error(1, -ret, "cannot bootstap core interface");
+
        __copperplate_setup_data.session_label = session;
        __copperplate_setup_data.registry_root = rootdir;
        sysroot = mountpt;
-       copperplate_bootstrap_minimal(arg0, mountpt, flags);
+       copperplate_bootstrap_internal(arg0, mountpt, flags);
 
        note("mounted system fs at %s", mountpt);
 
diff --git a/lib/copperplate/registry.c b/lib/copperplate/registry.c
index ac041f1..fb8315e 100644
--- a/lib/copperplate/registry.c
+++ b/lib/copperplate/registry.c
@@ -45,7 +45,7 @@
 #include "copperplate/clockobj.h"
 #include "boilerplate/lock.h"
 #include "copperplate/debug.h"
-#include "copperplate/init.h"
+#include "xenomai/init.h"
 #include "internal.h"
 
 /*
diff --git a/lib/copperplate/traceobj.c b/lib/copperplate/traceobj.c
index f93975f..a06cfd9 100644
--- a/lib/copperplate/traceobj.c
+++ b/lib/copperplate/traceobj.c
@@ -21,7 +21,7 @@
 #include "copperplate/traceobj.h"
 #include "copperplate/threadobj.h"
 #include "copperplate/heapobj.h"
-#include "copperplate/init.h"
+#include "xenomai/init.h"
 #include "internal.h"
 #ifdef CONFIG_XENO_VALGRIND_API
 #include <valgrind/valgrind.h>
diff --git a/lib/mercury/Makefile.am b/lib/mercury/Makefile.am
new file mode 100644
index 0000000..d2b0621
--- /dev/null
+++ b/lib/mercury/Makefile.am
@@ -0,0 +1,9 @@
+
+lib_LTLIBRARIES = libmercury.la
+
+libmercury_la_SOURCES =
+
+libmercury_la_LDFLAGS = @XENO_LIB_LDFLAGS@ -version-info 0:0:0 -lpthread -lrt
+
+libmercury_la_LIBADD = \
+       ../boilerplate/libboilerplate.la
diff --git a/lib/psos/Makefile.am b/lib/psos/Makefile.am
index 6abaf95..4eb7ad8 100644
--- a/lib/psos/Makefile.am
+++ b/lib/psos/Makefile.am
@@ -4,7 +4,6 @@ libpsos_la_LDFLAGS = @XENO_LIB_LDFLAGS@ -version-info 0:0:0
 
 libpsos_la_SOURCES =   \
        init.c          \
-       init.h          \
        internal.h      \
        pt.c            \
        pt.h            \
diff --git a/lib/psos/init.c b/lib/psos/init.c
index c57afeb..be4e157 100644
--- a/lib/psos/init.c
+++ b/lib/psos/init.c
@@ -21,12 +21,11 @@
 #include <stdlib.h>
 #include <unistd.h>
 #include <getopt.h>
-#include <copperplate/init.h>
+#include <xenomai/init.h>
 #include <copperplate/registry.h>
 #include <copperplate/clockobj.h>
 #include <copperplate/debug.h>
 #include <psos/psos.h>
-#include "init.h"
 #include "internal.h"
 #include "tm.h"
 #include "task.h"
@@ -95,8 +94,8 @@ static int psos_parse_option(int optnum, const char *optarg)
 
 static void psos_help(void)
 {
-        fprintf(stderr, "--psos-clock-resolution=<ns>    tick value (default 
1ms)\n");
-        fprintf(stderr, "--psos-time-slice=<psos-ticks>  round-robin time 
slice\n");
+        fprintf(stderr, "--psos-clock-resolution=<ns>  tick value (default 
1ms)\n");
+        fprintf(stderr, "--psos-time-slice=<psos-ticks>        round-robin 
time slice\n");
 }
 
 static int psos_init(void)
@@ -141,7 +140,7 @@ const char *__psos_maybe_short_name(char shrt[5], const 
char *lng)
        return (const char *)shrt;
 }
 
-static struct skin_descriptor psos_skin = {
+static struct setup_descriptor psos_skin = {
        .name = "psos",
        .init = psos_init,
        .options = psos_options,
@@ -149,4 +148,4 @@ static struct skin_descriptor psos_skin = {
        .help = psos_help,
 };
 
-DECLARE_SKIN(psos_skin, __LIBPSOS_CTOR_PRIO);
+interface_setup_call(psos_skin);
diff --git a/lib/psos/init.h b/lib/psos/init.h
deleted file mode 100644
index 34d832f..0000000
--- a/lib/psos/init.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2014 Philippe Gerum <r...@xenomai.org>.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
-
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
- */
-#ifndef _PSOS_INIT_H
-#define _PSOS_INIT_H
-
-#define __LIBPSOS_CTOR_PRIO  300
-
-#endif /* _PSOS_INIT_H */
diff --git a/lib/psos/pt.c b/lib/psos/pt.c
index aac253b..324ece6 100644
--- a/lib/psos/pt.c
+++ b/lib/psos/pt.c
@@ -21,7 +21,6 @@
 #include <errno.h>
 #include <stdlib.h>
 #include <memory.h>
-#include <copperplate/init.h>
 #include <copperplate/cluster.h>
 #include <boilerplate/lock.h>
 #include <psos/psos.h>
diff --git a/lib/psos/queue.c b/lib/psos/queue.c
index e9cd782..fce091c 100644
--- a/lib/psos/queue.c
+++ b/lib/psos/queue.c
@@ -24,7 +24,6 @@
 #include <copperplate/threadobj.h>
 #include <copperplate/heapobj.h>
 #include <copperplate/clockobj.h>
-#include <copperplate/init.h>
 #include <copperplate/cluster.h>
 #include <psos/psos.h>
 #include "internal.h"
diff --git a/lib/psos/rn.c b/lib/psos/rn.c
index fec88ed..5fb1724 100644
--- a/lib/psos/rn.c
+++ b/lib/psos/rn.c
@@ -21,7 +21,6 @@
 #include <errno.h>
 #include <stdlib.h>
 #include <memory.h>
-#include <copperplate/init.h>
 #include <copperplate/threadobj.h>
 #include <copperplate/clockobj.h>
 #include <psos/psos.h>
diff --git a/lib/psos/sem.c b/lib/psos/sem.c
index 8f20be0..5535cda 100644
--- a/lib/psos/sem.c
+++ b/lib/psos/sem.c
@@ -22,7 +22,6 @@
 #include <stdlib.h>
 #include <string.h>
 #include <copperplate/heapobj.h>
-#include <copperplate/init.h>
 #include <copperplate/cluster.h>
 #include <copperplate/clockobj.h>
 #include <copperplate/semobj.h>
diff --git a/lib/psos/task.c b/lib/psos/task.c
index a8a53a7..5142e36 100644
--- a/lib/psos/task.c
+++ b/lib/psos/task.c
@@ -24,7 +24,6 @@
 #include <unistd.h>
 #include <pthread.h>
 #include <sched.h>
-#include "copperplate/init.h"
 #include "copperplate/heapobj.h"
 #include "copperplate/threadobj.h"
 #include "copperplate/syncobj.h"
diff --git a/lib/smokey/init.c b/lib/smokey/init.c
index 1fc6e7f..e5ccf0a 100644
--- a/lib/smokey/init.c
+++ b/lib/smokey/init.c
@@ -27,8 +27,8 @@
 #include <fnmatch.h>
 #include <boilerplate/list.h>
 #include <boilerplate/ancillaries.h>
-#include <copperplate/init.h>
 #include "copperplate/internal.h"
+#include <xenomai/init.h>
 #include <smokey/smokey.h>
 
 /**
@@ -266,22 +266,15 @@ static const struct option smokey_options[] = {
                .val = 1,
        },
        {
-#define quiet_opt      3
-               .name = "quiet",
-               .flag = &smokey_quiet_mode,
-               .val = 1,
-       },
-       {
                /* sentinel */
        }
 };
 
 static void smokey_help(void)
 {
-        fprintf(stderr, "--keep-going                  don't stop upon test 
error\n");
-        fprintf(stderr, "--quiet                       require tests to tame 
down verbosity\n");
-       fprintf(stderr, "--list                         list all tests\n");
-       fprintf(stderr, "--run[=<id[,id...]>]]          run [portion of] test 
list\n");
+        fprintf(stderr, "--keep-going                  don't stop upon test 
error\n");
+       fprintf(stderr, "--list                         list all tests\n");
+       fprintf(stderr, "--run[=<id[,id...]>]]          run [portion of] the 
test list\n");
 }
 
 static inline void pick_test_range(int start, int end)
@@ -427,7 +420,6 @@ static int smokey_parse_option(int optnum, const char 
*optarg)
 
        switch (optnum) {
        case keep_going_opt:
-       case quiet_opt:
                break;
        case run_opt:
                if (pvlist_empty(&register_list)) {
@@ -456,12 +448,14 @@ static int smokey_parse_option(int optnum, const char 
*optarg)
 static int smokey_init(void)
 {
        if (pvlist_empty(&smokey_test_list))
-               copperplate_set_silent();
+               copperplate_set_quiet();
+       else
+               smokey_quiet_mode = __base_setup_data.quiet_mode;
 
        return 0;
 }
 
-static struct skin_descriptor smokey_interface = {
+static struct setup_descriptor smokey_interface = {
        .name = "smokey",
        .init = smokey_init,
        .options = smokey_options,
@@ -469,4 +463,4 @@ static struct skin_descriptor smokey_interface = {
        .help = smokey_help,
 };
 
-DECLARE_SKIN(smokey_interface, __SMOKEYPLUG_CTOR_PRIO+1);
+post_setup_call(smokey_interface);
diff --git a/lib/trank/Makefile.am b/lib/trank/Makefile.am
index 89b2f13..816a1a4 100644
--- a/lib/trank/Makefile.am
+++ b/lib/trank/Makefile.am
@@ -5,7 +5,6 @@ libtrank_la_LDFLAGS = @XENO_LIB_LDFLAGS@ -version-info 0:0:0
 
 libtrank_la_SOURCES =  \
        init.c          \
-       init.h          \
        internal.c      \
        internal.h      \
        posix.c         \
diff --git a/lib/trank/init.c b/lib/trank/init.c
index 5773c79..ebb5925 100644
--- a/lib/trank/init.c
+++ b/lib/trank/init.c
@@ -15,7 +15,7 @@
  * License along with this library; if not, write to the Free Software
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
  */
-#include "init.h"
+#include <xenomai/init.h>
 #include "internal.h"
 
 /**
@@ -29,9 +29,9 @@
  * over Xenomai 3.x.
  */
 
-#define __libtrank_ctor  __attribute__ ((constructor(__LIBTRANK_CTOR_PRIO)))
+static struct setup_descriptor trank_interface = {
+       .name = "trank",
+       .init = trank_init_interface,
+};
 
-static __libtrank_ctor void init_trank(void)
-{
-       trank_init_interface();
-}
+post_setup_call(trank_interface);
diff --git a/lib/trank/init.h b/lib/trank/init.h
deleted file mode 100644
index 182b109..0000000
--- a/lib/trank/init.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2014 Philippe Gerum <r...@xenomai.org>.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
-
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
- */
-#ifndef _TRANK_INIT_H
-#define _TRANK_INIT_H
-
-#define __LIBTRANK_CTOR_PRIO  350
-
-#endif /* !_TRANK_INIT_H */
diff --git a/lib/trank/internal.c b/lib/trank/internal.c
index 927992f..585fc36 100644
--- a/lib/trank/internal.c
+++ b/lib/trank/internal.c
@@ -53,10 +53,8 @@ static void trank_init_context(void)
        struct trank_context *tc;
 
        tc = malloc(sizeof(*tc));
-       if (tc == NULL) {
-               report_error("error creating TSD: %s\n", strerror(ENOMEM));
-               exit(EXIT_FAILURE);
-       }
+       if (tc == NULL)
+               early_panic("error creating TSD: %s", strerror(ENOMEM));
                
        memset(tc, 0, sizeof(*tc));
        pthread_setspecific(trank_context_key, tc);
@@ -85,17 +83,17 @@ static struct cobalt_tsd_hook tsd_hook = {
        .delete_tsd = trank_destroy_context,
 };
 
-void trank_init_interface(void)
+int trank_init_interface(void)
 {
 #ifndef HAVE_TLS
        int ret;
 
        ret = pthread_key_create(&trank_context_key, __trank_destroy_context);
-       if (ret) {
-               report_error("error creating TSD key: %s\n", strerror(ret));
-               exit(EXIT_FAILURE);
-       }
+       if (ret)
+               early_panic("error creating TSD key: %s", strerror(ret));
 #endif
        sigaddset(&trank_sigperiod_set, SIGPERIOD);
        cobalt_register_tsd_hook(&tsd_hook);
+
+       return 0;
 }
diff --git a/lib/trank/internal.h b/lib/trank/internal.h
index 93ba9f1..5fd9d7e 100644
--- a/lib/trank/internal.h
+++ b/lib/trank/internal.h
@@ -47,7 +47,7 @@ static inline struct trank_context *trank_get_context(void)
 
 #endif
 
-void trank_init_interface(void);
+int trank_init_interface(void);
 
 extern sigset_t trank_sigperiod_set;
 
diff --git a/lib/vxworks/Makefile.am b/lib/vxworks/Makefile.am
index 483d811..a123864 100644
--- a/lib/vxworks/Makefile.am
+++ b/lib/vxworks/Makefile.am
@@ -4,7 +4,6 @@ libvxworks_la_LDFLAGS = @XENO_LIB_LDFLAGS@ -version-info 0:0:0
 
 libvxworks_la_SOURCES = \
        init.c          \
-       init.h          \
        errnoLib.c      \
        intLib.c        \
        kernLib.c       \
diff --git a/lib/vxworks/init.c b/lib/vxworks/init.c
index d1f0581..7f1b487 100644
--- a/lib/vxworks/init.c
+++ b/lib/vxworks/init.c
@@ -20,9 +20,8 @@
 #include <stdlib.h>
 #include <unistd.h>
 #include <getopt.h>
-#include <copperplate/init.h>
+#include <xenomai/init.h>
 #include <vxworks/errnoLib.h>
-#include "init.h"
 #include "tickLib.h"
 #include "taskLib.h"
 
@@ -75,7 +74,7 @@ static int vxworks_parse_option(int optnum, const char 
*optarg)
 
 static void vxworks_help(void)
 {
-        fprintf(stderr, "--vxworks-clock-resolution=<ns>  tick value (default 
1ms)\n");
+        fprintf(stderr, "--vxworks-clock-resolution=<ns> tick value (default 
1ms)\n");
 }
 
 static int vxworks_init(void)
@@ -102,7 +101,7 @@ static int vxworks_init(void)
        return 0;
 }
 
-static struct skin_descriptor vxworks_skin = {
+static struct setup_descriptor vxworks_skin = {
        .name = "vxworks",
        .init = vxworks_init,
        .options = vxworks_options,
@@ -110,4 +109,4 @@ static struct skin_descriptor vxworks_skin = {
        .help = vxworks_help,
 };
 
-DECLARE_SKIN(vxworks_skin, __LIBVXWORKS_CTOR_PRIO);
+interface_setup_call(vxworks_skin);
diff --git a/lib/vxworks/init.h b/lib/vxworks/init.h
deleted file mode 100644
index 2f35162..0000000
--- a/lib/vxworks/init.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2014 Philippe Gerum <r...@xenomai.org>.
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
-
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
- */
-#ifndef _VXWORKS_INIT_H
-#define _VXWORKS_INIT_H
-
-#define __LIBVXWORKS_CTOR_PRIO  300
-
-#endif /* _VXWORKS_INIT_H */
diff --git a/lib/vxworks/memPartLib.c b/lib/vxworks/memPartLib.c
index ee9f5cc..7bb5c6a 100644
--- a/lib/vxworks/memPartLib.c
+++ b/lib/vxworks/memPartLib.c
@@ -22,7 +22,6 @@
 #include <memory.h>
 #include <boilerplate/lock.h>
 #include <copperplate/heapobj.h>
-#include <copperplate/init.h>
 #include <vxworks/errnoLib.h>
 #include <vxworks/memPartLib.h>
 #include "memPartLib.h"
diff --git a/lib/vxworks/semLib.c b/lib/vxworks/semLib.c
index d033289..73397cc 100644
--- a/lib/vxworks/semLib.c
+++ b/lib/vxworks/semLib.c
@@ -21,7 +21,6 @@
 #include <stdlib.h>
 #include <limits.h>
 #include <copperplate/heapobj.h>
-#include <copperplate/init.h>
 #include <vxworks/errnoLib.h>
 #include "reference.h"
 #include "taskLib.h"
diff --git a/lib/vxworks/taskLib.c b/lib/vxworks/taskLib.c
index 81540c4..340afc7 100644
--- a/lib/vxworks/taskLib.c
+++ b/lib/vxworks/taskLib.c
@@ -29,7 +29,6 @@
 #include "tickLib.h"
 #include "msgQLib.h"
 #include "taskHookLib.h"
-#include "copperplate/init.h"
 #include "copperplate/heapobj.h"
 #include "copperplate/threadobj.h"
 #include "copperplate/syncobj.h"
diff --git a/lib/vxworks/tickLib.c b/lib/vxworks/tickLib.c
index b1f6a5d..9f7ec5a 100644
--- a/lib/vxworks/tickLib.c
+++ b/lib/vxworks/tickLib.c
@@ -21,7 +21,6 @@
 #include <string.h>
 #include <stdlib.h>
 #include <unistd.h>
-#include <copperplate/init.h>
 #include <boilerplate/lock.h>
 #include <vxworks/tickLib.h>
 #include "tickLib.h"
diff --git a/scripts/wrap-link.sh b/scripts/wrap-link.sh
index 24a270e..1b8c3f4 100755
--- a/scripts/wrap-link.sh
+++ b/scripts/wrap-link.sh
@@ -139,9 +139,9 @@ while test $# -gt 0; do
            ;;
 
        -Wl,--wrap,main|-Wl,--wrap=main|-Wl,--dynamic-list=*)
-           # special case so that Copperplate can interpose on the
-           # main() routine. For this we need this wrapping to
-           # take place in the second stage.
+           # special case so that we can interpose on the main()
+           # routine. For this we need this wrapping to take place in
+           # the second stage.
            stage2_args="$stage2_args $arg"
            ;;
 
diff --git a/scripts/xeno-config-cobalt.in b/scripts/xeno-config-cobalt.in
index d2ee3fd..c6e51d1 100644
--- a/scripts/xeno-config-cobalt.in
+++ b/scripts/xeno-config-cobalt.in
@@ -18,7 +18,7 @@ XENO_BASE_CFLAGS="-I$XENO_INCLUDE_DIR/cobalt 
-I$XENO_INCLUDE_DIR @XENO_USER_APP_
 XENO_POSIX_LDFLAGS="-L${staging}${libdir} -lcobalt -lpthread -lrt 
@XENO_USER_APP_LDFLAGS@"
 XENO_LIBRARY_DIR="${staging}${libdir}"
 LD_FILE_OPTION="@LD_FILE_OPTION@"
-WRAP_MAIN_OPT="-Wl,--wrap=main 
-Wl,--dynamic-list=${XENO_LIBRARY_DIR}/dynlist.ld"
+WRAP_MAIN_OPT="${staging}${libdir}/xenomai/bootstrap.o -Wl,--wrap=main 
-Wl,--dynamic-list=${XENO_LIBRARY_DIR}/dynlist.ld"
 WRAP_MAIN="$WRAP_MAIN_OPT"
 
 unset prefix exec_prefix libdir datadir datarootdir pkgdatadir includedir 
skin_list compat
@@ -246,7 +246,7 @@ if test x$do_ldflags = xy; then
                # with --cobalt. On the contrary, --posix does.
                ;;
            vxworks|psos|alchemy|smokey)
-               copperplate="$WRAP_MAIN -lcopperplate"
+               copperplate="-lcopperplate"
                ldflags="$ldflags -l$skin"
                if [ -r ${XENO_LIBRARY_DIR}/${skin}.wrappers ]; then
                    ldflags=" `dump_wrappers ${skin}.wrappers` $ldflags"
@@ -258,7 +258,7 @@ if test x$do_ldflags = xy; then
                ;;
        esac
     done
-    echo "$ldflags $copperplate $XENO_POSIX_LDFLAGS"
+    echo "$ldflags $copperplate $WRAP_MAIN $XENO_POSIX_LDFLAGS"
 fi
 
 exit 0
diff --git a/scripts/xeno-config-mercury.in b/scripts/xeno-config-mercury.in
index 88852e6..2145182 100644
--- a/scripts/xeno-config-mercury.in
+++ b/scripts/xeno-config-mercury.in
@@ -15,9 +15,9 @@ XENO_CC="@CC@"
 XENO_TARGET_ARCH="@XENO_BUILD_STRING@"
 XENO_INCLUDE_DIR="${staging}${includedir}"
 XENO_BASE_CFLAGS="-I$XENO_INCLUDE_DIR/mercury -I$XENO_INCLUDE_DIR 
@XENO_USER_APP_CFLAGS@ -D__MERCURY__"
-XENO_BASE_LDFLAGS="-L${staging}${libdir} -lcopperplate -lpthread -lrt 
@XENO_USER_APP_LDFLAGS@"
+XENO_BASE_LDFLAGS="-L${staging}${libdir} -lmercury -lpthread -lrt 
@XENO_USER_APP_LDFLAGS@"
 XENO_LIBRARY_DIR="${staging}${libdir}"
-WRAP_MAIN_OPT="-Wl,--wrap=main 
-Wl,--dynamic-list=${XENO_LIBRARY_DIR}/dynlist.ld"
+WRAP_MAIN_OPT="${staging}${libdir}/xenomai/bootstrap.o -Wl,--wrap=main 
-Wl,--dynamic-list=${XENO_LIBRARY_DIR}/dynlist.ld"
 WRAP_MAIN="$WRAP_MAIN_OPT"
 
 unset prefix exec_prefix libdir datadir datarootdir pkgdatadir includedir 
skin_list
@@ -182,12 +182,14 @@ fi
 
 if test x$do_ldflags = xy; then
     test -z "$skin_list" && skin_list=posix
-    ldflags="$WRAP_MAIN $XENO_BASE_LDFLAGS"
+    ldflags=
+    copperplate=
     for skin in $skin_list; do
        case "$skin" in
            posix|rtdm)
                ;;
            vxworks|psos|alchemy|smokey)
+               copperplate="-lcopperplate"
                ldflags="-l$skin $ldflags"
                ;;
            *)
@@ -196,7 +198,7 @@ if test x$do_ldflags = xy; then
                ;;
        esac
     done
-    echo $ldflags
+    echo "$ldflags $copperplate $WRAP_MAIN $XENO_BASE_LDFLAGS"
 fi
 
 exit 0
diff --git a/testsuite/clocktest/Makefile.am b/testsuite/clocktest/Makefile.am
index 4692ce8..7290063 100644
--- a/testsuite/clocktest/Makefile.am
+++ b/testsuite/clocktest/Makefile.am
@@ -10,7 +10,7 @@ clocktest_CPPFLAGS =                                  \
        $(XENO_USER_CFLAGS)                             \
        -I$(top_srcdir)/include
 
-clocktest_LDFLAGS = $(XENO_POSIX_WRAPPERS)
+clocktest_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 clocktest_LDADD =                      \
        ../../lib/cobalt/libcobalt.la   \
diff --git a/testsuite/latency/Makefile.am b/testsuite/latency/Makefile.am
index b58bf40..cfa18c4 100644
--- a/testsuite/latency/Makefile.am
+++ b/testsuite/latency/Makefile.am
@@ -10,14 +10,9 @@ latency_CPPFLAGS =           \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-latency_LDFLAGS = $(XENO_POSIX_WRAPPERS)
+latency_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
-core_libs =
-if XENO_COBALT
-core_libs += ../../lib/cobalt/libcobalt.la
-endif
-
-latency_LDADD =                        \
-       $(core_libs)            \
-        @XENO_USER_LDADD@      \
+latency_LDADD =                                \
+       ../../lib/@XENO_CORE_LIB@       \
+        @XENO_USER_LDADD@              \
        -lpthread -lrt -lm
diff --git a/testsuite/regression/posix/Makefile.am 
b/testsuite/regression/posix/Makefile.am
index f975984..01aab8e 100644
--- a/testsuite/regression/posix/Makefile.am
+++ b/testsuite/regression/posix/Makefile.am
@@ -13,7 +13,7 @@ test_PROGRAMS = \
 CPPFLAGS = $(XENO_USER_CFLAGS)                 \
        -I$(top_srcdir)/include
 
-LDFLAGS = $(XENO_POSIX_WRAPPERS)
+LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 LDADD =                                        \
        ../../../lib/cobalt/libcobalt.la        \
diff --git a/testsuite/smokey/Makefile.am b/testsuite/smokey/Makefile.am
index 9ee9cf0..70192a9 100644
--- a/testsuite/smokey/Makefile.am
+++ b/testsuite/smokey/Makefile.am
@@ -5,9 +5,7 @@ CCLD = $(top_srcdir)/scripts/wrap-link.sh $(CC)
 
 smokey_SOURCES = main.c
 
-core_libs =
 if XENO_COBALT
-core_libs += ../../lib/cobalt/libcobalt.la
 wrappers = $(XENO_POSIX_WRAPPERS)
 SUBDIRS =              \
        arith           \
@@ -38,14 +36,13 @@ smokey_CPPFLAGS =                   \
        $(XENO_USER_CFLAGS)             \
        -I$(top_srcdir)/include
 
-smokey_LDFLAGS=$(wrappers) -Wl,--wrap=main \
-       -Wl,--dynamic-list=$(top_srcdir)/scripts/dynlist.ld $(undef_list)
+smokey_LDFLAGS=$(wrappers) @XENO_AUTOINIT_LDFLAGS@ $(undef_list)
 
 smokey_LDADD =                                         \
        $(plugin_list)                          \
        ../../lib/smokey/libsmokey.la           \
        ../../lib/copperplate/libcopperplate.la \
-       $(core_libs)                            \
+       ../../lib/@XENO_CORE_LIB@               \
         @XENO_USER_LDADD@                      \
        -lpthread -lrt
 
diff --git a/testsuite/switchtest/Makefile.am b/testsuite/switchtest/Makefile.am
index a86389c..c479cc3 100644
--- a/testsuite/switchtest/Makefile.am
+++ b/testsuite/switchtest/Makefile.am
@@ -6,13 +6,13 @@ test_PROGRAMS = switchtest
 
 switchtest_SOURCES = switchtest.c
 
-switchtest_CPPFLAGS =                                  \
-       $(XENO_USER_CFLAGS)                             \
+switchtest_CPPFLAGS =                  \
+       $(XENO_USER_CFLAGS)             \
        -I$(top_srcdir)/include
 
-switchtest_LDFLAGS =  $(XENO_POSIX_WRAPPERS)
+switchtest_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 switchtest_LDADD =                     \
-       ../../lib/cobalt/libcobalt.la   \
+       ../../lib/@XENO_CORE_LIB@       \
        @XENO_USER_LDADD@               \
        -lpthread -lrt
diff --git a/utils/analogy/Makefile.am b/utils/analogy/Makefile.am
index 42d5309..6b91121 100644
--- a/utils/analogy/Makefile.am
+++ b/utils/analogy/Makefile.am
@@ -15,8 +15,6 @@ CPPFLAGS =                                            \
        -I$(top_srcdir)/include                         \
         -I$(top_srcdir)/lib/analogy
 
-LDFLAGS =
-
 noinst_HEADERS = wf_facilities.h analogy_calibrate.h calibration_ni_m.h
 
 noinst_LTLIBRARIES = libwaveform.la
@@ -25,14 +23,16 @@ libwaveform_la_SOURCES = wf_facilities.c
 
 analogy_config_SOURCES = analogy_config.c
 analogy_config_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lrt -lpthread
+       -lrt -lpthread -lm
 
 analogy_calibrate_SOURCES = analogy_calibrate.c calibration_ni_m.c
 analogy_calibrate.c: calibration_ni_m.h
 analogy_calibrate_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
@@ -40,53 +40,61 @@ analogy_calibrate_LDADD = \
 
 cmd_read_SOURCES = cmd_read.c
 cmd_read_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/alchemy/libalchemy.la \
        ../../lib/copperplate/libcopperplate.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 cmd_write_SOURCES = cmd_write.c
 cmd_write_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/alchemy/libalchemy.la \
        ../../lib/copperplate/libcopperplate.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 cmd_bits_SOURCES = cmd_bits.c
 cmd_bits_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 insn_read_SOURCES = insn_read.c
 insn_read_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 insn_write_SOURCES = insn_write.c
 insn_write_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 insn_bits_SOURCES = insn_bits.c
 insn_bits_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
        ../../lib/analogy/libanalogy.la \
        ../../lib/cobalt/libcobalt.la   \
        @XENO_USER_LDADD@               \
-       -lpthread -lrt
+       -lrt -lpthread -lm
 
 wf_generate_SOURCES = wf_generate.c
-wf_generate_LDADD = ./libwaveform.la -lm
-
-
-.PHONY: git-stamp
-
+wf_generate_LDADD = \
+       @XENO_AUTOINIT_LDFLAGS@         \
+        ./libwaveform.la \
+       ../../lib/analogy/libanalogy.la \
+       ../../lib/cobalt/libcobalt.la   \
+       @XENO_USER_LDADD@               \
+       -lrt -lpthread -lm
diff --git a/utils/autotune/Makefile.am b/utils/autotune/Makefile.am
index 22a387d..3ba6032 100644
--- a/utils/autotune/Makefile.am
+++ b/utils/autotune/Makefile.am
@@ -9,7 +9,7 @@ autotune_CPPFLAGS =             \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-autotune_LDFLAGS = $(XENO_POSIX_WRAPPERS)
+autotune_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 autotune_LDADD =                       \
        ../../lib/cobalt/libcobalt.la   \
diff --git a/utils/autotune/autotune.c b/utils/autotune/autotune.c
index 3ea6672..de1365b 100644
--- a/utils/autotune/autotune.c
+++ b/utils/autotune/autotune.c
@@ -16,7 +16,6 @@
  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
  * 02111-1307, USA.
  */
-#include <xeno_config.h>
 #include <fcntl.h>
 #include <unistd.h>
 #include <getopt.h>
@@ -28,10 +27,14 @@
 #include <error.h>
 #include <sys/cobalt.h>
 #include <rtdm/autotune.h>
+#include <boilerplate/setup.h>
 
 static int tune_irqlat, tune_kernlat, tune_userlat;
 
-static int reset, noload, quiet, background;
+static int reset, noload, background;
+
+/* --quiet[=2] means fully quiet, quiet=1 means almost quiet */
+#define quiet_mode (__base_setup_data.quiet_mode)
 
 static const struct option base_options[] = {
        {
@@ -72,24 +75,12 @@ static const struct option base_options[] = {
                .val = 1
        },
        {
-#define quiet_opt      6
-               .name = "quiet",
-               .flag = &quiet,
-               .val = 2
-       },
-       {
-#define semiquiet_opt  7
-               .name = "semi-quiet",
-               .flag = &quiet,
-               .val = 1
-       },
-       {
-#define period_opt     8
+#define period_opt     6
                .name = "period",
                .has_arg = 1,
        },
        {
-#define background_opt 9
+#define background_opt 7
                .name = "background",
                .flag = &background,
                .val = 1,
@@ -212,9 +203,7 @@ static void usage(void)
        fprintf(stderr, "   --period            set the sampling period\n");
        fprintf(stderr, "   --reset             reset core timer gravity to 
factory defaults\n");
        fprintf(stderr, "   --noload            disable load generation\n");
-       fprintf(stderr, "   --semi-quiet        tame down verbosity\n");
-       fprintf(stderr, "   --quiet             disable all output\n");
-       fprintf(stderr, "   --background        run in the background\n");
+       fprintf(stderr, "   --background        run in the background\n");
        fprintf(stderr, "   --help              print this help\n\n");
        fprintf(stderr, "if no option is given, tune for all contexts using the 
default period.\n");
 }
@@ -227,12 +216,12 @@ static void run_tuner(int fd, unsigned int op, int 
period, const char *type)
        int ret;
 
        setup.period = period;
-       setup.quiet = quiet;
+       setup.quiet = quiet_mode;
        ret = ioctl(fd, op, &setup);
        if (ret)
                error(1, errno, "setup failed (%s)", type);
 
-       if (!quiet) {
+       if (!quiet_mode) {
                printf("%s gravity... ", type);
                fflush(stdout);
        }
@@ -247,7 +236,7 @@ static void run_tuner(int fd, unsigned int op, int period, 
const char *type)
        if (op == AUTOTUNE_RTIOC_USER)
                pthread_cancel(sampler);
 
-       if (!quiet)
+       if (!quiet_mode)
                printf("%u ns\n", gravity);
 }
 
@@ -281,8 +270,6 @@ int main(int argc, char *const argv[])
                                      CONFIG_XENO_DEFAULT_PERIOD);
                        break;
                case noload_opt:
-               case quiet_opt:
-               case semiquiet_opt:
                case background_opt:
                        break;
                case irq_opt:
@@ -318,7 +305,7 @@ int main(int argc, char *const argv[])
        if (tune_irqlat || tune_kernlat || tune_userlat) {
                if (!noload)
                        create_load(&load_pth);
-               if (!quiet)
+               if (!quiet_mode)
                        printf("== auto-tuning started, period=%d ns (may take 
a while)\n",
                               period);
        } else
@@ -335,7 +322,7 @@ int main(int argc, char *const argv[])
        if (tune_userlat)
                run_tuner(fd, AUTOTUNE_RTIOC_USER, period, "user");
 
-       if (!quiet && (tune_userlat || tune_kernlat || tune_userlat))
+       if (!quiet_mode && (tune_userlat || tune_kernlat || tune_userlat))
                printf("== auto-tuning completed after %ds\n",
                       (int)(time(NULL) - start));
 
diff --git a/utils/can/Makefile.am b/utils/can/Makefile.am
index 6db5ed2..2d67fa5 100644
--- a/utils/can/Makefile.am
+++ b/utils/can/Makefile.am
@@ -8,7 +8,7 @@ CPPFLAGS =                                              \
        @XENO_USER_CFLAGS@                              \
        -I$(top_srcdir)/include
 
-LDFLAGS = $(XENO_POSIX_WRAPPERS)
+LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 rtcanconfig_SOURCES = rtcanconfig.c
 
diff --git a/utils/corectl/Makefile.am b/utils/corectl/Makefile.am
index 471e04a..4840488 100644
--- a/utils/corectl/Makefile.am
+++ b/utils/corectl/Makefile.am
@@ -9,7 +9,7 @@ corectl_CPPFLAGS =              \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-corectl_LDFLAGS = $(XENO_POSIX_WRAPPERS)
+corectl_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@ $(XENO_POSIX_WRAPPERS)
 
 corectl_LDADD =                                        \
        ../../lib/cobalt/libcobalt.la           \
diff --git a/utils/hdb/Makefile.am b/utils/hdb/Makefile.am
index 89ea4cc..b7e5dc0 100644
--- a/utils/hdb/Makefile.am
+++ b/utils/hdb/Makefile.am
@@ -2,20 +2,14 @@ sbin_PROGRAMS = hdb
 
 hdb_SOURCES = hdb.c
 
-core_libs =
-if XENO_COBALT
-core_libs += ../../lib/cobalt/libcobalt.la
-endif
-
 hdb_CPPFLAGS =                         \
        $(XENO_USER_CFLAGS)     \
        -I$(top_srcdir)/include
 
-hdb_LDFLAGS=-Wl,--wrap=main \
-       -Wl,--dynamic-list=$(top_srcdir)/scripts/dynlist.ld
+hdb_LDFLAGS = @XENO_AUTOINIT_LDFLAGS@
 
 hdb_LDADD =                                    \
        ../../lib/copperplate/libcopperplate.la \
-       $(core_libs)                            \
+       ../../lib/@XENO_CORE_LIB@               \
         @XENO_USER_LDADD@                      \
        -lpthread -lrt


_______________________________________________
Xenomai-git mailing list
Xenomai-git@xenomai.org
http://xenomai.org/mailman/listinfo/xenomai-git

Reply via email to