move libmigdb into a libmigdb/
[gdbmicli.git] / libmigdb / examples / x11_cpp_test.cc
1 /**[txh]********************************************************************
2
3   Copyright (c) 2004 by Salvador E. Tropea.
4   Covered by the GPL license.
5
6   Comment:
7   X11 example/test of the libmigdb.
8   Run it from an X11 terminal (xterm, Eterm, etc.).
9   
10 ***************************************************************************/
11
12 #include <stdio.h>
13 #include <unistd.h> //usleep
14 #include "mi_gdb.h"
15
16 void cb_console(const char *str, void *data)
17 {
18  printf("CONSOLE> %s\n",str);
19 }
20
21 /* Note that unlike what's documented in gdb docs it isn't usable. */
22 void cb_target(const char *str, void *data)
23 {
24  printf("TARGET> %s\n",str);
25 }
26
27 void cb_log(const char *str, void *data)
28 {
29  printf("LOG> %s\n",str);
30 }
31
32 void cb_to(const char *str, void *data)
33 {
34  printf(">> %s",str);
35 }
36
37 void cb_from(const char *str, void *data)
38 {
39  printf("<< %s\n",str);
40 }
41
42 volatile int async_c=0;
43
44 void cb_async(mi_output *o, void *data)
45 {
46  printf("ASYNC\n");
47  async_c++;
48 }
49
50 int wait_for_stop(MIDebugger &d)
51 {
52  int res=1;
53  mi_stop *sr;
54
55  while (!d.Poll(sr))
56     usleep(1000);
57  /* The end of the async. */
58  if (sr)
59    {
60     printf("Stopped, reason: %s\n",mi_reason_enum_to_str(sr->reason));
61     mi_free_stop(sr);
62    }
63  else
64    {
65     printf("Error while waiting\n");
66     printf("mi_error: %d\nmi_error_from_gdb: %s\n",mi_error,mi_error_from_gdb);
67     res=0;
68    }
69  return res;
70 }
71
72 int DoTryRun(int res, MIDebugger &d)
73 {
74  if (!res)
75    {
76     printf("Error in executing!\n");
77     return 0;
78    }
79  if (!wait_for_stop(d))
80     return 0;
81  return 1;
82 }
83
84 #define TryRun(a,b) if (!DoTryRun(a,b)) return 1
85
86 int main(int argc, char *argv[])
87 {
88  mi_bkpt *bk;
89  mi_wp *wp;
90
91  // Debugging object, used as an auto var.
92  MIDebugger d;
93
94  // You can use any gdb you want:
95  //MIDebugger::SetGDBExe("/usr/src/gdb-6.1.1/gdb/gdb");
96  // You can use a terminal different than xterm:
97  //MIDebugger::SetXTerm("/usr/bin/Eterm");
98  // You can specify commands for gdb
99  MIDebugger::SetGDBStartFile("cmds.txt");
100
101  // Connect to gdb child.
102  if (!d.Connect())
103    {
104     printf("Connect failed\n");
105     return 1;
106    }
107  printf("Connected to gdb!\n");
108
109  /* Set all callbacks. */
110  d.SetConsoleCB(cb_console);
111  d.SetTargetCB(cb_target);
112  d.SetLogCB(cb_log);
113  d.SetAsyncCB(cb_async);
114  d.SetToGDBCB(cb_to);
115  d.SetFromGDBCB(cb_from);
116
117  // Set the name of the child and the command line aguments.
118  // It also opens the xterm.
119  if (!d.SelectTargetX11("./test_target","prb1 2 prb3"))
120    {
121     printf("Error setting exec y args\n");
122     return 1;
123    }
124
125  /* Set a breakpoint. */
126  bk=d.Breakpoint("test_target.cc",15);
127  if (!bk)
128    {
129     printf("Error setting breakpoint\n");
130     return 1;
131    }
132  printf("Breakpoint %d @ function: %s\n",bk->number,bk->func);
133
134  /* You can do things like:
135  gmi_break_delete(h,bk->number);
136  gmi_break_set_times(h,bk->number,2);
137  gmi_break_set_condition(h,bk->number,"1");
138  gmi_break_state(h,bk->number,0);*/
139  /* If we no longer need this data we can release it. */
140  mi_free_bkpt(bk);
141
142  /* Set a watchpoint, that's a data breakpoint. */
143  wp=d.Watchpoint(wm_write,"v");
144  if (!wp)
145    {
146     printf("Error al setting watchpoint\n");
147     return 1;
148    }
149  printf("Watchpoint %d for expression: %s\n",wp->number,wp->exp);
150  mi_free_wp(wp);
151
152  TryRun(d.StepOver(),d);
153  /* Run the program. */
154  TryRun(d.RunOrContinue(),d);
155  /* Here we should be stopped at the breakpoint. */
156
157  /* Continue execution. */
158  TryRun(d.RunOrContinue(),d);
159  /* Here we should be terminated. */
160
161  /* Wait 5 seconds and close the auxiliar terminal. */
162  printf("Waiting 5 seconds\n");
163  sleep(5);
164
165  return 0;
166 }