2

I have a multithreaded program, in which some thread causes an exception. I ran it in gdb, which gives the following output after the exception occurred and the program is terminated:

terminate called after throwing an instance of 'std::out_of_range'
  what():  vector::_M_range_check: __n (which is 0) >= this->size() (which is 0)

Thread 46 "MyProgram" received signal SIGABRT, Aborted.
[Switching to Thread 0x7fff3bfff700 (LWP 24491)]
0x00007ffff48f2428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54
54      ../sysdeps/unix/sysv/linux/raise.c: No such file or directory.
(gdb) where
#0  0x00007ffff48f2428 in __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:54
#1  0x00007ffff48f402a in __GI_abort () at abort.c:89
#2  0x00007ffff514d0d5 in __gnu_cxx::__verbose_terminate_handler() () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#3  0x00007ffff514acc6 in ?? () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#4  0x00007ffff514ad11 in std::terminate() () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#5  0x00007ffff517719e in ?? () from /usr/lib/x86_64-linux-gnu/libstdc++.so.6
#6  0x00007ffff4c8e6ba in start_thread (arg=0x7fff3bfff700) at pthread_create.c:333
#7  0x00007ffff49c441d in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:109

The output from where does not really help to find out which thread causes the problem.

Is there a way to get more information out of this situation?

jww
  • 97,681
  • 90
  • 411
  • 885
Bobface
  • 2,782
  • 4
  • 24
  • 61

2 Answers2

2

When you see this output it is too late to find out what thread have thrown an exception because your program is already terminated. I guess what you need is to set catchpoint on std::out_of_range exception and continue running your program until this exception is thrown:

(gdb) catch throw out_of_range

When exception is thrown, gdb should stop and you can print backtrace of thread that causes an exception.

ks1322
  • 33,961
  • 14
  • 109
  • 164
  • and how to get know `what()` – kyb Nov 16 '22 at 17:06
  • @kyb, you may try to call and print `what()` result on exception object with `p ex.what()` – ks1322 Nov 16 '22 at 18:09
  • in __cxa_throw there is no symbols at all. I have no debug symbols. So I found a sequence to go `backtrace` or `bt` => find the frame exception was thrown from and select it `f 3`, then `info locals`. Among variables I see `std::string strerr` with message contents. – kyb Nov 16 '22 at 20:32
0

For those ones who go after us. I was come to the same issue:

where

And it text

Thread 1 "Auditor_Tst" hit Catchpoint 1 (exception thrown), 0xb6a07b48 in __cxa_throw () from /usr/lib/libstdc++.so.6
(gdb) bt
#0  0xb6a07b48 in __cxa_throw () from /usr/lib/libstdc++.so.6
#1  0xb6f3105e in Utils::(anonymous namespace)::getSubJson (j=..., key=...) at ../Src/Auditor/GetterJsonValue.cpp:61
#2  0xb6f31270 in Utils::getJsonValueByPath (json=..., keyList=...) at ../Src/Auditor/GetterJsonValue.cpp:132
#3  0xb6f42b76 in Utils::getJsonValueByPathAs<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > (json=..., keyList=...) at ../Src/Auditor/Helper/GetterJsonValue.hpp:136
#4  0xb6f5c852 in Utils::getJsonValueByPathAs<std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > > (json=..., keyList=..., defaultValue=...) at ../Src/Auditor/Helper/GetterJsonValue.hpp:155
#5  0xb6f80488 in Auditor::LogProcessor::extractBeginDate (message=..., isInvalid=@0xbefff2bd: false) at ../Src/Auditor/AuditorProcessor.cpp:320
#6  0xb6f7f9a6 in Auditor::LogProcessor::processHistory (this=0xbefff750, message=...) at ../Src/Auditor/AuditorProcessor.cpp:197
#7  0xb6f7f4ca in Auditor::LogProcessor::process (this=0xbefff750, message=...) at ../Src/Auditor/AuditorProcessor.cpp:135
#8  0x00106eb0 in Auditor::Processor_Test_requestEmptyHitoryJson_Test::TestBody (this=0x16fef8) at ../Tst/Auditor/AuditorProcessorTests.cpp:262
#9  0xb6b75fa2 in testing::internal::HandleSehExceptionsInMethodIfSupported<testing::Test, void> (object=0x16fef8, method=&virtual testing::Test::TestBody(), location=0xb6b86330 "the test body") at ../Tools/googletest/googletest/src/gtest.cc:2607
#10 0xb6b7054a in testing::internal::HandleExceptionsInMethodIfSupported<testing::Test, void> (object=0x16fef8, method=&virtual testing::Test::TestBody(), location=0xb6b86330 "the test body") at ../Tools/googletest/googletest/src/gtest.cc:2643
#11 0xb6b5092e in testing::Test::Run (this=0x16fef8) at ../Tools/googletest/googletest/src/gtest.cc:2682
#12 0xb6b51056 in testing::TestInfo::Run (this=0x160a00) at ../Tools/googletest/googletest/src/gtest.cc:2861
#13 0xb6b516f2 in testing::TestSuite::Run (this=0x160490) at ../Tools/googletest/googletest/src/gtest.cc:3015
#14 0xb6b5c820 in testing::internal::UnitTestImpl::RunAllTests (this=0x15dd90) at ../Tools/googletest/googletest/src/gtest.cc:5851
#15 0xb6b76d42 in testing::internal::HandleSehExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool> (object=0x15dd90, method=(bool (testing::internal::UnitTestImpl::*)(testing::internal::UnitTestImpl * const)) 0xb6b5c571 <testing::internal::UnitTestImpl::RunAllTests()>, location=0xb6b86dbc "auxiliary test code (environments or event listeners)") at ../Tools/googletest/googletest/src/gtest.cc:2607
#16 0xb6b71136 in testing::internal::HandleExceptionsInMethodIfSupported<testing::internal::UnitTestImpl, bool> (object=0x15dd90, method=(bool (testing::internal::UnitTestImpl::*)(testing::internal::UnitTestImpl * const)) 0xb6b5c571 <testing::internal::UnitTestImpl::RunAllTests()>, location=0xb6b86dbc "auxiliary test code (environments or event listeners)") at ../Tools/googletest/googletest/src/gtest.cc:2643
#17 0xb6b5b738 in testing::UnitTest::Run (this=0xb6ba6dd8 <testing::UnitTest::GetInstance()::instance>) at ../Tools/googletest/googletest/src/gtest.cc:5434
#18 0x0012a22a in RUN_ALL_TESTS () at ../Tools/googletest/googletest/include/gtest/gtest.h:2471
#19 0x0012a1b6 in main (argc=1, argv=0xbefffc54) at ../Tst/Auditor/AuditorMain.cpp:10

frame1

(gdb) frame 1
#1  0xb6f3105e in Utils::(anonymous namespace)::getSubJson (j=..., key=...) at ../Src/Auditor/GetterJsonValue.cpp:61
61      in ../Src/Auditor/GetterJsonValue.cpp
(gdb) info locals
error = {static npos = 4294967295, _M_dataplus = {<std::allocator<char>> = {<__gnu_cxx::new_allocator<char>> = {<No data fields>}, <No data fields>}, _M_p = 0x162940 "Key 'begin-date' not found in {\"msg-name\":\"get-audit-log\",\"msg-type\":\"req\",\"val\":12,\"res\":\"ok\"}."}, _M_string_length = 96, {_M_local_buf = "`\000\000\000\330\006\354\266\254\361\377\276`\221\377\266", _M_allocated_capacity = 96}}
__func__ = "getSubJson"
(gdb) p (char*)error
$6 = 0x162940 "Key 'begin-date' not found in {\"msg-name\":\"get-auditor-name\",\"msg-type\":\"req\",\"val\":12,\"res\":\"ok\"}."

last line shows what is passed to constructor of exception, this is what it would return from what()

kyb
  • 7,233
  • 5
  • 52
  • 105