I like the GNU linker functionality to wrap functions a lot. I normally use it mock eg nondeterministic function calls like rand()
. Consider the following example where I would like to write a unit test for giveMeANumber
:
//number.cpp
int giveMeANumber() {
return rand() % 6 + 1;
}
I can wrap the call to rand with the GNU linker functionality wrap like this:
//test.cpp
extern "C" int __wrap_rand(void) {
return 4;
}
void unitTest() {
assert giveMeANumber() == 5;
}
$ g++ test.cpp -o test number.o -Xlinker --wrap=rand
Is there any way to do the same with normal C++ functions? The following does not work, I guess it is because of name mangling. But even when I try it with the mangled name it does not work.
//number.cpp
int foo() {
//some complex calculations I would like to mock
}
int giveMeANumber() {
return foo() % 6 + 1;
}
//test.cpp
extern "C" int __wrap_foo(void) {
return 4;
}
$ g++ test.cpp -o test number.o -Xlinker --wrap=foo
You need to either also extern "C"
the function you want to wrap (if that's possible) or you need to wrap the mangled name, eg, __wrap__Z3foov
and then pass --wrap=_Z3foov
to the linker.
Getting the underscores right is a little tricky. This works for me:
$ cat x.cc
#include <iostream>
using namespace std;
int giveMeANumber();
int main() {
cerr << giveMeANumber() << endl;
return 0;
}
$ cat y.cc
int giveMeANumber() {
return 0;
}
extern "C" int __wrap__Z13giveMeANumberv() {
return 10;
}
$ g++ -c x.cc y.cc && g++ x.o y.o -Wl,--wrap=_Z13giveMeANumberv && ./a.out
10
It seems like you are trying to mock functions and classes for testing. Have you consider using Google Mock
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.