If you have a statically allocated array, the Visual Studio debugger can easily display all of the array elements. However, if you have an array allocated dynamically and pointed to by a pointer, it will only display the first element of the array when you click the + to expand it. Is there an easy way to tell the debugger, show me this data as an array of type Foo and size X?
Yes, simple.
say you have
char *a = new char[10];
writing in the debugger:
a,10
would show you the content as if it were an array.
There are two methods to view data in an array m4x4:
float m4x4[16]={
1.f,0.f,0.f,0.f,
0.f,2.f,0.f,0.f,
0.f,0.f,3.f,0.f,
0.f,0.f,0.f,4.f
};
One way is with a Watch window (Debug/Windows/Watch). Add watch =
m4x4,16
This displays data in a list:
Another way is with a Memory window (Debug/Windows/Memory). Specify a memory start address =
m4x4
This displays data in a table, which is better for two and three dimensional matrices:
Right-click on the Memory window to determine how the binary data is visualized. Choices are limited to integers, floats and some text encodings.
In a watch window, add a comma after the name of the array, and the amount of items you want to be displayed.
a revisit:
let's assume you have a below pointer:
double ** a; // assume 5*10
then you can write below in Visual Studio debug watch:
(double(*)[10]) a[0],5
which will cast it into an array like below, and you can view all contents in one go.
double[5][10] a;
For,
int **a; //row x col
add this to watch
(int(**)[col])a,row
Yet another way to do this is specified here in MSDN.
In short, you can display a character array as several types of string. If you've got an array declared as:
char *a = new char[10];
You could print it as a unicode string in the watch window with the following:
a,su
See the tables on the MSDN page for all of the different conversions possible since there are quite a few. Many different string variants, variants to print individual items in the array, etc.
You can find a list of many things you can do with variables in the watch window in this gem in the docs:
https://msdn.microsoft.com/en-us/library/75w45ekt.aspx
For a variable a, there are the things already mentioned in other answers like
a,10
a,su
but there's a whole lot of other specifiers for format and size, like:
a,en (shows an enum value by name instead of the number)
a,mb (to show 1 line of 'memory' view right there in the watch window)
For MFC arrays (CArray, CStringArray, ...)
following the next link in its Tip #4
http://www.codeproject.com/Articles/469416/10-More-Visual-Studio-Debugging-Tips-for-Native-De
For example for "CArray pArray", add in the Watch windows
pArray.m_pData,5
to see the first 5 elements .
If pArray is a two dimensional CArray you can look at any of the elements of the second dimension using the next syntax:
pArray.m_pData[x].m_pData,y
I haven't found a way to use this with a multidimensional array. But you can at least (if you know the index of your desired entry) add a watch to a specific value. Simply use the index-operator.
For an Array named current, which has an Array named Attribs inside, which has an Array named Attrib inside, it should look like this if you like to have to position 26:
((*((*current).Attribs)).Attrib)[26]
You can also use an offset
((*((*current).Attribs)).Attrib)+25
will show ne "next" 25 elements.
(I'm using VS2008, this shows only 25 elements maximum).
Related
I routinely have to debug legacy Fortran code that is utilizing large arrays of complex data, and the best option available is TotalView. I have created my own visualizer to view data (as per TotalView's instructions here) that works well. It is more flexible than the default one and has the ability to ingest and display complex data, but TotalView will not send complex arrays through its visualization pipe.
Is there any way to make TotalView be able to display complex data without having to recompile the code with additional debugging arrays just to take the absolute value?
E.g. for code like the following short example, I could make another array in Fortran, but I'd really like to just stop and examine the variable my_arr:
program main
implicit none
integer N, M, i, j
parameter (N=100, M=30)
complex my_arr(N, M)
real pi
pi = ACOS(-1.0)
do j = 1, M
do i = 1, N
my_arr(i,j) = cmplx(i*cos(j/pi), i*sin(j/pi))
end do
end do
return
end
For small arrays I can get away with something like this as an expression:
my_arr%Real_Part**2 + my_arr%Imaginary_Part**2
but that won't work for anything very large, TotalView complains about the memory.
I'm using TotalView 8.13.
You can do this if your array is contiguous in memory and you can adjust your visualizer to input the complex data as a real array with an extra dimension containing the real and imaginary parts.
In your example above, if you 'dive' into the variable my_arr, it will show up as type
COMPLEX(4)(100,30)
This is actually the same as the TotalView built-in $complex_8. You can recast the type and dimensions by simply retyping the following into the "Type:" field:
$real_4(2,100,30)
Then the real and imaginary parts will reside in the first (fastest-iterating) dimension and TotalView will allow you to pass the 3D float array to the visualizer. Note: by default TotalView restricts itself to visualizing 2D arrays, so you'll need to change that to 3D (or however many your visualizer can handle) under "Preferences->Launch Strings" in the "Enable Visualizer Launch" box under "Maximum array rank."
Allocatable arrays:
Dynamically sized arrays can be handled in the same way, but require a couple extra steps.
Usually the address of the reference to the array is not the address of the actual array in memory, so you will have to manually adjust the address of the dive window.
In the dive window on the right side there is an option button just above the scroll bar to indicate what columns are shown in the window - turn on "Address" and write down the hex address of the first element in the array. After you recast by changing the type string, type that hex address into the "Address" field at the top, then your data will show up correctly.
The type string will contain something along the lines of COMPLEX(4),allocatable::(:,:), whereas the "Actual Type" string will show you the dimensions. When you do the recast, make sure to remove the ,allocatable:: and change the (:,:) to the actual dimensions (e.g. (100,30)).
I have the following list of pointers:
(here is a simple example, but in reality, my list could be componed by hundreds of entries)
{0xae5c4e8, 0xa09d4e8, 0xa753458, 0xae554e8}
I successfully print pointers content, one by one, by using :
p *(const Point *) 0xae5c4e8
How can I print contents of the preceding list in one command ?
There is no canned way to do this. It would be cool if you could type print *(*p # 23) -- using the # extension inside another expression, resulting in an implicit loop -- but you can't.
However, there are two decent ways to do this.
One way to do it is to use Python. Something like:
(gdb) python x = gdb.parse_and_eval('my_array')
(gdb) python
> for i in range(nnn):
> print x[i].dereference()
> end
You can wrap this in a new gdb command, written in Python, pretty easily.
Another way is to use define to make your own command using the gdb command language. This is a bit uglier, and has some (minor) limitations compared to the Python approach, but it is still doable.
Finally, once upon a time there was a gdb extension called "duel" that provided this feature. Unfortunately it was never merged in.
I don't think there is a simple way to show all the list elements at once. You could try to iterate through the items using:
set $it=mylist.begin()._M_node
print *(*(std::_List_node<const Point *>*)$it)._M_data
set $it=(*$it)._M_next
...
In the batch way. The problem is that the list items do not need to be located near to each other in the memory. To have better preview option in debug you could switch to the std::vector.
Hope this will help.
I have the following list of pointers:
You don't appear to have a list, you appear to have an array. Let's assume that it looks something like:
void *array[10] = {0xae5c4e8, 0xa09d4e8, 0xa753458, 0xae554e8};
You can print the first 4 dereferenced elements of that array like so:
(gdb) print ((Point**)array)[0]#4
I have structure statically allocated. It has couple of arrays. When I see the values of these arrays they are displayed but all values are zero (0). When I werite this array to file, the values are correct however if I watch the values at the same time in debugger the values show up as zero. I used TRACE to print the values on output window and that is also correct.
So the program is doing all computation correctly but debugger shows the variables' values all zero. I am using VS2010 and C++. Is there a way to fix it?
p.s I have tried other solutions listed around like typing array_name,number in debugger but that doesn't work for me either.
I am trying to simulate a piece of hardware, and this hardware has a static ribbon display.
to do this, I'd like to use a TextView. My display has 10 rows, with 25 columns. So I figured that a TextView should be easy enough.
basically, I would like to be able to say "insert/replace string S at row X, starting at column Y". i may need to only update a specific row, or even a single column within a row.
I have not been successful at getting this to work though. the best I have been able to do is to fill the TextView with 10 lines of 25 spaces when i create it, and then use the get_iter_at_line_offset to get the iterator of a line, and then push the new text onto that line.
but this will start appending text to the line, rather than replacing the existing one.
I need both row and column control (i.e. need to be able to set text at a specific (X,Y) coordinate).
I'm assuming this is somehow possible using marks.
Can anyone give me a quick example of how i can do this? Unfortunately, there isn't a whole lot of documentation on this sort of thing.
You'll have to get an iter at a specific line, row X, and then use the iterator's forward_chars() method to move forward Y characters. Then delete the number of characters you are replacing, and finally insert the text you want to insert. You can do it all with iterators, I think - iterators are invalidated when you change the buffer, but when you delete text, one of your iterators is revalidated to point to the place where the text was.
If you're targetting GTK+ 3.x, you should really look into using Cairo. Since you don't actually need a text buffer, it seems like overkill and a bit of a mis-alignment to use the GtkTextView.
Look at the very basic introduction on how to draw with Cairo in GTK+. Then look at the text-rendering Cairo APIs, that should be enough to get you started.
Is it possible to see the content of a dynamically allocated array, as in:
int *array = new int[dimension];
I only see the value of the pointer.
edit: just found the option "display as an array", but I always have to manually enter the size of the array. Is it possible to get that automagically?
In Eclipse, in order to see the content of a dynamically allocated array (for anyone else who stumbles over this question),
Make sure you are in the debugging perspective;
Look for the "Variables" window. if you don't see it, click "Window" > "Show view" > "Variables";
Right-click on the array variable;
Click "display as array...";
Eclipse does not know how big your array is. So type 0 for the start index and choose the number of elements dynamically allocated for the length. Of course, you can use these values to display any part of the array of your liking.
And, dealing with a pointer, take note of clicking 'Display as Array' when hovering on the pointer itself (arrow icon), and not on the value it is referenced at first (say in the position of (x)= counts in the picture).
Otherwise you get an error of the type
Failed to execute MI command:
-data-evaluate-expression [specifics]
Error message from debugger back end:
Cannot access memory at address 0x[address of older *counts]
showing up in the dialogue window just below the list (starting with "Name:" in the screenshot above).
If you want to avoid having to repeatedly do "Display As Array", open the "Expressions" tab and add the expression (*array#dimension). Not sure why the parentheses are necessary. Without them you'd get an error.
In the "Expressions" tab, if you do what cleong noted and type (*array#dimension) then you can dynamically set the size of the array to display as well. This even works when you need another expression to get it.
So say you have a variable x that contains your array size, you type (*array#x) and it'll use the content of x as a dimension.
"x" can also be things like struct contents or pointer dereferences and the like - i.e.
(*array#SomePtrToStruct->x)
works just fine.
just found the option "display as an array", but I always have to manually enter the size of the array. Is it possible to get that automagically?
That's good. I'd stick with it. Getting the array automatically is not possible in the general case in C or C++, though surely in some trivial cases it could be done (but probably is not, yet--features need to be implemented before they exist, to paraphrase Raymond Chen).