From: Vyacheslav Cherkashin Date: Mon, 24 Jun 2013 11:43:18 +0000 (+0400) Subject: [FEATURE] implement /un/register_syscall() X-Git-Tag: Tizen_SDK_2.3~439 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=d22e387e41db551a138fe4810809234ab1d1c888;p=kernel%2Fswap-modules.git [FEATURE] implement /un/register_syscall() --- diff --git a/ks_features/Makefile.am b/ks_features/Makefile.am index bef7b30..f670827 100644 --- a/ks_features/Makefile.am +++ b/ks_features/Makefile.am @@ -5,8 +5,9 @@ module_dir = $(realpath $(top_srcdir)/src/modules/ks_features) module_name = swap_ks_features cross_compiler = $(subst gcc,,$(CC)) -#inlude_opt = -I$(realpath $(top_srcdir)/src/modules/kprobe) \ -# -I$(realpath $(top_srcdir)/src/modules/kprobe/arch) +inlude_opt = -I$(realpath $(top_srcdir)/src/modules/kprobe) \ + -I$(realpath $(top_srcdir)/src/modules/kprobe/arch) \ + -I$(realpath $(top_srcdir)/src/modules/ksyms) extra_cflags = "$(inlude_opt) $(board_opt)" all-local: diff --git a/ks_features/features_data.h b/ks_features/features_data.h index a0df130..5fe0e14 100644 --- a/ks_features/features_data.h +++ b/ks_features/features_data.h @@ -1,36 +1,27 @@ #ifndef _FEATURES_DATA_H #define _FEATURES_DATA_H -#include #include "syscall_list.h" -#define X(x) #x -static const char *const syscall_name[] = { - SYSCALL_LIST -}; -#undef X - -enum { - syscall_name_cnt = sizeof(syscall_name) / sizeof(char *) -}; - #define X(x) id_##x enum syscall_id { SYSCALL_LIST }; #undef X -static char sys_counter[syscall_name_cnt] = { 0 }; - static enum syscall_id id_file[] = { id_sys_acct, id_sys_mount, id_sys_umount, id_sys_truncate, - id_sys_stat, +/* TODO: + * id_sys_stat, + */ id_sys_statfs, id_sys_statfs64, - id_sys_lstat, +/* TODO: + * id_sys_lstat, + */ id_sys_stat64, id_sys_fstat64, id_sys_lstat64, @@ -77,7 +68,9 @@ static enum syscall_id id_file[] = { id_sys_fchmodat, id_sys_fchownat, id_sys_openat, - id_sys_newfstatat, +/* TODO: + * id_sys_newfstatat, + */ id_sys_readlinkat, id_sys_utimensat, id_sys_fanotify_mark, @@ -133,7 +126,9 @@ static enum syscall_id id_process[] = { id_sys_exit_group, id_sys_wait4, id_sys_waitid, - id_sys_waitpid, +/* TODO: + * id_sys_waitpid, + */ id_sys_rt_tgsigqueueinfo, id_sys_unshare, id_sys_fork, @@ -148,7 +143,9 @@ static enum syscall_id id_process[] = { static enum syscall_id id_signal[] = { id_sys_sigpending, id_sys_sigprocmask, - id_sys_sigaltstack, +/* TODO: + * id_sys_sigaltstack, + */ /* TODO: add support CONFIG_OLD_SIGSUSPEND and CONFIG_OLD_SIGSUSPEND3 * id_sys_sigsuspend, * id_sys_sigsuspend, @@ -161,7 +158,9 @@ static enum syscall_id id_signal[] = { id_sys_rt_tgsigqueueinfo, id_sys_kill, id_sys_tgkill, - id_sys_signal, +/* TODO: + * id_sys_signal, + */ id_sys_pause, id_sys_signalfd, id_sys_signalfd4 @@ -197,7 +196,9 @@ static enum syscall_id id_desc[] = { id_sys_fchmodat, id_sys_fchownat, id_sys_openat, - id_sys_newfstatat, +/* TODO: + * id_sys_newfstatat, + */ id_sys_readlinkat, id_sys_utimensat, id_sys_splice, @@ -222,30 +223,4 @@ static enum syscall_id id_desc[] = { id_sys_setns }; -struct feature { - size_t cnt; - enum syscall_id *feature_list; -}; - -#define CREATE_FEATURE(x) \ -{ \ - .cnt = sizeof(x) / sizeof(enum syscall_id), \ - .feature_list = x \ -} - -static struct feature features[] = { - CREATE_FEATURE(id_file), - CREATE_FEATURE(id_irq), - CREATE_FEATURE(id_net), - CREATE_FEATURE(id_process), - CREATE_FEATURE(id_signal), - CREATE_FEATURE(id_desc) -}; - -#undef CREATE_FEATURE - -enum { - feature_cnt = sizeof(features) / sizeof(struct feature) -}; - #endif /* _FEATURES_DATA_H */ diff --git a/ks_features/ks_features.c b/ks_features/ks_features.c index 1dd1507..4b5e832 100644 --- a/ks_features/ks_features.c +++ b/ks_features/ks_features.c @@ -1,36 +1,143 @@ +#include +#include +#include +#include #include "ks_features.h" #include "features_data.h" -#include -#include +#include "syscall_list.h" + + +struct feature { + size_t cnt; + enum syscall_id *feature_list; +}; + +struct ks_probe { + struct jprobe jp; + struct kretprobe rp; + int counter; +}; + + +#define CREATE_JP(name) \ +{ \ + .entry = NULL, \ + .pre_entry = NULL \ +} + +#define CREATE_RP(name) \ +{ \ + .entry_handler = NULL, \ + .handler = NULL \ +} + +#define CREATE_FEATURE(x) \ +{ \ + .cnt = sizeof(x) / sizeof(enum syscall_id), \ + .feature_list = x \ +} + + +#define X(x) #x +static const char *const syscall_name[] = { + SYSCALL_LIST +}; +#undef X + +enum { + syscall_name_cnt = sizeof(syscall_name) / sizeof(char *) +}; + + +#define X(x) \ +{ \ + .jp = CREATE_JP(x), \ + .rp = CREATE_RP(x), \ + .counter = 0 \ +} + +static struct ks_probe ksp[] = { + SYSCALL_LIST +}; +#undef X + + +static struct feature features[] = { + CREATE_FEATURE(id_file), + CREATE_FEATURE(id_irq), + CREATE_FEATURE(id_net), + CREATE_FEATURE(id_process), + CREATE_FEATURE(id_signal), + CREATE_FEATURE(id_desc) +}; + +enum { + feature_cnt = sizeof(features) / sizeof(struct feature) +}; + + +static char *get_sys_name(size_t id) +{ + return syscall_name[id]; +} + +static int get_counter(size_t id) +{ + return ksp[id].counter; +} + +static void inc_counter(size_t id) +{ + ++ksp[id].counter; +} + +static void dec_counter(size_t id) +{ + --ksp[id].counter; +} static int register_syscall(size_t id) { - printk("register_syscall: %s\n", syscall_name[id]); - return 0; + int ret; + printk("register_syscall: %s\n", get_sys_name(id)); + + ret = dbi_register_jprobe(&ksp[id].jp); + if (ret) + return ret; + + ret = dbi_register_kretprobe(&ksp[id].rp); + if (ret) + dbi_unregister_jprobe(&ksp[id].jp); + + return ret; } static int unregister_syscall(size_t id) { - printk("unregister_syscall: %s\n", syscall_name[id]); + printk("unregister_syscall: %s\n", get_sys_name(id)); + + dbi_unregister_kretprobe(&ksp[id].rp); + dbi_unregister_jprobe(&ksp[id].jp); + return 0; } static int install_features(struct feature *f) { - size_t i, num; + size_t i, id; for (i = 0; i < f->cnt; ++i) { - num = f->feature_list[i]; + id = f->feature_list[i]; - if (sys_counter[num] == 0) { - int ret = register_syscall(num); + if (get_counter(id) == 0) { + int ret = register_syscall(id); if (ret) { /* TODO: error */ return ret; } } - ++sys_counter[num]; + inc_counter(id); } return 0; @@ -38,20 +145,20 @@ static int install_features(struct feature *f) static int uninstall_features(struct feature *f) { - size_t i, num; + size_t i, id; for (i = 0; i < f->cnt; ++i) { - num = f->feature_list[i]; + id = f->feature_list[i]; - if (sys_counter[num] == 0) { + if (get_counter(id) == 0) { /* TODO: error */ return -EINVAL; } - --sys_counter[num]; + dec_counter(id); - if (sys_counter[num] == 0) { - int ret = unregister_syscall(num); + if (get_counter(id) == 0) { + int ret = unregister_syscall(id); if (ret) { /* TODO: error */ return ret; @@ -70,7 +177,7 @@ static struct feature *get_feature(enum feature_id id) return &features[id]; } -int set_features(enum feature_id id) +int set_feature(enum feature_id id) { struct feature *f = get_feature(id); @@ -79,8 +186,9 @@ int set_features(enum feature_id id) return install_features(f); } +EXPORT_SYMBOL_GPL(set_feature); -int unset_features(enum feature_id id) +int unset_feature(enum feature_id id) { struct feature *f = get_feature(id); @@ -89,10 +197,26 @@ int unset_features(enum feature_id id) return uninstall_features(f); } +EXPORT_SYMBOL_GPL(unset_feature); static int __init init_ks_feature(void) { - return 0; + int i; + unsigned long addr; + char *name; + + for (i = 0; i < syscall_name_cnt; ++i) { + name = get_sys_name(i); + addr = swap_ksyms(name); + if (addr == 0) { + printk("%s() not found\n", name); + return -EFAULT; + } + + ksp[i].jp.kp.addr = ksp[i].rp.kp.addr = addr; + } + + return 0; } static void __exit exit_ks_feature(void) @@ -102,13 +226,15 @@ static void __exit exit_ks_feature(void) module_init(init_ks_feature); module_exit(exit_ks_feature); +MODULE_LICENSE("GPL"); + /* debug */ static void print_feature(struct feature *f) { size_t i; for (i = 0; i < f->cnt; ++i) { - printk(" feature[%3u]: %s\n", i, syscall_name[f->feature_list[i]]); + printk(" feature[%3u]: %s\n", i, get_sys_name(f->feature_list[i])); } } @@ -129,7 +255,7 @@ void print_all_syscall(void) printk("SYSCALL:\n"); for (i = 0; i < syscall_name_cnt; ++i) { - printk(" [%2d] %s\n", sys_counter[i], syscall_name[i]); + printk(" [%2d] %s\n", get_counter(i), get_sys_name(i)); } } /* debug */ diff --git a/ks_features/ks_features.h b/ks_features/ks_features.h index 6e56790..4178990 100644 --- a/ks_features/ks_features.h +++ b/ks_features/ks_features.h @@ -10,8 +10,8 @@ enum feature_id { FID_DESC }; -int set_features(enum feature_id id); -int unset_features(enum feature_id id); +int set_feature(enum feature_id id); +int unset_feature(enum feature_id id); /* debug */ void print_features(void); diff --git a/ks_features/syscall_list.h b/ks_features/syscall_list.h index 1566b3e..6fa0e2e 100644 --- a/ks_features/syscall_list.h +++ b/ks_features/syscall_list.h @@ -55,7 +55,7 @@ X(sys_listen), \ X(sys_listxattr), \ X(sys_lstat64), \ - X(sys_lstat), \ +/* TODO: X(sys_lstat), */ \ X(sys_mkdirat), \ X(sys_mkdir), \ X(sys_mknodat), \ @@ -67,7 +67,7 @@ X(sys_msgrcv), \ X(sys_msgsnd), \ X(sys_name_to_handle_at), \ - X(sys_newfstatat), \ +/* TODO: X(sys_newfstatat), */ \ X(sys_old_mmap), \ X(sys_openat), \ X(sys_open_by_handle_at), \ @@ -114,10 +114,10 @@ X(sys_shmget), \ X(sys_shutdown), \ X(sys_sigaction), \ - X(sys_sigaltstack), \ +/* TODO: X(sys_sigaltstack), */ \ X(sys_signalfd4), \ X(sys_signalfd), \ - X(sys_signal), \ +/* TODO: X(sys_signal), */ \ X(sys_sigpending), \ X(sys_sigprocmask), \ X(sys_sigsuspend), \ @@ -128,7 +128,7 @@ X(sys_stat64), \ X(sys_statfs64), \ X(sys_statfs), \ - X(sys_stat), \ +/* TODO: X(sys_stat), */ \ X(sys_swapoff), \ X(sys_swapon), \ X(sys_symlinkat), \ @@ -152,7 +152,7 @@ X(sys_vfork), \ X(sys_vmsplice), \ X(sys_wait4), \ - X(sys_waitid), \ - X(sys_waitpid) + X(sys_waitid) +/* TODO: X(sys_waitpid) */ #endif /* _SYSCALL_LIST_H */