aboutsummaryrefslogtreecommitdiff
path: root/tests/exceptions
diff options
context:
space:
mode:
authorAdrian Taylor <adrian@macrobug.com>2012-02-10 23:11:34 +0000
committerAdrian Taylor <adrian@macrobug.com>2012-02-20 08:50:04 +0000
commite6f092d69f1806153571e6e808caea76f8bf5190 (patch)
tree0ed8e824e097d43cd3b6a03e39bb79c627a2deef /tests/exceptions
parent1d5093e31274f666b052e0ac392a396f3e3b1875 (diff)
Polymorphic exception handling.
Previously exception handling only worked if there were a 'catch' block which precisely matched the type of the thrown exception. That's not always the case if we're trying to catch subclasses. This change enhances behaviour to match subclasses, and also covers some other cases where we weren't catching the right thing.
Diffstat (limited to 'tests/exceptions')
-rw-r--r--tests/exceptions/output.txt27
-rw-r--r--tests/exceptions/typed.cpp45
2 files changed, 50 insertions, 22 deletions
diff --git a/tests/exceptions/output.txt b/tests/exceptions/output.txt
index 2db8345e..718f189a 100644
--- a/tests/exceptions/output.txt
+++ b/tests/exceptions/output.txt
@@ -1,9 +1,12 @@
*CREATING A FOO
*CREATING A BAR
*CREATING A QUUX
+*CREATING A QUUX
+*CREATING A CHILD
start
+test 0
throwing ExFooInstance
*COPYING A FOO
*COPYING A FOO
@@ -12,6 +15,7 @@ outer catch foo: 11
*DESTROYING A FOO (11)
+test 1
throwing ExBarInstance
*COPYING A BAR
*COPYING A BAR
@@ -21,6 +25,7 @@ outer catch bar-ref: 22
*DESTROYING A BAR (22)
+test 2
throwing ExQuuxInstance
*COPYING A QUUX
*COPYING A QUUX
@@ -29,22 +34,44 @@ inner catch quux: 33
*DESTROYING A QUUX (33)
+test 3
+ throwing ExQuux ptr
+outer catch quux-ptr: 33
+
+
+test 4
+ throwing ExChildInstance
+*CREATING A QUUX
+*COPYING CHILD
+*COPYING A QUUX
+inner catch quux: 44
+*DESTROYING A QUUX (44)
+*DESTROYING A CHILD (44)
+*DESTROYING A QUUX (44)
+test 5
+ throwing ExChildInstance ptr
+outer catch quux-ptr: 44
+test 6
throwing 42
outer catch int: 42
+test 7
throwing NULL
outer catch-all
+test 8
not throwing
end
+*DESTROYING A CHILD (44)
+*DESTROYING A QUUX (44)
*DESTROYING A QUUX (33)
*DESTROYING A BAR (22)
*DESTROYING A FOO (11)
diff --git a/tests/exceptions/typed.cpp b/tests/exceptions/typed.cpp
index 29bf548a..a2b77fee 100644
--- a/tests/exceptions/typed.cpp
+++ b/tests/exceptions/typed.cpp
@@ -21,13 +21,12 @@ public:
ExQuux(const ExQuux& other) { x=other.x; printf("*COPYING A QUUX\n"); }
~ExQuux() { printf("*DESTROYING A QUUX (%d)\n", x); }
} ExQuuxInstance(33);
-// NOTE: Throwing pointers and polymorphic matching not supported.
-// class ExChild : public ExQuux {
-// public:
-// ExChild(int x) : ExQuux(x) { printf("*CREATING A CHILD\n"); }
-// ExChild(const ExChild& other) : ExQuux(x) { x=other.x; printf("*COPYING CHILD\n"); }
-// ~ExChild() { printf("*DESTROYING A CHILD (%d)\n", x); }
-// } ExChildInstance(44);
+class ExChild : public ExQuux {
+public:
+ ExChild(int x) : ExQuux(x) { printf("*CREATING A CHILD\n"); }
+ ExChild(const ExChild& other) : ExQuux(x) { x=other.x; printf("*COPYING CHILD\n"); }
+ ~ExChild() { printf("*DESTROYING A CHILD (%d)\n", x); }
+} ExChildInstance(44);
void magic(int which) {
try {
@@ -41,20 +40,22 @@ void magic(int which) {
case 2:
printf(" throwing ExQuuxInstance\n");
throw ExQuuxInstance;
-// NOTE: Throwing pointers and polymorphic matching not supported.
-// case 3:
-// printf(" throwing ExQuux ptr\n");
-// throw &ExQuuxInstance;
-// case 4:
-// printf(" throwing ExChildInstance\n");
-// throw ExChildInstance;
+ case 3:
+ printf(" throwing ExQuux ptr\n");
+ throw &ExQuuxInstance;
+ case 4:
+ printf(" throwing ExChildInstance\n");
+ throw ExChildInstance;
case 5:
+ printf(" throwing ExChildInstance ptr\n");
+ throw &ExChildInstance;
+ case 6:
printf(" throwing 42\n");
throw 42;
- case 6:
+ case 7:
printf(" throwing NULL\n");
throw (void*)0;
- case 7:
+ case 8:
printf(" not throwing\n");
}
} catch (ExQuux e1) {
@@ -67,18 +68,18 @@ void magic(int which) {
int main() {
printf("start\n\n\n");
- for (int i = 0; i < 8; i++) {
+ for (int i = 0; i < 9; i++) {
+ printf("test %d\n", i);
try {
magic(i);
} catch (ExFoo e1) {
printf("outer catch foo: %d\n", e1.x);
} catch (ExBar& e2) {
printf("outer catch bar-ref: %d\n", e2.x);
-// NOTE: Throwing pointers and polymorphic matching not supported.
-// } catch (ExQuux& e3) {
-// printf("outer catch quux-ref: %d\n", e3.x);
-// } catch (ExQuux* e4) {
-// printf("outer catch quux-ptr: %d\n", e4->x);
+ } catch (ExQuux& e3) {
+ printf("outer catch quux-ref: %d\n", e3.x);
+ } catch (ExQuux* e4) {
+ printf("outer catch quux-ptr: %d\n", e4->x);
} catch (int e5) {
printf("outer catch int: %d\n", e5);
} catch (...) {