qemu/module.h中的模块类型定义
cpp
typedef enum {
MODULE_INIT_MIGRATION, // 1. 迁移功能初始化
MODULE_INIT_BLOCK, // 2. 块设备层初始化
MODULE_INIT_OPTS, // 3. 命令行/配置选项解析初始化
MODULE_INIT_QOM, // 4. QEMU 对象模型(核心框架)初始化
MODULE_INIT_TRACE, // 5. 跟踪调试系统初始化
MODULE_INIT_XEN_BACKEND, // 6. Xen 虚拟化后端初始化
MODULE_INIT_LIBQOS, // 7. 服务质量(QoS)控制初始化
MODULE_INIT_FUZZ_TARGET, // 8. 模糊测试目标初始化
MODULE_INIT_MAX // 枚举边界值(无实际功能)
} module_init_type;
#define block_init(function) module_init(function, MODULE_INIT_BLOCK)
#define opts_init(function) module_init(function, MODULE_INIT_OPTS)
#define type_init(function) module_init(function, MODULE_INIT_QOM)
#define trace_init(function) module_init(function, MODULE_INIT_TRACE)
#define xen_backend_init(function) module_init(function, MODULE_INIT_XEN_BACKEND)
#define libqos_init(function) module_init(function, MODULE_INIT_LIBQOS)
#define fuzz_target_init(function) module_init(function, MODULE_INIT_FUZZ_TARGET)
#define migration_init(function) module_init(function, MODULE_INIT_MIGRATION)
#define module_init(function, type) \
static void __attribute__((constructor)) do_qemu_init_ ## function(void) \
{ \
register_module_init(function, type); \
}
其中,utils/module.c中的register_module_init函数
cpp
void register_module_init(void (*fn)(void), module_init_type type)
{
ModuleEntry *e;
ModuleTypeList *l;
e = g_malloc0(sizeof(*e));
e->init = fn;
e->type = type;
l = find_type(type);
QTAILQ_INSERT_TAIL(l, e, node);
}
全局保存的链表数组,根据模块类型可以找到相应的列表,列表再找到类
cpp
static ModuleTypeList init_type_list[MODULE_INIT_MAX];
static bool modules_init_done[MODULE_INIT_MAX];
列表的定义
cpp
typedef struct ModuleEntry
{
void (*init)(void); // type_init注册函数,
QTAILQ_ENTRY(ModuleEntry) node;
module_init_type type;
} ModuleEntry;
typedef QTAILQ_HEAD(, ModuleEntry) ModuleTypeList;
比如:object的注册函数type_init(register_types)
module_init(register_types, MODULE_INIT_QOM)
转换成在main函数之前执行的函数
cpp
static void __attribute__((constructor)) do_qemu_init_register_types(void)
{
register_module_init(register_types, MODULE_INIT_QOM);
}
再调用register_module_init函数添加到QOM的列表中
cpp
void register_module_init(void (*fn)(void), module_init_type type)
{
ModuleEntry *e;
ModuleTypeList *l;
e = g_malloc0(sizeof(*e));
e->init = fn;
e->type = type;
l = find_type(type);
QTAILQ_INSERT_TAIL(l, e, node);
}
main函数之前只是将函数添加到列表,在main执行到最终会调用
main()
└─ qemu_init() // softmmu/vl.c
└─ qemu_init_subsystems() // softmmu/runstate.c
└─ module_call_init(MODULE_INIT_QOM)
└─ 遍历队列,对每个 e->init() 调用
└─ test_czj_register_types()
└─ type_register_static(&test_czj_info)
qemu_init_subsystems初始化子系统
cpp
void qemu_init_subsystems(void)
{
Error *err = NULL;
os_set_line_buffering();
module_call_init(MODULE_INIT_TRACE);
qemu_init_cpu_list();
qemu_init_cpu_loop();
qemu_mutex_lock_iothread();
atexit(qemu_run_exit_notifiers);
module_call_init(MODULE_INIT_QOM);
module_call_init(MODULE_INIT_MIGRATION);
runstate_init();
precopy_infrastructure_init();
postcopy_infrastructure_init();
monitor_init_globals();
if (qcrypto_init(&err) < 0) {
error_reportf_err(err, "cannot initialize crypto: ");
exit(1);
}
os_setup_early_signal_handling();
bdrv_init_with_whitelist();
socket_init();
}
module_call_init的代码实现
cpp
void module_call_init(module_init_type type)
{
ModuleTypeList *l;
ModuleEntry *e;
if (modules_init_done[type]) {
return;
}
l = find_type(type);
QTAILQ_FOREACH(e, l, node) {
e->init();
}
modules_init_done[type] = true;
}
最终调用注册函数register_types
cpp
static void register_types(void)
{
static const TypeInfo interface_info = {
.name = TYPE_INTERFACE,
.class_size = sizeof(InterfaceClass),
.abstract = true,
};
static const TypeInfo object_info = {
.name = TYPE_OBJECT,
.instance_size = sizeof(Object),
.class_init = object_class_init,
.abstract = true,
};
type_interface = type_register_internal(&interface_info);
type_register_internal(&object_info);
}