创建适用于所有函数类型的通用函数包装器

时间:2017-04-10 19:05:47

标签: c

我希望能够在一个大系统中包含任何函数,该函数将在包装函数之前和之后插入一些语句。这些添加的语句将用于特殊目的,例如计时函数执行或打印调试消息或任何类型的消息。

包装器不必绝对只有一个函数(或宏),但如果需要多个函数,则应将它们保持在最小值。

为了更好地解释我想在这里做的是一个例子:

现有代码:

void my_big_function(void) {
     int data1;
     int data2;
     int ret1;
     fun1();
     ret1 = fun2();
     anotherfun3(data1);
     myfun4();
     awesomefun5(data2);
}

需要将其更改为: void run_and_time

run_and_time(void* fun_p, void* retval, ... )
{
         // statements before calling the function (e.g. get current time)
         // call the function and give it the parameters it needs.
         // statements After calling the function (e.g. get new time and subtract start time from it)

}

void my_big_function(void) {
         run_and_time(&fun1, NULL);
         run_and_time(&fun2, &ret1);
         run_and_time(&anotherfun3, NULL, data1);
         run_and_time(&myfun4, NULL);
         run_and_time(&awesomefun5, NULL, data2);
}

这需要在标准C中完成。

更新: 在某些环境中,您无法运行配置文件以及时调试函数调用。例如,考虑嵌入式系统的Linux内核中的启动过程。在这种情况下,工具链可能无法保持在较高且有用的水平。

要提出一些建议,我们可以查看Linux内核中的start_kernel函数。在该函数中,对void f(void)类型的函数进行了一系列调用。对于这种类型的功能来说很容易。以下是可以做的事情的抽象示例:

#include <stdio.h>
#include <stdlib.h>

#ifdef MY_DEFINITION
#include <sys/time.h>

#define time_func_call(x, y) do { \
struct timeval  tv1, tv2; \
gettimeofday(&tv1, NULL); \
x(); \
gettimeofday(&tv2, NULL); \
printf ("%s took %lu micro seconds to finish\n", y, (tv2.tv_usec - tv1.tv_usec)   + \
       (tv2.tv_sec - tv1.tv_sec) * 1000000); \
\
} while (0)
#else
#define time_func_call(x, y) do { \
x();\
} while (0)
#endif



void good_function(void){
    printf("Inside good_function\n");
    return;
}

int main(int argc, char** argv) {
    time_func_call(good_function, "good_function");
    return (EXIT_SUCCESS);
}

这是一个测试运行:

$ gcc -o ./test ./main.c 
$ ./test 
Inside good_function
$ gcc -o ./test -DMY_DEFINITION ./main.c 
$ ./test 
Inside good_function
good_function took 51 micro seconds to finish

现在,这适用于特定类型的功能。但我们可以扩展它以与其他签名一起使用吗?

0 个答案:

没有答案