Infinite Loop when calling a mock function that takes boost::filesystem::path as parameter
Opened this issue · 5 comments
GoogleCodeExporter commented
Minimal example:
---------------------
#include "gtest/gtest.h"
#include "gmock/gmock.h"
#include <boost/filesystem.hpp>
class MyMock {
public:
MOCK_METHOD1(func, void(const boost::filesystem::path &path));
};
TEST(MyTest, mockTest) {
MyMock mock;
mock.func(boost::filesystem::path("/myfile"));
}
-------------------
When running this test (using gtest 1.7.0 and gmock 1.7.0 on linux 64bit with
g++ (Ubuntu 4.9.1-16ubuntu6)), it aborts with a SIGSEV.
gdb shows that the SIGSEV is raised in malloc(), while the stack is very large
and contains a short periodic set of functions calling each other in a circle.
I assume there is an infinite loop.
The interesting part of the stacktrace is here:
#0 _int_malloc (av=0x7ffff703a760 <main_arena>, bytes=26) at malloc.c:3302
#1 0x00007ffff6cff1e0 in __GI___libc_malloc (bytes=26) at malloc.c:2891
#2 0x00007ffff72b7688 in operator new(unsigned long) () from
/usr/lib/x86_64-linux-gnu/libstdc++.so.6
#3 0x00007ffff731b669 in std::string::_Rep::_S_create(unsigned long, unsigned
long, std::allocator<char> const&) () from
/usr/lib/x86_64-linux-gnu/libstdc++.so.6
#4 0x00007ffff731b6f4 in std::string::_M_mutate(unsigned long, unsigned long,
unsigned long) () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#5 0x00007ffff731bd2e in std::string::_M_replace_safe(unsigned long, unsigned
long, char const*, unsigned long) () from
/usr/lib/x86_64-linux-gnu/libstdc++.so.6
#6 0x00007ffff731d1f9 in std::string::replace(unsigned long, unsigned long,
char const*, unsigned long) () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#7 0x00007ffff7779821 in boost::filesystem::path::begin() const () from
/usr/lib/x86_64-linux-gnu/libboost_filesystem.so.1.55.0
#8 0x00000000004c3cd4 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:275
#9 0x00000000004c3846 in testing::internal::PrintTo<boost::filesystem::path>
(value=..., os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#10 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#11 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#12 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
#13 0x00000000004c3846 in testing::internal::PrintTo<boost::filesystem::path>
(value=..., os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#14 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#15 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#16 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
[...many more repetitions of these lines..]
#116387 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#116388 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
#116389 0x00000000004c3846 in
testing::internal::PrintTo<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#116390 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#116391 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#116392 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
#116393 0x00000000004c3846 in
testing::internal::PrintTo<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#116394 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#116395 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#116396 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
#116397 0x00000000004c3846 in
testing::internal::PrintTo<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#116398 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#116399 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#116400 0x00000000004c3d37 in
testing::internal::DefaultPrintTo<boost::filesystem::path> (container=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:287
#116401 0x00000000004c3846 in
testing::internal::PrintTo<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:376
#116402 0x00000000004c2ea6 in
testing::internal::UniversalPrinter<boost::filesystem::path>::Print (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:600
#116403 0x00000000004c237d in
testing::internal::UniversalPrint<boost::filesystem::path> (value=...,
os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:756
#116404 0x00000000004c22d0 in
testing::internal::UniversalPrinter<boost::filesystem::path const&>::Print
(value=..., os=0x7fffffffd720) at
/home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/
gtest-printers.h:668
#116405 0x00000000004c0d81 in
testing::internal::TuplePrefixPrinter<1ul>::PrintPrefixTo<std::tuple<boost::file
system::path const&> > (t=std::tuple containing = {...}, os=0x7fffffffd720)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/gtest-printers.h:810
#116406 0x00000000004bfe71 in
testing::internal::PrintTupleTo<std::tuple<boost::filesystem::path const&> >
(t=std::tuple containing = {...}, os=0x7fffffffd720)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/gtest-printers.h:827
#116407 0x00000000004bd1e5 in
testing::internal::PrintTo<boost::filesystem::path const&> (t=std::tuple
containing = {...}, os=0x7fffffffd720)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/gtest-printers.h:503
#116408 0x00000000004b8eaa in
testing::internal::UniversalPrinter<std::tuple<boost::filesystem::path const&>
>::Print (value=std::tuple containing = {...}, os=0x7fffffffd720)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/gtest-printers.h:600
#116409 0x00000000004b66a6 in
testing::internal::UniversalPrint<std::tuple<boost::filesystem::path const&> >
(value=std::tuple containing = {...}, os=0x7fffffffd720)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gtest/src/gtest/include/gtest/gtest-printers.h:756
#116410 0x00000000004b4e8b in testing::internal::FunctionMockerBase<void
(boost::filesystem::path const&)>::UntypedDescribeUninterestingCall(void
const*, std::ostream*) const (this=0x7fffffffd950, untyped_args=0x7fffffffd8f0,
os=0x7fffffffd720) at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gmock/src/gmock/include/gmock/gmock-spec-builders.h:1604
#116411 0x000000000050204d in
testing::internal::UntypedFunctionMockerBase::UntypedInvokeWith(void const*) ()
#116412 0x00000000004af8af in testing::internal::FunctionMockerBase<void
(boost::filesystem::path
const&)>::InvokeWith(std::tuple<boost::filesystem::path const&> const&)
(this=0x7fffffffd950, args=std::tuple containing = {...})
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gmock/src/gmock/include/gmock/gmock-spec-builders.h:1529
#116413 0x00000000004ad301 in testing::internal::FunctionMocker<void
(boost::filesystem::path const&)>::Invoke(boost::filesystem::path const&)
(this=0x7fffffffd950, a1=...)
at /home/heinzi/workspace_cpp/cryfs/build.debug/test/gmock/src/gmock/include/gmock/gmock-generated-function-mockers.h:97
#116414 0x00000000004c8d7f in MyMock::func (this=0x7fffffffd950, gmock_a1=...)
at /home/heinzi/workspace_cpp/cryfs/src/test/fspp/test.cpp:7
---Type <return> to continue, or q <return> to quit---
#116415 0x00000000004c8b84 in MyTest_mockTest_Test::TestBody (this=0x75bd10) at
/home/heinzi/workspace_cpp/cryfs/src/test/fspp/test.cpp:12
#116416 0x00000000004f34a2 in void
testing::internal::HandleSehExceptionsInMethodIfSupported<testing::Test,
void>(testing::Test*, void (testing::Test::*)(), char const*) ()
#116417 0x00000000004ee2b7 in void
testing::internal::HandleExceptionsInMethodIfSupported<testing::Test,
void>(testing::Test*, void (testing::Test::*)(), char const*) ()
#116418 0x00000000004d429b in testing::Test::Run() ()
#116419 0x00000000004d4b1b in testing::TestInfo::Run() ()
#116420 0x00000000004d51f0 in testing::TestCase::Run() ()
#116421 0x00000000004dbe42 in testing::internal::UnitTestImpl::RunAllTests() ()
#116422 0x00000000004f4a65 in bool
testing::internal::HandleSehExceptionsInMethodIfSupported<testing::internal::Uni
tTestImpl, bool>(testing::internal::UnitTestImpl*, bool
(testing::internal::UnitTestImpl::*)(), char const*) ()
#116423 0x00000000004ef14f in bool
testing::internal::HandleExceptionsInMethodIfSupported<testing::internal::UnitTe
stImpl, bool>(testing::internal::UnitTestImpl*, bool
(testing::internal::UnitTestImpl::*)(), char const*) ()
#116424 0x00000000004da96e in testing::UnitTest::Run() ()
#116425 0x00000000004fe856 in RUN_ALL_TESTS() ()
#116426 0x00000000004fe7f1 in main ()
Original issue reported on code.google.com by heinzis...@gmail.com
on 18 Nov 2014 at 6:27
GoogleCodeExporter commented
btw I'm using libboost-filesystem in version 1.55
Original comment by heinzis...@gmail.com
on 18 Nov 2014 at 6:29
GoogleCodeExporter commented
Can you make an even more minimal example that doesn't depend on Boost?
I'd like to know what it is about boost::filesystem::path that makes this
happen.
Original comment by billydon...@google.com
on 18 Nov 2014 at 6:33
GoogleCodeExporter commented
I tried to, but gave up after some hours. It is quite complicated to resolve
all the inner boost dependencies, boost::filesystem::path is having.
Original comment by heinzis...@gmail.com
on 18 Nov 2014 at 8:12
GoogleCodeExporter commented
I have this bug too.
The problem in function DefaultPrintTo(IsContainerTest<T>(0), is_pointer<T>(),
value, os); [gmock-printers.h]. This function calls infinity times, because it
desides that boost::filesystem::path is container (has cons_iterator), then
takes first element: it = container.begin(), and then calls DefaultPrintTo(...,
*it, ) again (subsequented call) - and we have infifnity calls loop, because
the value_type of path iterator is - path !!!! (we have infinity nested
containers)
Original comment by ibez...@gmail.com
on 23 Apr 2015 at 3:29
GoogleCodeExporter commented
This bug can also be triggered in Visual Studio 2012 with boost 1.51 gmock
1.7.0.
You can work around this bug if you define a PrintTo function. Defining a
PrintTo function is described in
https://code.google.com/p/googletest/wiki/AdvancedGuide#Teaching_Google_Test_How
_to_Print_Your_Values
I use the following PrintTo function:
namespace boost {
namespace filesystem {
void PrintTo(const boost::filesystem::path& path, std::ostream* os) {
*os << path;
}
}
}
Original comment by hb2...@googlemail.com
on 20 May 2015 at 1:32