我想一劳永逸地为这个mocks for C code创建一个漂亮而有光泽的版本。
我想创建一个如下所示的锅炉板宏:
#define MOCK_FREE_FUNCTION(NAME, SIGN, MOCK) \
/* whatever goes here */
在代码(或标题)中,它应该像这样使用:MOCK_FREE_FUNCTION2(myFunc, void(char *, const char *), myFuncMock);
并扩展为某种东西
struct Whatever_myFunc {
MOCK_CONST_METHOD2(myFunc, void (char *x, char *y));
};
Whatever_myFunc myFuncMock;
extern "C" {
void myFunc(char *x, char *y) {
myFuncMock.(x,y);
}
}
/* maybe some convenience EXPECT_CALL thing */
我很清楚并非一切皆有可能,但我希望尽可能接近这一点。只要链接器没有抱怨并找到它的符号,我也不会抱怨。如果它有两个不同的宏,我不介意:一个用于定义静态成员,另一个用于定义原型。
从评论中添加
生成大部分内容很简单 我不能完成的问题是 gmock如何设法从
获得 MOCK_METHOD2(foo, void(char *, char*)
类似于void foo(char *, char*)
这是我能提出的最接近的事情:
#include <stdio.h>
#define MOCK_FREE_FUNCTION2(NAME, MOCK, RET, ARGS) \
typedef RET (*NAME ## Type) ARGS; \
NAME ## Type NAME = barfoo_f;
/* ok it's callable, but how do I get my own code inside here? */
void barfoo_f(int i, int j) {
printf ("hello world %d %d\n", i, j);
}
// How does google mock get rid of , in the prototype
MOCK_FREE_FUNCTION2(FooBar, XXX, void, (int,int));
int main(int argc, char **argv) {
FooBar(1,2);
}
答案 0 :(得分:1)
解决您的近似问题(如何从MACRO(foo, void(char*, char*))
到void foo(char*, char*)
)的可能方法可能与功能特征结合使用:
template <typename F>
struct func_traits;
template <typename R, typename... Args>
struct func_traits<R(Args...)>
{
using return_type = R;
template <size_t I>
using arg_type = typename std::tuple_element<I, std::tuple<Args...>>::type;
};
#define MACRO_2(NAME, TYPE) \
func_traits<TYPE>::return_type NAME(func_traits<TYPE>::arg_type<0> arg0, \
func_traits<TYPE>::arg_type<1> arg1)
(我只是使用std::tuple
作为在此处实施类型列表的快捷方式。)