📄 ap_hook.c
字号:
ap_hook_value modeval; ap_hook_entry *he; va_list ap; int rc; va_start(ap, modeid); if (modeid == AP_HOOK_MODE_DECLINE || modeid == AP_HOOK_MODE_DECLTMP) { if (AP_HOOK_SIG_HAS(sig, RC, char)) modeval.v_char = va_arg(ap, va_type(char)); else if (AP_HOOK_SIG_HAS(sig, RC, int)) modeval.v_int = va_arg(ap, va_type(int)); else if (AP_HOOK_SIG_HAS(sig, RC, long)) modeval.v_long = va_arg(ap, va_type(long)); else if (AP_HOOK_SIG_HAS(sig, RC, float)) modeval.v_float = va_arg(ap, va_type(float)); else if (AP_HOOK_SIG_HAS(sig, RC, double)) modeval.v_double = va_arg(ap, va_type(double)); else if (AP_HOOK_SIG_HAS(sig, RC, ptr)) modeval.v_ptr = va_arg(ap, va_type(ptr)); } if ((he = ap_hook_create(hook)) == NULL) return FALSE; if (he->he_sig == AP_HOOK_SIG_UNKNOWN) he->he_sig = sig; if (he->he_modeid == AP_HOOK_MODE_UNKNOWN) { he->he_modeid = modeid; he->he_modeval = modeval; } for (i = 0; he->he_func[i] != NULL; i++) if (ap_hook_call_func(ap, he, he->he_func[i])) break; if (i > 0 && he->he_modeid == AP_HOOK_MODE_ALL) rc = TRUE; else if (i == AP_HOOK_MAX_FUNCS || he->he_func[i] == NULL) rc = FALSE; else rc = TRUE; va_end(ap); return rc;}/* * Call a hook */API_EXPORT(int) ap_hook_call(char *hook, ...){ int i; ap_hook_entry *he; va_list ap; int rc; va_start(ap, hook); if ((he = ap_hook_find(hook)) == NULL) { va_end(ap); return FALSE; } if ( he->he_sig == AP_HOOK_SIG_UNKNOWN || he->he_modeid == AP_HOOK_MODE_UNKNOWN) { va_end(ap); return FALSE; } for (i = 0; he->he_func[i] != NULL; i++) if (ap_hook_call_func(ap, he, he->he_func[i])) break; if (i > 0 && he->he_modeid == AP_HOOK_MODE_ALL) rc = TRUE; else if (i == AP_HOOK_MAX_FUNCS || he->he_func[i] == NULL) rc = FALSE; else rc = TRUE; va_end(ap); return rc;}static int ap_hook_call_func(va_list ap, ap_hook_entry *he, ap_hook_func *hf){ void *v_rc; ap_hook_value v_tmp; int rc; /* * Now we dispatch the various function calls. We support function * signatures with up to 9 types (1 return type, 8 argument types) where * each argument can have 7 different types (ctx, char, int, long, float, * double, ptr), so theoretically there are 9^7 (=4782969) combinations * possible. But because we don't need all of them, of course, we * implement only the following well chosen subset (duplicates are ok): * * 1. `The basic hook'. * * void func() * * 2. The standard set of signatures which form all combinations of * int&ptr based signatures for up to 3 arguments. We provide * them per default for module authors. * * int func() * ptr func() * int func(int) * int func(ptr) * ptr func(int) * ptr func(ptr) * int func(int,int) * int func(int,ptr) * int func(ptr,int) * int func(ptr,ptr) * ptr func(int,int) * ptr func(int,ptr) * ptr func(ptr,int) * ptr func(ptr,ptr) * int func(int,int,int) * int func(int,int,ptr) * int func(int,ptr,int) * int func(int,ptr,ptr) * int func(ptr,int,int) * int func(ptr,int,ptr) * int func(ptr,ptr,int) * int func(ptr,ptr,ptr) * ptr func(int,int,int) * ptr func(int,int,ptr) * ptr func(int,ptr,int) * ptr func(int,ptr,ptr) * ptr func(ptr,int,int) * ptr func(ptr,int,ptr) * ptr func(ptr,ptr,int) * ptr func(ptr,ptr,ptr) * * 3. Actually currently used hooks. * * int func(ptr) [2x] * int func(ptr,ptr) [2x] * int func(ptr,ptr,int) [5x] * int func(ptr,ptr,ptr,int) [1x] * int func(ptr,ptr,ptr,int,ptr) [1x] * int func(ptr,ptr,ptr,ptr,int) [1x] * int func(ptr,ptr,ptr,ptr,int,ptr) [1x] * ptr func(ptr,ptr) [3x] * ptr func(ptr,ptr,ptr,ptr,ptr) [1x] * void func(ptr) [2x] * void func(ptr,int,int) [1x] * void func(ptr,ptr) [5x] * void func(ptr,ptr,ptr) [3x] * void func(ptr,ptr,ptr,ptr) [2x] * * To simplify the programming task we generate the actual dispatch code * for these calls via the embedded Perl script at the end of this source * file. This script parses the above lines and generates the section * below. So, when you need more signature variants just add them to the * above list and run * * $ perl ap_hook.c * * This automatically updates the above code. */ rc = TRUE; v_rc = NULL; if (!AP_HOOK_SIG_HAS(he->he_sig, RC, void)) { if (he->he_modeid == AP_HOOK_MODE_DECLTMP) { /* the return variable is a temporary one */ if (AP_HOOK_SIG_HAS(he->he_sig, RC, char)) v_rc = &v_tmp.v_char; else if (AP_HOOK_SIG_HAS(he->he_sig, RC, int)) v_rc = &v_tmp.v_int; else if (AP_HOOK_SIG_HAS(he->he_sig, RC, long)) v_rc = &v_tmp.v_long; else if (AP_HOOK_SIG_HAS(he->he_sig, RC, float)) v_rc = &v_tmp.v_float; else if (AP_HOOK_SIG_HAS(he->he_sig, RC, double)) v_rc = &v_tmp.v_double; else if (AP_HOOK_SIG_HAS(he->he_sig, RC, ptr)) v_rc = &v_tmp.v_ptr; } else { /* the return variable is provided by caller */ v_rc = va_arg(ap, void *); } } /* ----BEGIN GENERATED SECTION-------- */ if (he->he_sig == AP_HOOK_SIG1(void)) { /* Call: void func() */ ((void(*)())(hf->hf_ptr))(); } else if (he->he_sig == AP_HOOK_SIG1(int)) { /* Call: int func() */ *((int *)v_rc) = ((int(*)())(hf->hf_ptr))(); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG1(ptr)) { /* Call: ptr func() */ *((void * *)v_rc) = ((void *(*)())(hf->hf_ptr))(); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG2(int, int)) { /* Call: int func(int) */ int v1 = va_arg(ap, va_type(int)); *((int *)v_rc) = ((int(*)(int))(hf->hf_ptr))(v1); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG2(int, ptr)) { /* Call: int func(ptr) */ void *v1 = va_arg(ap, va_type(ptr)); *((int *)v_rc) = ((int(*)(void *))(hf->hf_ptr))(v1); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG2(ptr, int)) { /* Call: ptr func(int) */ int v1 = va_arg(ap, va_type(int)); *((void * *)v_rc) = ((void *(*)(int))(hf->hf_ptr))(v1); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG2(ptr, ptr)) { /* Call: ptr func(ptr) */ void *v1 = va_arg(ap, va_type(ptr)); *((void * *)v_rc) = ((void *(*)(void *))(hf->hf_ptr))(v1); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG3(int, int, int)) { /* Call: int func(int,int) */ int v1 = va_arg(ap, va_type(int)); int v2 = va_arg(ap, va_type(int)); *((int *)v_rc) = ((int(*)(int, int))(hf->hf_ptr))(v1, v2); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG3(int, int, ptr)) { /* Call: int func(int,ptr) */ int v1 = va_arg(ap, va_type(int)); void *v2 = va_arg(ap, va_type(ptr)); *((int *)v_rc) = ((int(*)(int, void *))(hf->hf_ptr))(v1, v2); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG3(int, ptr, int)) { /* Call: int func(ptr,int) */ void *v1 = va_arg(ap, va_type(ptr)); int v2 = va_arg(ap, va_type(int)); *((int *)v_rc) = ((int(*)(void *, int))(hf->hf_ptr))(v1, v2); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG3(int, ptr, ptr)) { /* Call: int func(ptr,ptr) */ void *v1 = va_arg(ap, va_type(ptr)); void *v2 = va_arg(ap, va_type(ptr)); *((int *)v_rc) = ((int(*)(void *, void *))(hf->hf_ptr))(v1, v2); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG3(ptr, int, int)) { /* Call: ptr func(int,int) */ int v1 = va_arg(ap, va_type(int)); int v2 = va_arg(ap, va_type(int)); *((void * *)v_rc) = ((void *(*)(int, int))(hf->hf_ptr))(v1, v2); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG3(ptr, int, ptr)) { /* Call: ptr func(int,ptr) */ int v1 = va_arg(ap, va_type(int)); void *v2 = va_arg(ap, va_type(ptr)); *((void * *)v_rc) = ((void *(*)(int, void *))(hf->hf_ptr))(v1, v2); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG3(ptr, ptr, int)) { /* Call: ptr func(ptr,int) */ void *v1 = va_arg(ap, va_type(ptr)); int v2 = va_arg(ap, va_type(int)); *((void * *)v_rc) = ((void *(*)(void *, int))(hf->hf_ptr))(v1, v2); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG3(ptr, ptr, ptr)) { /* Call: ptr func(ptr,ptr) */ void *v1 = va_arg(ap, va_type(ptr)); void *v2 = va_arg(ap, va_type(ptr)); *((void * *)v_rc) = ((void *(*)(void *, void *))(hf->hf_ptr))(v1, v2); rc = (*((void * *)v_rc) != he->he_modeval.v_ptr); } else if (he->he_sig == AP_HOOK_SIG4(int, int, int, int)) { /* Call: int func(int,int,int) */ int v1 = va_arg(ap, va_type(int)); int v2 = va_arg(ap, va_type(int)); int v3 = va_arg(ap, va_type(int)); *((int *)v_rc) = ((int(*)(int, int, int))(hf->hf_ptr))(v1, v2, v3); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG4(int, int, int, ptr)) { /* Call: int func(int,int,ptr) */ int v1 = va_arg(ap, va_type(int)); int v2 = va_arg(ap, va_type(int)); void *v3 = va_arg(ap, va_type(ptr)); *((int *)v_rc) = ((int(*)(int, int, void *))(hf->hf_ptr))(v1, v2, v3); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG4(int, int, ptr, int)) { /* Call: int func(int,ptr,int) */ int v1 = va_arg(ap, va_type(int)); void *v2 = va_arg(ap, va_type(ptr)); int v3 = va_arg(ap, va_type(int)); *((int *)v_rc) = ((int(*)(int, void *, int))(hf->hf_ptr))(v1, v2, v3); rc = (*((int *)v_rc) != he->he_modeval.v_int); } else if (he->he_sig == AP_HOOK_SIG4(int, int, ptr, ptr)) { /* Call: int func(int,ptr,ptr) */ int v1 = va_arg(ap, va_type(int));
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -