Author Topic: Problem with debugger  (Read 15975 times)

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Problem with debugger
« on: March 08, 2007, 05:38:22 pm »
Hi,

I just upgraded to SVN using wxGTK 2.6.3 patch2. I have compiled it in Linux. I have typically used C::B in Windows. The problem I seem to be having is during debugging. I am able to set break points but when I start the debugger my program does not start in a terminal. The debugger is active and I can step through the program if break points are set before any user input is required but as soon as it hits a cin >> I have to force the debugger to close. What am I overlooking during my transition from Windows to Linux.

PS, yes I have debugging symbols included and am compiling in Debug mode.

Thanks, Mark.

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #1 on: March 08, 2007, 06:44:44 pm »
Here's a patch to add a Linux debugging console.

Code: [Select]
Index: debuggergdb.cpp
===================================================================
--- debuggergdb.cpp (revision 3659)
+++ debuggergdb.cpp (working copy)
@@ -233,6 +233,10 @@
     {
         NotifyMissingFile(_T("debugger.zip"));
     }
+    // vars for Linux console //(pecan 2007/2/06)
+    m_bIsConsole = false;
+    m_nConsolePid = 0;
+    m_ConsoleTty = wxEmptyString;
 }
 
 DebuggerGDB::~DebuggerGDB()
@@ -1021,6 +1025,21 @@
     m_State.GetDriver()->Prepare(target && target->GetTargetType() == ttConsoleOnly);
     m_State.ApplyBreakpoints();
 
+   #ifdef __WXGTK__    //(pecan 2007/2/05)
+    // create xterm and issue tty "/dev/pts/#" to GDB where
+    // # is the tty for the newly created xterm
+    m_bIsConsole = (target && target->GetTargetType() == ttConsoleOnly);
+    if (m_bIsConsole)
+    {
+        if (RunNixConsole() > 0 )
+        {   wxString gdbTtyCmd;
+            gdbTtyCmd << wxT("tty ") << m_ConsoleTty;
+            m_State.GetDriver()->QueueCommand(new DebuggerCmd(m_State.GetDriver(), gdbTtyCmd, true));
+            DebugLog(wxString::Format( _("Queued:[%s]"), gdbTtyCmd.c_str()) );
+        }
+    }//if
+   #endif//def __WXGTK__
+
     // Don't issue 'run' if attaching to a process (Bug #1391904)
     if (m_PidToAttach == 0)
         m_State.GetDriver()->Start(m_BreakOnEntry);
@@ -1503,12 +1522,21 @@
 
 void DebuggerGDB::Stop()
 {
+    // m_Process is PipedProcess I/O; m_Pid is debugger pid
     if (m_pProcess && m_Pid)
     {
         if (IsStopped())
         {
             RunCommand(CMD_STOP);
             m_pProcess->CloseOutput();
+           #ifdef __WXGTK__
+            // kill any linux console //(pecan 2007/2/06)
+            if ( m_bIsConsole && (m_nConsolePid > 0) )
+            {
+                ::wxKill(m_nConsolePid);
+                m_nConsolePid = 0;
+            }
+           #endif
         }
         else
         {
@@ -2196,3 +2224,101 @@
 {
     Configure();
 }
+// ----------------------------------------------------------------------------
+int DebuggerGDB::RunNixConsole()
+// ----------------------------------------------------------------------------
+{
+    // start the xterm and put the shell to sleep with -e sleep 80000
+    // fetch the xterm tty so we can issue to gdb a "tty /dev/pts/#"
+    // redirecting program stdin/stdout/stderr to the xterm console.
+
+  #ifndef __WXMSW__
+    wxString cmd;
+    wxString title = wxT("Program Console");
+    m_nConsolePid = 0;
+    // for non-win platforms, use m_ConsoleTerm to run the console app
+    wxString term = Manager::Get()->GetConfigManager(_T("app"))->Read(_T("/console_terminal"), DEFAULT_CONSOLE_TERM);
+    //term.Replace(_T("$TITLE"), _T("'") + _T("*nixConsole") + _T("'"));
+    term.Replace(_T("$TITLE"), _T("'") + title + _T("'"));
+    cmd << term << _T(" ");
+    cmd << wxT("sleep ");
+    cmd << 80000 + ::wxGetProcessId(); //make a unique sleep command
+
+    Manager::Get()->GetMacrosManager()->ReplaceEnvVars(cmd);
+    //Manager::Get()->GetMessageManager()->Log(m_PageIndex, _("Executing: %s"), cmd.c_str() );
+    DebugLog(wxString::Format( _("Executing: %s"), cmd.c_str()) );
+    //start xterm -e sleep {some unique # of seconds}
+    m_nConsolePid = wxExecute(cmd, wxEXEC_ASYNC);
+    if (m_nConsolePid <= 0) return -1;
+
+    // Issue the PS command to get the /dev/tty device name
+    // First, wait for the xterm to settle down, else PS won't see the sleep task
+    Manager::Yield();
+    ::wxSleep(1);
+    m_ConsoleTty = GetConsoleTty(m_nConsolePid);
+    if (not m_ConsoleTty.IsEmpty() )
+        return m_nConsolePid;
+    // failed to find the console tty
+    DebugLog( wxT("Console Execution error:failed to find console tty."));
+    ::wxKill(m_nConsolePid);
+    m_nConsolePid = 0;
+  #endif//ndef __WWXMSW__
+    return -1;
+}
+// ----------------------------------------------------------------------------
+wxString DebuggerGDB::GetConsoleTty(int ConsolePid)
+// ----------------------------------------------------------------------------
+{
+    // execute the ps -xo command  and read PS output to get the /dev/tty field
+
+ unsigned long ConsPid = ConsolePid;
+ wxString psCmd;
+ wxArrayString psOutput;
+ wxArrayString psErrors;
+
+ psCmd << wxT("ps x -o tty,pid,command");
+    DebugLog(wxString::Format( _("Executing: %s"), psCmd.c_str()) );
+ int result = wxExecute(psCmd, psOutput, psErrors, wxEXEC_SYNC);
+ psCmd.Clear();
+ if (result != 0)
+ {   psCmd << wxT("Result of ps x:") << result;
+        DebugLog(wxString::Format( _("Execution Error:"), psCmd.c_str()) );
+        return wxEmptyString;
+ }
+
+    wxString ConsTtyStr;
+    wxString ConsPidStr;
+    ConsPidStr << ConsPid;
+    //find task with our unique sleep time
+    wxString uniqueSleepTimeStr;
+    uniqueSleepTimeStr << wxT("sleep ") << 80000 + ::wxGetProcessId();
+    // search the output of "ps pid" command
+    int knt = psOutput.GetCount();
+    for (int i=knt-1; i>-1; --i)
+    {   psCmd = psOutput.Item(i);
+        DebugLog(wxString::Format( _("PS result: %s"), psCmd.c_str()) );
+        // find the pts/# or tty/# or whatever it's called
+        // by seaching the output or out "ps x" command.
+        // The output of ps looks like:
+        // TT       PID   COMMAND
+        // pts/0    13342 /bin/sh ./run.sh
+        // pts/0    13343 /home/pecan/devel/trunk/src/devel/codeblocks
+        // pts/0    13361 /usr/bin/gdb -nx -fullname -quiet -args ./conio
+        // pts/0    13362 xterm -font -*-*-*-*-*-*-20-*-*-*-*-*-*-* -T Program Console -e sleep 93343
+        // pts/2    13363 sleep 93343
+        // ?        13365 /home/pecan/proj/conio/conio
+        // pts/1    13370 ps x -o tty,pid,command
+
+        if (psCmd.Contains(uniqueSleepTimeStr))
+        {   // found sleep 93343 string, extract tty field
+            ConsTtyStr = wxT("/dev/") + psCmd.BeforeFirst(' ');
+            DebugLog(wxString::Format( _("TTY is[%s]"), ConsTtyStr.c_str()) );
+            return ConsTtyStr;
+        }//if
+    }//for
+
+    knt = psErrors.GetCount();
+    for (int i=0; i<knt; ++i)
+        DebugLog(wxString::Format( _("PS Error:%s"), psErrors.Item(i).c_str()) );
+    return wxEmptyString;
+}
Index: debuggergdb.h
===================================================================
--- debuggergdb.h (revision 3659)
+++ debuggergdb.h (working copy)
@@ -205,6 +205,13 @@
 
         int m_HookId; // project loader hook ID
 
+        // Linux console support
+        int      RunNixConsole();
+        wxString GetConsoleTty(int ConsolePid);
+        bool     m_bIsConsole;
+        int      m_nConsolePid;
+        wxString m_ConsoleTty;
+
  DECLARE_EVENT_TABLE()
 };
 


Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #2 on: March 08, 2007, 07:02:47 pm »
Thank you! I applied the patch. When I start the debugger the terminal opens for a brief second and closes before I can see if there is any output to the screen. Does this patch work with last nights revision? Im trying to think of why it may be closing before I even get to a breakpoint.

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #3 on: March 08, 2007, 07:36:31 pm »
I reverted to SVN 3659 but the problem with the console automatically closing remains. This is quite upsetting as I had been using CodeBlocks under the assumption it was full platform independent. Any other suggestions?

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #4 on: March 08, 2007, 07:38:34 pm »
Hold on for a couple of hours. I'll update and see what's going on.

This patch has been working for me for some time now. Something must have changed.

What OS/distribution are you using.

Can you give me a short minimal pgm that causes the problem?
« Last Edit: March 08, 2007, 07:48:02 pm by Pecan »

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #5 on: March 08, 2007, 07:53:58 pm »
Here is the debugger console working with cout/cin in SVN 3659



Now I'll update to the latest svn.

Could you please attach a minimal pgm that fails for you.

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #6 on: March 08, 2007, 08:01:49 pm »
Try this source with the console and see if it runs for you.

Code: [Select]
#include <iostream>
#include <cstdlib>
#include <cstring>

using namespace std;

int upstring(char *value);


int main()
{
    //asm("int3");
        char value[81]={'\0'};
        int upper_count;

        // perform i/o operation
        do
    {   cout << "Please type in a String (max. 80 characters): ";
        cin.getline(value, 80);
        //strcpy(value,"FakeReply");
        upper_count = upstring(value);
        cout << upper_count << " characters are converted" << endl;
        cout << "The new string is now: " << value << endl;
        if ( (strlen(value) >3) && (0==strncmp(value,"LOOP",4) ))
            break;
    }while(upper_count);

    // perform infinite loop if user entered text "loop"
    if ( (strlen(value) >3) && (0==strncmp(value,"LOOP",4)) )
    {
        int i = 0;
        while(true){
            cout<<".";cout.flush();
            ++i;
            sleep(1);
        }
    }
  return EXIT_SUCCESS;
}

int upstring(char *value)
{
  int i=0;
  while(*value)
  {
    if(islower(*value))
    {
      *value=toupper(*value);
      i++;
    }
  value++;
  }
  return(i);
}



Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #7 on: March 08, 2007, 08:09:23 pm »
I am running Slackware 11 Kernel 2.6.20.

I am not sure if you mean a screen capture when you say PGM. It would be extremely difficult for me to catch the popup for you to see.

I tried executing your code. Works fine build/run but when I add a breakpoint and try to debug the console just pops up and dies again.

The patch was applied successfully in case you are wondering.

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #8 on: March 08, 2007, 08:13:04 pm »
I checked if X reported any problem.

Code: [Select]
-------------- Build: Debug in test ---------------
Compiling: test.cpp
Linking console executable: bin/Debug/test
Process terminated with status 0 (0 minutes, 1 seconds)
0 errors, 0 warnings
X Error: BadWindow (invalid Window parameter) 3
  Major opcode:  2
  Minor opcode:  0
  Resource id:  0x1000009


Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #9 on: March 08, 2007, 08:26:13 pm »
Uh oh,

This patch issues xterm -e sleep 80000+some pid number
in order to put the shell into a coma. Then it tells gdb to use the tty that it finds sleeping.

I guess the Slackware console starts running, but never sleeps on Slack.

So... how does Slack put a shell to sleep?

Can you issue an

xterm
sleep 60

Can you issue an xterm -e sleep 60

what happens?


« Last Edit: March 08, 2007, 08:28:15 pm by Pecan »

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #10 on: March 08, 2007, 08:33:49 pm »
Would you turn on the Debuggers debugging log:

MainMenu=>Settings=>Compiler and Debugger=>Debugger Settings=>check Display Debuggers log

Now debug youf program again and paste the contents of the tab marked "Debugger (debug)" and also the contents of the tab marked "Debugger".

Let's see what gdb sees.

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #11 on: March 08, 2007, 08:35:20 pm »
The xterm -e sleep 60 is working when I type it into another console

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #12 on: March 08, 2007, 08:38:50 pm »
Code: [Select]
Building to ensure sources are up-to-date
Build succeeded
Selecting target: Debug
Adding source dir: /home/mark/test/
Adding source dir: /home/mark/test/
Adding file: bin/Debug/test
Starting debugger: done
Registered new type: wxString
Registered new type: STL String
Registered new type: STL Vector
Setting breakpoints
Debugger name and version: GNU gdb 6.5
At /home/mark/test/test.cpp:18
At /home/mark/test/test.cpp:19

I used the program you posted and set the break right before the cin. I stepped until it got to the cin and then I am forced to stop the debugger manually.

Offline Pecan

  • Plugin developer
  • Lives here!
  • ****
  • Posts: 2143
Re: Problem with debugger
« Reply #13 on: March 08, 2007, 08:40:44 pm »
This is the Debugger log. I also need the "Debuggers (debug)" log as mentioned above. You may have to use the little black arrow at the right of the tabs to get to it.

Offline kramed

  • Multiple posting newcomer
  • *
  • Posts: 24
Re: Problem with debugger
« Reply #14 on: March 08, 2007, 08:42:18 pm »
Code: [Select]
Command-line: /usr/bin/gdb -nx -fullname  -quiet -args bin/Debug/test
Working dir : /home/mark/test/
> set prompt >>>>>>cb_gdb:
Executing: xterm -T 'Program Console' -e sleep
Using host libthread_db library "/lib/tls/libthread_db.so.1".
(gdb) >>>>>>cb_gdb:
> show version
GNU gdb 6.5
Copyright (C) 2006 Free Software Foundation, Inc.
GDB is free software, covered by the GNU General Public License, and you are
welcome to change it and/or distribute copies of it under certain conditions.
Type "show copying" to see the conditions.
There is absolutely no warranty for GDB.  Type "show warranty" for details.
This GDB was configured as "i486-slackware-linux".
>>>>>>cb_gdb:
> set confirm off
>>>>>>cb_gdb:
> set width 0
>>>>>>cb_gdb:
> set height 0
>>>>>>cb_gdb:
> set breakpoint pending on
>>>>>>cb_gdb:
> set print asm-demangle on
>>>>>>cb_gdb:
> set unwindonsignal on
>>>>>>cb_gdb:
> set disassembly-flavor att
>>>>>>cb_gdb:
> directory /home/mark/test/
>>>>>>cb_gdb:
> delete breakpoints
>>>>>>cb_gdb:
> break "/home/mark/test/test.cpp:17"
Breakpoint 1 at 0x8048a5b: file /home/mark/test/test.cpp, line 17.
>>>>>>cb_gdb:
Executing: ps x -o tty,pid,command
PS result: ?        27347 gaim
PS result: ?        27119 kio_file [kdeinit] file /tmp/ksocket-mark/klauncherMOSOQb.slave-socket /tmp/ksocket-mark/kdevelopKzOKsa.slave-socket
PS result: ?        25985 konqueror [kdeinit] --silent         
PS result: ?        20333 /usr/local/apps/firefox/firefox-bin
PS result: ?        20328 /bin/sh /usr/local/apps/firefox/run-mozilla.sh /usr/local/apps/firefox/firefox-bin
PS result: ?        20325 /bin/sh /usr/local/apps/firefox/firefox
PS result: ?        15990 xchat
PS result: ?        12097 kio_uiserver [kdeinit]               
PS result: ?         3253 ps x -o tty,pid,command
PS result: ?         3240 /usr/bin/gdb -nx -fullname -quiet -args bin/Debug/test
PS result: ?         2537 codeblocks
PS result: ?         1694 konqueror [kdeinit] -session 108f363330000117332767600000070480034_1173327676_271749
PS result: ?         1645 superkaramba -session 108f363330000117290000300000036900011_1173329213_704079
PS result: ?         1644 superkaramba -session 108f363330000117290000100000036900010_1173329213_704426
PS result: ?         1642 superkaramba -session 108f363330000117285908400000027280029_1173329213_704201
PS result: ?         1638 kaccess [kdeinit]                     
PS result: ?         1630 kicker [kdeinit]                     
PS result: ?         1627 kdesktop [kdeinit]                   
PS result: ?         1623 kwin [kdeinit] -session 108f363330000117208531500000062480000_1173329221_738408
PS result: ?         1621 ksmserver [kdeinit]                   
PS result: tty1      1619 kwrapper ksmserver
PS result: ?         1606 kded [kdeinit] --new-startup         
PS result: ?         1604 klauncher [kdeinit] --new-startup     
PS result: ?         1600 dcopserver [kdeinit] --nosid         
PS result: ?         1597 kdeinit Running...                   
PS result: tty1      1569 /bin/sh /opt/kde/bin/startkde
PS result: tty1      1567 /bin/sh /usr/X11R6/lib/X11/xinit/xinitrc
PS result: tty1      1556 /usr/X11R6/bin/xinit /usr/X11R6/lib/X11/xinit/xinitrc -- -auth /home/mark/.serverauth.1540
PS result: tty1      1540 /bin/sh /usr/X11R6/bin/startx
PS result: tty1      1514 -bash
PS result: pts/1      559 -bash
PS result: ?          558 konsole [kdeinit] --ls               
PS result: TT         PID COMMAND
Console Execution error:failed to find console tty.
> start
Breakpoint 2 at 0x8048a44: file /home/mark/test/test.cpp, line 13.
main () at /home/mark/test/test.cpp:13
/home/mark/test/test.cpp:13:142:beg:0x8048a44
>>>>>>cb_gdb:
> info program
Using the running image of child process 3254.
Program stopped at 0x8048a44.
It stopped at a breakpoint that has since been deleted.
Type "info stack" or "info registers" for more information.
>>>>>>cb_gdb:
> cont
Breakpoint 1, main () at /home/mark/test/test.cpp:18
/home/mark/test/test.cpp:18:243:beg:0x8048a5b
>>>>>>cb_gdb:
> info locals
value = '\0' <repeats 80 times>
upper_count = -1208292500
>>>>>>cb_gdb:
> info args
No arguments.
>>>>>>cb_gdb:
> next
/home/mark/test/test.cpp:19:309:beg:0x8048a70
>>>>>>cb_gdb:
> info locals
value = '\0' <repeats 80 times>
upper_count = -1208292500
>>>>>>cb_gdb:
> info args
No arguments.
>>>>>>cb_gdb:
> next
Please type in a String (max. 80 characters):
Program received signal SIGINT, Interrupt.
0xb7e1846e in __read_nocancel () from /lib/tls/libc.so.6
>>>>>>cb_gdb:
> info locals
No symbol table info available.
>>>>>>cb_gdb:
> info args
No symbol table info available.
>>>>>>cb_gdb:
> quit