我正在阅读有关模拟C函数(例如CMock或CMocka)的几篇文章,但是我不确定在此过程中如何将实际函数替换为模拟函数。例如,CMocka依赖于使用GNU编译器的自动包装,该编译器支持将参数--wrap
附加__wrap
到函数调用之后的参数,或者弱符号允许您覆盖所需的任何符号。
但是对于几乎所有其他框架,您如何在Visual Studio中执行此操作?
例如,CMock的示例与此相似(此处已简化很多):
// myfunc.c
#include <parsestuff.h>
// this is the function we would like to test
int MyFunc(char* Command)
{
// this is the call to the function we will mock
return ParseStuff(Command);
}
还有一个实际的实现,其中包含链接器应在实际应用程序中找到的实际功能:
// parsestuff.c
int ParseStuff(char* cmd)
{
// do some actual work
return 42;
}
现在,在测试过程中,Ruby脚本会创建模拟函数,例如:
// MockParseStuff.c (auto created by cmock)
int ParseStuff(char* Cmd);
void ParseStuff_ExpectAndReturn(char* Cmd, int toReturn);
但是,如果VS项目已经包括在内parsestuff.c
,那么来自的调用怎么可能myfunc.c
终止于MockParseStuff.c
?
这是否意味着我不能parsestuff.c
包含在单元测试项目中?但是,如果是这样的话,那么它也不可能嘲笑,例如,MyFunc
从myfunc.c
在任何测试,因为我已经有包括文件它以测试它?
(更新)我也知道我可以包括.c
文件而不是.h
文件,然后做一些预处理程序来替换原始调用,例如:
// replace ParseStuff with ParseStuff_wrap
#define ParseStuff ParseStuff_wrap
// include the source instead of the header
#include <myfunc.c>
#undef ParseStuff
int ParseStuff_wrap(char* cmd)
{
// this will get called from MyFunc,
// which is now statically included
}
但这似乎有很多问题,而且我什至没有看到它在任何地方提及。
这是河马的一个简单而简短的解决方案:
我用创建了一个空的Win32控制台应用程序
并在您的示例中添加了代码。
借助河马,您可以模拟每个C函数。这是我的main.cpp的样子:
#include "stdafx.h"
#include "myfunc.h"
#include "hippomocks.h"
extern "C" int ParseStuff(char* cmd);
int _tmain(int argc, _TCHAR* argv[])
{
MockRepository mocks;
mocks.ExpectCallFunc(ParseStuff).Return(4711);
char buf[10] = "";
int result = MyFunc(buf);
return result; //assert result is 4711
}
HippoMocks是一个免费,简单且功能强大的单头框架,可以在GitHub上下载。
希望我已经获得了赏金:)
更新,它是如何工作的:
这是我的机器上的样子:
@ILT+3080(_ParseStuff):
00D21C0D jmp HippoMocks::mockFuncs<char,int>::static_expectation1<0,char *> (0D21DB1h)
如果在内存窗口中看到内存地址00D21C0D(可能与运行时有所不同),则会看到在调用ExpectCallFunc之后,它会被修补。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句