@@ -85,6 +85,7 @@ all: $(PROGS) stap
#########################################################
# cpu emulator library
obj-y = exec.o translate-all.o cpu-exec.o
+obj-y += translate-common.o
obj-y += cpu-exec-common.o
obj-y += tcg/tcg.o tcg/tcg-op.o tcg/optimize.o
obj-$(CONFIG_TCG_INTERPRETER) += tci.o
@@ -267,6 +267,7 @@ typedef struct PCIHostDeviceAddress {
unsigned int function;
} PCIHostDeviceAddress;
+void tcg_exec_init_add(void (*fn)(unsigned long));
void tcg_exec_init(unsigned long tb_size);
bool tcg_enabled(void);
@@ -680,7 +680,7 @@ static inline void code_gen_alloc(size_t tb_size)
/* Must be called before using the QEMU cpus. 'tb_size' is the size
(in bytes) allocated to the translation buffer. Zero means default
size. */
-void tcg_exec_init(unsigned long tb_size)
+static void do_tcg_exec_init(unsigned long tb_size)
{
cpu_gen_init();
code_gen_alloc(tb_size);
@@ -694,6 +694,11 @@ void tcg_exec_init(unsigned long tb_size)
#endif
}
+static __attribute__((constructor)) void register_tcg_exec_init(void)
+{
+ tcg_exec_init_add(do_tcg_exec_init);
+}
+
bool tcg_enabled(void)
{
return tcg_ctx.code_gen_buffer != NULL;
new file mode 100644
@@ -0,0 +1,50 @@
+/*
+ * Host code generation common components
+ *
+ * Copyright (c) 2015 Peter Crosthwaite <crosthwaite.peter@gmail.com>
+ *
+ * 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, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "qemu-common.h"
+
+typedef struct TCGExecInitFn {
+ void (*do_tcg_exec_init)(unsigned long tb_size);
+ QLIST_ENTRY(TCGExecInitFn) list;
+} TCGExecInitFn;
+
+static QLIST_HEAD(, TCGExecInitFn) tcg_exec_init_list;
+
+void tcg_exec_init_add(void (*fn)(unsigned long))
+{
+ static bool inited;
+ TCGExecInitFn *lelem = g_malloc0(sizeof *lelem);
+
+ if (!inited) {
+ inited = true;
+ QLIST_INIT(&tcg_exec_init_list);
+ }
+
+ lelem->do_tcg_exec_init = fn;
+ QLIST_INSERT_HEAD(&tcg_exec_init_list, lelem, list);
+}
+
+void tcg_exec_init(unsigned long tb_size)
+{
+ TCGExecInitFn *t;
+
+ QLIST_FOREACH(t, &tcg_exec_init_list, list) {
+ t->do_tcg_exec_init(tb_size);
+ }
+}