473,396 Members | 2,036 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,396 software developers and data experts.

Problem using gdb. Unwanted optimization?

Hi all,

I have a problem using gdb. I am using Eclipse-CDT as a frontend, but since this problem is obviously related to the gcc compiler or the gdb itself, I have reproduced it without Eclipse.

Sample Program
This small program should suffice to show my problem. I have saved this file as "main.cpp".
Expand|Select|Wrap|Line Numbers
  1. #include<vector>
  2. #include <iostream>
  3.  
  4. struct I{
  5.     std::vector<unsigned> p;
  6.     I() : p(std::vector<unsigned>(1,0)){
  7.         std::cout << "p has length " << p.size() << " and its first value is " << p[0] << std::endl;
  8.     }
  9. };
  10.  
  11. struct T{
  12.     T (I i){
  13.         std::cout << "i.p has length " << i.p.size() << " and its first value is " << i.p[0] << std::endl;
  14.     }
  15. };
  16.  
  17. int main(){
  18.     I i;
  19.     T t(i);
  20. }
I compiled the program - using gcc version 4.4.3 on a PC running Ubuntu 10.04 - by typing
Expand|Select|Wrap|Line Numbers
  1. g++ -O0 -g -o test main.cpp
It runs as expected, printing this output:
Expand|Select|Wrap|Line Numbers
  1. p has length 1 and its first value is 0
  2. i.p has length 1 and its first value is 0
Weird debugging behaviour
My problem is the debugging. Typing "gdb test" I started the following debugging session on the command line:
Expand|Select|Wrap|Line Numbers
  1. GNU gdb (GDB) 7.1-ubuntu
  2. Copyright (C) 2010 Free Software Foundation, Inc.
  3. License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
  4. This is free software: you are free to change and redistribute it.
  5. There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
  6. and "show warranty" for details.
  7. This GDB was configured as "i486-linux-gnu".
  8. For bug reporting instructions, please see:
  9. <http://www.gnu.org/software/gdb/bugs/>...
  10. Reading symbols from /home/jonathan/eclipse-workspace/test/test...done.
  11. (gdb) break main.cpp:19
  12. Breakpoint 1 at 0x80488ab: file main.cpp, line 19.
  13. (gdb) break main.cpp:13
  14. Breakpoint 2 at 0x8048a82: file main.cpp, line 13.
  15. (gdb) run
  16. Starting program: /home/jonathan/eclipse-workspace/test/test 
  17. p has length 1 and its first value is 0
  18.  
  19. Breakpoint 1, main () at main.cpp:19
  20. 19    T t(i);
  21. (gdb) print i
  22. $1 = {p = {<std::_Vector_base<unsigned int, std::allocator<unsigned int> >> = {
  23.       _M_impl = {<std::allocator<unsigned int>> = {<__gnu_cxx::new_allocator<unsigned int>> = {<No data fields>}, <No data fields>}, _M_start = 0x804c008, _M_finish = 0x804c00c, 
  24.         _M_end_of_storage = 0x804c00c}}, <No data fields>}}
  25. (gdb) print {unsigned int}0x804c008
  26. $2 = 0
  27. (gdb) c
  28. Continuing.
  29.  
  30. Breakpoint 2, T (this=0xbffff41f, i=...) at main.cpp:13
  31. 13            std::cout << "i.p has length " << i.p.size() << " and its first value is " << i.p[0] << std::endl;
  32. (gdb) print i
  33. $3 = {p = {<std::_Vector_base<unsigned int, std::allocator<unsigned int> >> = {
  34.       _M_impl = {<std::allocator<unsigned int>> = {<__gnu_cxx::new_allocator<unsigned int>> = {<No data fields>}, <No data fields>}, _M_start = 0xbffff404, _M_finish = 0xbffff408, 
  35.         _M_end_of_storage = 0x80486d4}}, <No data fields>}}
  36. (gdb) print {unsigned int}0xbffff404
  37. $4 = 134529048
  38. (gdb) print {I}0xbffff404
  39. $5 = {p = {<std::_Vector_base<unsigned int, std::allocator<unsigned int> >> = {
  40.       _M_impl = {<std::allocator<unsigned int>> = {<__gnu_cxx::new_allocator<unsigned int>> = {<No data fields>}, <No data fields>}, _M_start = 0x804c018, _M_finish = 0x804c01c, 
  41.         _M_end_of_storage = 0x804c01c}}, <No data fields>}}
  42. (gdb) print {unsigned int}0x804c018
  43. $6 = 0
  44. (gdb) c
  45. Continuing.
  46. i.p has length 1 and its first value is 0
  47.  
  48. Program exited normally.
  49. (gdb) quit
I'll explain the debugging session
First I set two breakpoints, namely at lines 19 and 13. Then I run the program (till before line 19) and let gdb print out the value of variable i. Its type is struct I, thus containing nothing but a std::vector<unsigned int> object, which itself contains three pointers to unsigned int: _M_start, _M_finish, and _M_end_of_storage. I want to know the value of the vector at index 0. I can view it by just dereferencing the _M_start pointer. I do this by printing the memory at adress 0x804c008 parsed as unsigned int. The value is 0, as I expected. Then I let the program run until the next breakpoint on line 13 and have gdb print out i and the memory at _M_start again. The value is 134529048, not 0, as it should be. Now I try dereferencing the alleged _M_start as a pointer to an object of struct I and find it to point to memory just looking like a well-structured I object, with a _M_start pointer to 0. I let my programm continue, it prints out information about i and then exits. I quit gdb.

What I can make of it
struct T's constructor T::T(I) in line 12 should get its argument i as a copy of the variable i in line 18. At least this is how I understand my code. But instead, variable i seems to be copied and then passed to the constructor by reference (technically, a pointer). This is neither call by reference nor call by value, as I understand it. The constructor seems to be able to cope with this, as the correct program output shows. However, the debugger interprets the reference to parameter i like the value of the parameter, which leads to the puzzling output following "print i". gdb's user sees a different i than the program sees.

What my problem is
For me this looks like some unwanted optimization done by the compiler. But I switched off any optimization (I used the -O0 flag). So is this a compiler bug? Or am I missing something here? Actually, I don't care that much about how the compiler handles my code, as long as my program does what it is supposed to (which is the case) and as long as the constructor T::T(I) gets hold of a copy of i, not of i itself (which seems to be the case, too). However, since I work on a project much more complex and I really depend on debugging, I want to view the variable's values and trust this information provided by the gdb. What can I do to make gdb's output reliable? And: Can anyone confirm this behaviour?

I would be delighed to find some help here. Of course and as always, I will be pleased to give more detail which could help solve this problem. Thanks in advance.

~<><~~~~~~~~ presencia
Apr 6 '11 #1
3 2217
mac11
256 100+
I tested on ubuntu 10.01 with gcc 4.4.3 and gdb 7.1, all from standard 'apt-get' and get the same results.

I have another machine that runs much older software (gcc 4.0.3, gdb 6.8) and produces the results you'd expect (shows i.p[0] as a value of 0 instead of 1345somethingsomething).

Sorry, that's about as helpful as I can be at the moment.
Apr 6 '11 #2
mac11
256 100+
Ok, I experimented more by moving the executable built by my old g++ over to the ubuntu box with new gdb and I get the expected (0) result at breakpoint 2 (line 13).

Expand|Select|Wrap|Line Numbers
  1. Breakpoint 2, T (this=0xbffff31b, i=...) at test.cpp:13
  2. 13            std::cout << "i.p has length " << i.p.size() << " and its first value is " << i.p[0] << std::endl;
  3. (gdb) print i
  4. $4 = (I &) @0xbffff328: {
  5.   p = {<std::_Vector_base<unsigned int, std::allocator<unsigned int> >> = {
  6.       _M_impl = {<std::allocator<unsigned int>> = {<__gnu_cxx::new_allocator<unsigned int>> = {<No data fields>}, <No data fields>}, _M_start = 0x804b018, 
  7.         _M_finish = 0x804b01c, 
  8.         _M_end_of_storage = 0x804b01c}}, <No data fields>}}
  9. (gdb) print {unsigned int} 0x804b018
  10. $5 = 0
  11.  
A curiosity that I just noticed is that gdb knows that i is type (I &) in the output above, whereas the output you posted before gdb (as you stated) doesn't get this clue.

So, I'm guessing g++ is a culprit here?
Apr 6 '11 #3
Thanks a lot, mac11, for considering my problem and even trying different gcc versions. This is especially valuable for me since now I know a way to get my code compiled with correct debugging information.

I just installed gcc versions 4.5 and 4.1. When I compile using gcc 4.1 the debugging information seems correct (like in your post). However, the bug stays in version 4.5. Why would the developers have changed that?

Maybe I should file a bug report. I already searched for a bug report that describes this problem but couldn't find one. Would be great if we could just use the up to date compiler versions.
Apr 7 '11 #4

Sign in to post your reply or Sign up for a free account.

Similar topics

1
by: André Gasser | last post by:
hello newsgroup, I just discovered a weird effect in my php code. here is the flow of my code: 1. upload jepg file to server 2. create new (empty) jpeg file using imagecreatefromjpeg()...
4
by: bmiras | last post by:
I've got a problem using urllib2 to get a web page. I'm going through a proxy using user/password authentification and i'm trying to get a page asking for a HTTP authentification. And I'm using...
2
by: Stephen Last | last post by:
Hi all, I have a problem using FSO with a mapped drive. I have mapped x: on our Intranet server to a folder on one of our file servers. The folder contains user home directories. I want to be...
2
by: dorin | last post by:
I wonder if anyone can help me with a problem using the DOM getElementById method. I am using the Xerces Java 2 library to parse an XML file and create and validate the DOM Document. I am able...
0
by: Sansanee | last post by:
Hi, I am having problem using EmployeePrivateAdrUS.GetList through SAP.NET. I used the code below and get the error messgae that the method can not be reflected. I assume taht the problem arise...
4
by: Derek Timothy | last post by:
Hi folks I have strange problem using cmd.exe from asp code I am trying to save the results of an FTP command into a text file. When I run this command from the command line of the web server it...
3
by: Jacky Zhu | last post by:
Hi all, I am having a problem trying to consume a webservice that is developed on ..Net. I can access it without any problem using a .net client, but when I use a java client (based on Axis...
4
by: Dani | last post by:
Hi everyone Description of the problem: Using a PreparedStatement to write down an integer (int) plus a timestamp for testing purposes. When read out again the integer looks very different. We...
2
by: Kent Lewandowski | last post by:
hi all, Recently I wrote some stored procedures using java jdbc code (admittedly my first stab) and then tried to implement the same within java packages (for code reuse). I encountered...
3
by: Franky | last post by:
Been having a problem using a treeview. Work great the first time the form containing it is entered but not the second time. Took a while to create a small sample that exhibits the problem, but...
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.