|
version 1.1, 2012/02/21 22:19:56
|
version 1.1.1.2, 2014/07/30 07:55:27
|
|
Line 1
|
Line 1
|
| /* |
/* |
| * input.c Input API |
* input.c Input API |
| * |
* |
| * Copyright (c) 2001-2005 Thomas Graf <tgraf@suug.ch> | * Copyright (c) 2001-2013 Thomas Graf <tgraf@suug.ch> |
| | * Copyright (c) 2013 Red Hat, Inc. |
| * |
* |
| * Permission is hereby granted, free of charge, to any person obtaining a |
* Permission is hereby granted, free of charge, to any person obtaining a |
| * copy of this software and associated documentation files (the "Software"), |
* copy of this software and associated documentation files (the "Software"), |
|
Line 24
|
Line 25
|
| |
|
| #include <bmon/bmon.h> |
#include <bmon/bmon.h> |
| #include <bmon/input.h> |
#include <bmon/input.h> |
| #include <bmon/node.h> | #include <bmon/module.h> |
| #include <bmon/utils.h> |
#include <bmon/utils.h> |
| |
|
| static struct input_module *reg_pri_list; | static struct bmon_subsys input_subsys; |
| static struct input_module *reg_sec_list; | |
| static struct input_module *preferred; | |
| |
|
| const char * | void input_register(struct bmon_module *m) |
| get_preferred_input_name(void) | |
| { |
{ |
| return preferred ? preferred->im_name : "none"; | module_register(&input_subsys, m); |
| } |
} |
| |
|
| static inline void | static void activate_default(void) |
| __register_input_module(struct input_module *ops, struct input_module **list) | |
| { |
{ |
| ops->im_next = *list; | /* |
| *list = ops; | * Try to activate a default input module if the user did not make |
| } | * a selection |
| | */ |
| | if (!input_subsys.s_nmod) { |
| | struct bmon_module *m; |
| |
|
| |
#ifdef SYS_LINUX |
| |
if (!input_set("netlink")) |
| |
return; |
| |
|
| void | if (!input_set("proc")) |
| register_input_module(struct input_module *ops) | return; |
| { | #endif |
| __register_input_module(ops, ®_pri_list); | |
| } | |
| |
|
| void | #ifdef SYS_BSD |
| register_secondary_input_module(struct input_module *ops) | if (!input_set("sysctl")) |
| { | return; |
| __register_input_module(ops, ®_sec_list); | |
| } | |
| |
| static inline struct input_module * | |
| __get_input_module(const char *name, struct input_module *list) | |
| { | |
| struct input_module *i; | |
| |
| for (i = list; i; i = i->im_next) | |
| if (!strcmp(i->im_name, name)) | |
| return i; | |
| |
| return NULL; | |
| } | |
| |
| static struct input_module * | |
| get_input_module(const char *name) | |
| { | |
| return __get_input_module(name, reg_pri_list); | |
| } | |
| |
| static struct input_module * | |
| get_sec_input_module(const char *name) | |
| { | |
| return __get_input_module(name, reg_sec_list); | |
| } | |
| |
| #define FOREACH_SIM(F) \ | |
| do { \ | |
| struct input_module *i; \ | |
| for (i = reg_sec_list; i; i = i->im_next) \ | |
| if (i->im_enable && i->im_##F) \ | |
| i->im_##F (); \ | |
| } while (0) | |
| |
| static void | |
| find_preferred(void) | |
| { | |
| if (NULL == preferred) { | |
| struct input_module *i; | |
| /* | |
| * User has not chosen a output module | |
| */ | |
| |
| #if defined SYS_SUNOS | |
| preferred = get_input_module("kstat"); | |
| #elif defined SYS_BSD | |
| preferred = get_input_module("sysctl"); | |
| #elif defined SYS_LINUX | |
| preferred = get_input_module("netlink"); | |
| |
| if (NULL == preferred) | |
| preferred = get_input_module("proc"); | |
| |
| if (NULL == preferred) | |
| preferred = get_input_module("sysfs"); | |
| #endif |
#endif |
| |
|
| if (NULL == preferred) { | /* Fall back to anything that could act as default */ |
| for (i = reg_pri_list; i; i = i->im_next) { | list_for_each_entry(m, &input_subsys.s_mod_list, m_list) { |
| if (i->im_no_default) { | if (m->m_flags & BMON_MODULE_DEFAULT) |
| preferred = i; | if (!input_set(m->m_name)) |
| break; | return; |
| } | |
| } | |
| } |
} |
| |
|
| if (NULL == preferred) | quit("No input module found\n"); |
| quit("No input method found\n"); | |
| } |
} |
| } |
} |
| |
|
| void input_read(void) |
| void | |
| input_read(void) | |
| { |
{ |
| find_preferred(); | module_foreach_run_enabled(&input_subsys); |
| |
| reset_nodes(); | |
| preferred->im_read(); | |
| |
| FOREACH_SIM(read); | |
| |
| remove_unused_node_items(); | |
| } |
} |
| |
|
| static void | int input_set(const char *name) |
| list_input(void) | |
| { |
{ |
| struct input_module *i; | return module_set(&input_subsys, name); |
| |
| printf("Input modules:\n"); | |
| if (NULL == reg_pri_list) | |
| printf("\tNo input modules found.\n"); | |
| else | |
| for (i = reg_pri_list; i; i = i->im_next) | |
| printf("\t%s\n", i->im_name); | |
| } |
} |
| |
|
| void | static struct bmon_subsys input_subsys = { |
| set_input(const char *name) | .s_name = "input", |
| { | .s_activate_default = &activate_default, |
| static int set = 0; | .s_mod_list = LIST_SELF(input_subsys.s_mod_list), |
| module_conf_t *ml, *m; | }; |
| | |
| if (set) | |
| return; | |
| set = 1; | |
| |
|
| if (NULL == name || !strcasecmp(name, "list")) { | static void __init __input_init(void) |
| list_input(); | |
| exit(0); | |
| } | |
| | |
| ml = parse_module_param(name); | |
| |
| for (m = ml; m; m = m->next) { | |
| preferred = get_input_module(ml->name); | |
| |
| if (NULL == preferred) | |
| continue; | |
| |
| if (preferred->im_set_opts) | |
| preferred->im_set_opts(ml->attrs); | |
| |
| if (preferred->im_probe) | |
| if (preferred->im_probe()) | |
| return; | |
| } | |
| |
| quit("No (working) input module found\n"); | |
| } | |
| |
| static void | |
| list_sec_input(void) | |
| { |
{ |
| struct input_module *i; | module_register_subsys(&input_subsys); |
| |
| printf("Secondary input modules:\n"); | |
| if (NULL == reg_sec_list) | |
| printf("\tNo secondary input modules found.\n"); | |
| else | |
| for (i = reg_sec_list; i; i = i->im_next) | |
| printf("\t%s\n", i->im_name); | |
| } | |
| |
| void | |
| set_sec_input(const char *name) | |
| { | |
| static int set = 0; | |
| module_conf_t *ml, *m; | |
| |
| if (set) | |
| return; | |
| set = 1; | |
| |
| if (NULL == name || !strcasecmp(name, "list")) { | |
| list_sec_input(); | |
| exit(0); | |
| } | |
| | |
| ml = parse_module_param(name); | |
| |
| for (m = ml; m; m = m->next) { | |
| struct input_module *i = get_sec_input_module(m->name); | |
| |
| if (NULL == i) | |
| continue; | |
| |
| if (i->im_set_opts) | |
| i->im_set_opts(ml->attrs); | |
| |
| if (i->im_probe) { | |
| if (i->im_probe() == 1) | |
| i->im_enable = 1; | |
| } | |
| } | |
| } | |
| |
| void | |
| input_init(void) | |
| { | |
| find_preferred(); | |
| |
| if (preferred->im_init) | |
| preferred->im_init(); | |
| |
| FOREACH_SIM(init); | |
| } | |
| |
| void | |
| input_shutdown(void) | |
| { | |
| find_preferred(); | |
| |
| if (preferred->im_shutdown) | |
| preferred->im_shutdown(); | |
| |
| FOREACH_SIM(shutdown); | |
| } |
} |