Oracle® Developer Studio 12.5:使用 dbx 调试程序

退出打印视图

更新时间: 2016 年 6 月
 
 

dbx 中的异常处理

如果出现异常,程序便停止运行。异常会发送编程异常信号,例如:被零除或数组上溢。可以设置块来捕获代码中其他位置的表达式引起的异常。

    调试程序时,您可以使用 dbx 完成以下操作:

  • 在堆栈解开之前捕获未处理的异常

  • 捕获意外的异常

  • 在堆栈解开之前捕获已处理或未处理的特定异常

  • 确定程序中特定点处出现的异常的捕获位置

如果在程序停止于异常抛出点之后发出 step 命令,则将在堆栈解开期间开始执行第一个析构函数时返回控制。 如果通过 step 命令步出堆栈解开期间执行的析构函数,则将在下一个析构函数的起始处返回控制。当所有析构函数都执行完毕后,step 命令将前进到处理异常抛出的 catch 块。

异常处理命令

本节介绍了处理异常的 dbx 命令。

exception 命令

exception 命令的语法如下所示:

exception [-d | +d]

在调试期间,可以随时使用 exception 命令显示异常的类型。 如果使用 exception 命令时不带选项,则所示类型由 dbxenv 变量 output_dynamic_type: 的设置确定:

  • 如果设置为 on,则显示派生类型。

  • 如果设置为 off(缺省值),则显示静态类型。

    如果指定 -d+d 选项,则会覆盖环境变量的设置。

  • 如果指定 -d,则显示派生类型。

  • 如果指定 +d,则显示静态类型。

有关更多信息,请参见exception 命令

intercept 命令

intercept 命令的语法如下所示:

intercept [-all] [-x] [-set] [typename]

可以在堆栈解开之前拦截或捕获特定类型的异常。

  • 使用不带参数的 intercept 命令可列出正在拦截的类型。

  • 使用 -all 可拦截所有异常。使用 typename 可将类型添加到拦截列表中。

  • 使用 -x 可从排除列表中排除特定类型,从而不拦截该类型。

  • 使用 -set 可清除拦截列表和排除列表,并将列表设置为仅拦截或排除指定类型的抛出。

例如,要拦截除 int 之外的所有类型:

(dbx) intercept -all -x int

要拦截类型为 Error 的异常:

(dbx) intercept Error

如果使用以下命令拦截的 CommonError 异常过多:

(dbx) intercept -x CommonError

如果键入不带参数的 intercept 命令,则会发现拦截列表中包括未处理的异常和意外的异常(缺省情况下将拦截这些异常),以及 Error 类的异常(CommonError 类的异常除外)。

(dbx) intercept
-unhandled   -unexpected   class Error -x class CommonError

如果您随后意识到 Error 不是您需要的异常类,但是不知道要查找的异常类的名称,则可以通过键入以下内容来尝试拦截除 Error 类异常之外的所有异常:

(dbx) intercept -all -x Error

有关更多信息,请参见intercept 命令

unintercept 命令

unintercept 命令的语法如下所示:

unintercept [-all] [-x] [typename]
  • 使用 unintercept 命令可从拦截列表或排除列表中删除异常类型。

  • 使用不带参数的命令可列出正在拦截的类型(与 intercept 命令相同)。

  • 使用 -all 可从拦截列表中删除所有类型。使用 typename 可从拦截列表中删除一个类型。使用 -x 可从排除列表中删除一个类型。

有关更多信息,请参见unintercept 命令

whocatches 命令

如果在当前执行点抛出异常,whocatches 命令会报告捕获类型为 typename 的异常的位置。 使用此命令可查出从堆栈顶帧抛出异常时会发生什么情况。

捕获 typename 的 catch 子句的行号、函数名和帧号均会显示出来。如果捕获点所在函数与抛出异常的函数相同,则该命令返回 "type is unhandled"

有关更多信息,请参见whocatches 命令

异常处理示例

此示例通过一个包含异常的样例程序说明 dbx 中的异常处理。 在函数 bar 中抛出类型为 int 的异常,并在后面的 catch 块中捕获该异常。

1  #include <stdio.h>
2
3  class c {
4      int x;
5    public:
6      c(int i) { x = i; }
7      ~c() {
8                printf("destructor for c(%d)\n", x);
9           }
10  };
11
12  void bar() {
13      c c1(3);
14      throw(99);
15  }
16
17  int main() {
18      try {
19          c c2(5);
20          bar();
21          return 0;
22      }
23      catch (int i) {
24          printf("caught exception %d\n", i);
25      }
26  }

下面摘录的程序示例显示了 dbx 中的异常处理功能。

(dbx) intercept
-unhandled -unexpected
(dbx) intercept int
<dbx> intercept
-unhandled -unexpected int
(dbx) stop in bar
(2) stop in bar()
(dbx)run
Running: a.out
(process id 304)
Stopped in bar at line 13 in file “foo.cc”
   13       c c1(3);
(dbx) whocatches int
int is caught at line 24, in function main (frame number 2)
(dbx) whocatches c
dbx: no runtime type info for class c (never thrown or caught)
(dbx) cont
Exception of type int is caught at line 24, in function main (frame number 4)
stopped in _exdbg_notify_of_throw at 0xef731494
0xef731494: _exdbg_notify_of_throw          :        jmp     %o7 + 0x8
Current function is bar
   14        throw(99);
(dbx) step
stopped in c::~c at line 8 in file "foo.cc"
    8         printf("destructor for c(%d)\n", x);
(dbx) step
destructor for c(3)
stopped in c::~c at line 9 in file "foo.cc"
    9       }
(dbx) step
stopped in c::~c at line 8 in file "foo.cc"
    8        printf("destructor for c(%d)\n", x);
(dbx) step
destructor for c(5)
stopped in c::~c at line 9 in file "foo.cc"
    9       )
(dbx) step
stopped in main at line 24 in file "foo.cc"
   24           printf("caught exception %d\n", i);
(dbx) step
caught exception 99
stopped in main at line 26 in file "foo.cc"
   26   }

注 -  本节中使用的示例是使用 Oracle Developer Studio 编译器构建的。如果使用 gcc 编译代码,则示例可能有所不同。