source: src/tests/except-2.c @ fcc88a4

aaron-thesisarm-ehcleanup-dtorsdeferred_resndemanglerjacob/cs343-translationjenkins-sandboxnew-astnew-ast-unique-exprnew-envno_listpersistent-indexerresolv-newwith_gc
Last change on this file since fcc88a4 was fcc88a4, checked in by Andrew Beach <ajbeach@…>, 4 years ago

That got the last case in except-2 working.

  • Property mode set to 100644
File size: 2.9 KB
Line 
1// New draft of exception tests.
2
3
4#include <string.h>
5
6// Local Exception Types and manual vtable types.
7#define GLUE2(left, right) left##right
8#define GLUE3(left, middle, right) left##middle##right
9#define BASE_EXCEPT __cfaehm__base_exception_t
10#define TABLE(name) GLUE2(name,_vtable)
11#define INSTANCE(name) GLUE3(_,name,_vtable_instance)
12#define TRIVIAL_EXCEPTION(name) \
13struct name; \
14struct TABLE(name) { \
15        struct TABLE(BASE_EXCEPT) const * parent; \
16        size_t size; \
17        void (*copy)(name *this, name * other); \
18        void (*free)(name *this); \
19        const char * (*msg)(name *this); \
20}; \
21extern TABLE(name) INSTANCE(name); \
22struct name { \
23        struct TABLE(name) const * virtual_table; \
24}; \
25const char * name##_msg(name * this) { \
26        return #name; \
27} \
28void name##_copy(name * this, name * other) { \
29        this->virtual_table = other->virtual_table; \
30} \
31TABLE(name) INSTANCE(name) @= { \
32        .parent : &INSTANCE(BASE_EXCEPT), \
33        .size : sizeof(name), .copy : name##_copy, \
34        .free : ^?{}, .msg : name##_msg \
35}; \
36void ?{}(name * this) { \
37        this->virtual_table = &INSTANCE(name); \
38}
39TRIVIAL_EXCEPTION(yin)
40TRIVIAL_EXCEPTION(yang)
41
42struct num_error;
43struct num_error_vtable {
44        struct TABLE(BASE_EXCEPT) const * parent;
45        size_t size;
46        void (*copy)(num_error *this, num_error * other);
47        void (*free)(num_error *this);
48        const char * (*msg)(num_error *this);
49        int (*code)(num_error *this);
50};
51extern num_error_vtable INSTANCE(num_error);
52struct num_error {
53        struct num_error_vtable const * virtual_table;
54        char * msg;
55        int num;
56};
57void num_error_msg(num_error * this) {
58        if ( ! this->msg ) {
59                const char * base = "Num Error with code: X";
60                this->msg = strdup( base );
61        }
62        this->msg[21] = '0' + this->num;
63        return this->msg;
64}
65void ?{}(num_error * this, int num) {
66        this->virtual_table = &INSTANCE(num_error);
67        this->msg = 0;
68        this->num = num;
69}
70void ?{}(num_error * this, num_error * other) {
71        this->virtual_table = other->virtual_table;
72        this->msg = 0;
73        this->num = other->num;
74}
75void ^?{}(num_error * this) {
76        if( this->msg ) free( this->msg );
77}
78int num_error_code( num_error * this ) {
79        return this->num;
80}
81num_error_vtable _num_error_vtable_instance @= {
82        &INSTANCE(BASE_EXCEPT),
83        sizeof(num_error), ?{}, ^?{},
84        num_error_msg, num_error_code
85};
86
87
88// Test simple throwing, matching and catching.
89void throw_catch() {
90        try {
91                yin black;
92                throw (BASE_EXCEPT *)&black;
93        } catch ( yin * error ) {
94                printf("throw yin caught.\n");
95        }
96
97        try {
98                yang white;
99                throwResume (BASE_EXCEPT *)&white;
100                printf("> throwResume returned.\n");
101        } catchResume ( yang * error ) {
102                printf("throwResume yang caught <");
103        }
104
105        try {
106                num_error x = { 2 };
107                throw (BASE_EXCEPT *)&x;
108        }
109        catch (num_error * error ; 3 == error->virtual_table->code( error ) ) {
110                printf("exception at %p\n", error );
111                printf("Should not be printed.\n");
112        }
113        catch (num_error * error ; 2 == error->virtual_table->code( error ) ) {
114                printf("Should be printed.\n");
115        }
116}
117
118int main (int argc, char * argv[]) {
119        throw_catch();
120        return 0;
121}
Note: See TracBrowser for help on using the repository browser.