I am using armadillo c++ library for developing a Rcpp package. However I am finding debugging any run time errors from armadillo extremely cumbersome. Currently I have to insert printout after every line to fish out line at which errors are coming. Armadillo just throw errors like:
error: subtraction: incompatible matrix dimensions: 756x1 and 26x1
and it does not tell any information about line number. Using gdb is also not particularly helpful because the error might be coming after many iterations. Is there any better to get line number of where the error is occurring.
I do not know about the Rcpp integration, but I debug my Armadillo code using gdb.
Just make sure that you never catch any exceptions like std::logic_error in your code. If you then run the program from within gdb, it will abort once the error occurs and just by typing bt you get a nice back trace that shows you which line is to blame. And then you also easily inspect variable values etc. in that stack frame.
You do not need to step through the code to make use of the advantages of the debugger.
If Rcpp does not allow avoiding to catch that exception, you should always be able to write a simple C++ test program for your code that does not block the debugger.
Related
I am currently using a large computational package written in c++, which I have downloaded from github and compiled myself as I want to use it for some work I am doing.
The code works well for most purposes. Unfortunately, I have found that for certain inputs the code gives the error: Floating point exception (core dumped)
Now, I am a beginner at c++ and I have had no luck trying to browse through the many scripts that make up the code. My question is therefore: Is there a simple way to get a c++ code to output which line and which script the error occurred? Being used to Python, this is where I would always start, but unfortunately the compiled code does not return any more details about the error. Do I need to compile it in a form of debugging mode to get it to do so?
Yes, you should build the program in debug mode and run it through a debugger. It'll "break" when the error happens and tell you exactly what line of code triggers it. Furthermore, you can examine the values of variables in that stack frame and lower to diagnose the cause of the problem.
In fact, while developing, you should be doing this anyway.
It is impossible to give general steps as to how to do this, but if you're using an IDE (Visual Studio, Xcode) this should automatically happen; if you're using GCC on the command line, research GDB; if you're using Clang on the command line, research LLDB.
Speaking generally, though, a Floating-Point Exception (not a C++ exception!) is usually, and perhaps confusingly, triggered by an integer division by zero. Though, there are other reasons it can occur. You'll know more once you're debugging.
I am a java developer trying my hands on C-C++ code.
Basically I have some build script that uses Visual Studio components to build the application libraries - dlls. We do not use Visual Studio IDE to debug.
But whenever we face some crash in our application, we have to enter the debug statements line by line and need to check the exact line of code in which it is crashing.
Is there any API in C/C++ which would write the stack trace into a file during the crash of our program?
Some kind of event listener that would be called during a program exit and that could print the stack trace and error information into a log file.
I have seen many questions related to this but I am not able to get how to handle this in code rather than debugging tools. I feel Java is very much advanced with respect to error handling.
Thanks in advance!
The Standard does not give you any facilites for this. That said, you can use OS-specific APIs to get what you want. On windows, the easiest is probably to use StackWalker. You do need to take care of SEH oddities yourself. I suggest this article for more information.
On POSIX platforms, you can use the backtrace function from glibc.
In general, both require your program to be compiled with debug information. It is also possible to create crash dumps without symbol names (see Minidumps on Windows), but you will need to decode them (which Visual Studio does for you for example, but you mentioned in your post that you don't use it).
Also, keep in mind that writing crash dumps from a crashing process is very error-prone (since you really have no idea what state your application is at that time). You might get more reliable results if you write the crash dumps from another process. Earlier I've put together a simple example out-of-process crash handler that demonstrates how to implement that.
You can use std::set_terminate to define a function to be called when an exception leaves main() additionally you can install a signal handler for SIGSEGV to catch segmentation faults.
You can get a stack trace (on Linux) using libunwind ( http://www.nongnu.org/libunwind/ ) or use the backtrace() function from libc.
One thing I sometimes do in my own exception classes is to grab and store a stacktrace in the constructor that I can then obtain where I catch the exception and print the trace of where it was thrown from.
You could use <errno.h> in C to handle your error and log them into a log file. The standard flux for the errors is stderr.
One solution to get the error is to use the function perror included in <errno.h> that will display the exact error.
To use it, put it in an error catcher.
if (!fileIsOpen())
perror("File not opened");
I hope it helped.
Background
I've got about a terabyte of files with raw data, with a relatively small subset of labelled data. I've written c++ code (calling some ancient MSVC++2003 code I heavily modified to get it to compile on recent compilers) to aggregate the annotated data slices.
A big part of that labelled data is concentrated in one file, but that file turns out to be the one where my program crashes.
Problem
I'm getting
Invalid parameter passed to C runtime function.
Invalid parameter passed to C runtime function.
terminate called after throwing an instance of 'int'
In my Qt output window, and windows tells me the same in a popup, but at this point it's too late to get any useful info out of the executable / debugger it seems (though I'm not experienced at all with Qt's debugger).
What I have tried
I've googled all over and found plenty of people with this error message but it's so generic that none of their issues could be the same as mine, and there's such a long list of different C runtime functions that sifting through all of them is slow and it doesn't seem to help.
My question
"Find a man a bug, and you help him for a day. Teach a man to debug and you help him for a lifetime. Post the way on stackoverflow and you help many men and get a lot of upvotes."
Is there a generic method to find what C runtime function the problem was and what the argument was? Did I miss some fancy debugger features? Is there anything else you could recommend or info I could provide?
I'd hope to get a catch-all answer to this to help everyone with this problem, not just me, but I'll be glad if I'm helped too of course.
Specific to my problem:
My stack trace is as follows:
0 ntdll!DbgBreakPoint 0x7727000d
1 ntdll!DbgUiRemoteBreakin 0x772ff156
2 ?? 0x6f06eaa1
3 KERNEL32!BaseThreadInitThunk 0x7501338a
4 ntdll!RtlInitializeExceptionChain 0x77299902
5 ntdll!RtlInitializeExceptionChain 0x772998d5
6 ??
and gdb can't get a better trace it seems (anything I try to do with it gets me a timeout error).
After trying a couple more functions just to be sure everything gave a timeout trying "backtrace" once again did give me a result. I guess I just never put this much time in gdb after it timeouting on me once.
That said, I might be able to find something with this new info. Consider my specific problem closed, but my general point is still valid I believe: I've now found the function with the problem (I think), but not why it is a problem, nor what the invalid parameter is. Even better, I've traced it to a line where it says "throw 1". So now I'm assuming windows/Qt translates that to the "invalid parameter". But it's not true.
It can just be some bad code, it does not even need to be a C function, and nothing needs to be wrong with your parameters.
...
#17 0x00c17d72 in libstdc++-6!.cxa_throw () from C:\Qt\5.5\mingw492_32\bin\libstdc++-6.dll
No symbol table info available.
...
Since the log is printed to the debug console then it should be reported by OutputDebugStringA function. You can place a breakpoint on the function to see who results in that log. To place a breakpoint on a function you can Ctrl+B in Visual Studio and enter function name:
But this might not work, or you may have too many other messages logged using OutputDebugStringA. Usually Invalid parameter passed to C runtime function is reported by _invalid_parameter, so, you may as well try to place a breakpoint on _invalid_parameter function. This might not work as well because it could be reported from some other system dll that your process links to: ntdll.dll, KernelBase.dll etc. To place a breakpoint on a function exported by a dll you need to use: <dll>!<exportname>:
_invalid_parameter
ntdll.dll!__invalid_parameter
KernelBase.dll!__invalid_parameter
msvcrt.dll!__invalid_parameter
ucrtbase.dll!__invalid_parameter
All of these are different functions and you can see their addresses:
In my case only when I set a breakpoint on ntdll.dll!__invalid_parameter I was able to see backtrace and the log message was caused by GetAdaptersAddresses winapi. The reason breakpoint on OutputDebugStringA wasn't helpful was because the log was printed through DbgPrint api. Placing breakpoint on DbgPrint works in this case.
In Visual Studio 2017 at least, you can hit CTRL+B and add a function breakpoint on _invalid_parameter. This will stop your program at the point where the message would have been logged, which will let you find the offending function in the call stack. It will work even if someone else's code undoes your call to _CrtSetReportMode().
Things I learned from this question (and that might help people searching for this question) :
Turns out that this error could be traced back to a line of code saying
throw 1;
This means It can just be some bad code, it does not even need to be a C function, and nothing needs to be wrong with your parameters. Searching your code and libraries' source for "throw"
Turns out that getting timeouts on gdb are not an indicator of anything. Keep trying things and retrying and maybe at one time you might get a stack trace.
Personally, on a Linux terminal, I use gcc for compiling and gdb for debugging. To compile a program with debugging options using gcc, you simply have to add a -g to your other flags. Ex:gcc file.c -o file -std=c99 -g. You can then type gdb file and you enter into an interactive debugger. Among other helpful things, you can run the program, call functions and insert breakpoints. For a full and well explained usage go to this website-http://www.tutorialspoint.com/gnu_debugger/index.htm
I ran into this same error message "Invalid parameter..." while debugging a windows driver.
The technique on this page, even though for Windows and not exactly addressing for this question, might be useful to someone who is looking for this particular error message. IOW HTH..
http://dennisyurichev.blogspot.com/2013/05/warning-invalid-parameter-passed-to-c.html
So in summary you have to narrow down specific to your environment where a debug string is being output by possibly a debugging "helper" library function. Once known, set a breakpoint there and then look back up the call stack. IMHO, it's a very clever solution to what can be a tough location to find.
If you are using MinGW only (no Visual Studio build stuff). Try compiling your application for the Console subsystem instead of the Windows subsystem when building debug version. In that case when an invalid argument is passed to a C function the function will fail and will trip your error handling code instead of the standard library's error box which should give you better control over what is happening.
We are using Google Test as our C++ unit testing framework. But I ran into a painful situation and don't know how to deal with.
Basically, when there is an uncaught exception in the code, I got the following error message printed in the console and get a FAILED. Obviously, the exception is captures by google test. However, I have no information at all where is the exception was throw.
unknown file: error: SEH exception with code 0xc000005 thrown in the test body.
What I can do is debug and step through the code and I will eventually figure out where the problem is. But this is not very efficient as the project is big.
I want the debugger to stop at the line of uncaught exception and give me a nice call stack. Is there any settings in google test that I don't know of? Any other work around or suggestions will be very much appreciated.
Edit: I am looking for something like the following under Windows
Finally according to the answers, I found this settings for visual studio and everything works as the way I want now :)
At work the approach I use is to run only the failing testcase using gdb like so:
gdb /path/to/test
catch throw
r --gtest_filter='Test.Testcase' --gmock_verbose=info
bt
With visual studio, I suspect you should be able to start your binary with arguments as above, and set a breakpoint to any throw, then take a look at the backtrace.
An SEH Exception is NOT a C++ exception.
It is a windows exception that is throw outside of the standard C++ framework for exception handing (there is a different syntax for catching them).
The best way to find the location is to run this inside DevStudio. Its been a while but I am sure DevStudio has an option to break when SEH exception is thrown. Just turn this on and your debugger will stop at the throw point and allow you to debug.
See: https://msdn.microsoft.com/en-us/library/d14azbfh.aspx
As noted by #MatthiasVegh you should pass the name of the test as well so you don't have to run through all the tests.
That is not possible since C++ doesn't keep stack trace in the exception object and even if gtest had some smart catching mechanism it would have no means to know where the exception came from. The best you can do is to store some information in the exception yourself and check it in the test case.
I am learning TDD and using CppUTest in eclipse.
Is there any way to debug my code getting a nagging segmentation fault.
Thanks
I don't know anything special in CppUTest or Eclipse to help you, but some generic segfault debugging ideas seem appropriate here:
Add flushing print statements (e.g. printf(...) + fflush(stdout) or fprintf(stderr, ...)) to your code and see what gets printed. Do this in a binary search fashion with just a few prints at a time until you narrow down exactly where it is crashing. This sounds old fashioned but is extremely effective. Here is a guide I found googling that talks about this well-known technique: http://www.floccinaucinihilipilification.net/blog/2011/3/24/debugging-via-binary-search.html
Compile your code with debugging symbols and run it in a debugger. When you hit your segfault, ask for a backtrace and see if you can figure out what happened. When doing this it can be especially helpful to use a graphical debugger.
Run your code with a debugging tool like a debug malloc library or something from the valgrind suite. This may catch problems that are root causes of your segfaults but aren't occuring at the exact place where the segfault is generated (e.g. double frees, out of bound array access clobbering pointers used later, etc).
It would be helpful if you could add some code to your question, to give us a better idea of what you are up against. Not knowing any of the details, I would suggest the following:
Add -vto your executable's arguments in the Debug dialog. This will print the names of your test cases as they are executed. The last name that prints is likely the test where the segmentation fault occurs.
Put a breakpoint in that test case, where you call your code under test
Step into your code until the segfault occurs.
Trace back the value that caused the segfault (most often, a dangling pointer) and find out, why it was NULL or uninitialized.