r16524: Fix double evaluation.
[gd/samba-autobuild/.git] / source4 / torture / ui.h
1 /* 
2    Unix SMB/CIFS implementation.
3    SMB torture UI functions
4
5    Copyright (C) Jelmer Vernooij 2006
6    
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2 of the License, or
10    (at your option) any later version.
11    
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16    
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 */
21
22 #ifndef __TORTURE_UI_H__
23 #define __TORTURE_UI_H__
24
25 struct torture_test;
26 struct torture_context;
27 struct torture_suite;
28 struct torture_tcase;
29
30 enum torture_result { 
31         TORTURE_OK=0, 
32         TORTURE_FAIL=1, 
33         TORTURE_TODO=2, 
34         TORTURE_SKIP=3
35 };
36
37 struct torture_ui_ops
38 {
39         void (*comment) (struct torture_context *, const char *);
40         void (*suite_start) (struct torture_context *, struct torture_suite *);
41         void (*suite_finish) (struct torture_context *, struct torture_suite *);
42         void (*tcase_start) (struct torture_context *, struct torture_tcase *); 
43         void (*tcase_finish) (struct torture_context *, struct torture_tcase *);
44         void (*test_start) (struct torture_context *, 
45                                                 struct torture_tcase *,
46                                                 struct torture_test *);
47         void (*test_result) (struct torture_context *, enum torture_result, 
48                                                  const char *reason);
49 };
50
51 struct torture_context
52 {
53         const struct torture_ui_ops *ui_ops;
54         void *ui_data;
55
56         struct torture_test *active_test;
57         struct torture_tcase *active_tcase;
58
59         int skipped;
60         int todo;
61         int success;
62         int failed;
63
64         enum torture_result last_result;
65         char *last_reason;
66 };
67
68 struct torture_suite
69 {
70         const char *name;
71         const char *description;
72         struct torture_tcase {
73             const char *name;
74                 const char *description;
75                 BOOL (*setup) (struct torture_context *tcase, void **data);
76                 BOOL (*teardown) (struct torture_context *tcase, void *data); 
77                 BOOL fixture_persistent;
78                 const void *data;
79                 struct torture_test {
80                         const char *name;
81                         const char *description;
82                         const void *data;
83                         BOOL dangerous;
84                         BOOL (*run) (struct torture_context *test, 
85                                                  const void *tcase_data,
86                                                  const void *test_data);
87                         struct torture_test *prev, *next;
88                 } *tests;
89                 struct torture_tcase *prev, *next;
90         } *testcases;
91 };
92
93 struct torture_suite *torture_suite_create(TALLOC_CTX *ctx, const char *name);
94 void torture_tcase_set_fixture(struct torture_tcase *tcase, 
95                 BOOL (*setup) (struct torture_context *, void **),
96                 BOOL (*teardown) (struct torture_context *, void *));
97 struct torture_test *torture_tcase_add_test(struct torture_tcase *tcase, 
98                 const char *name, 
99                 BOOL (*run) (struct torture_context *test, const void *tcase_data,
100                                          const void *test_data),
101                 const void *test_data);
102 struct torture_tcase *torture_suite_add_tcase(struct torture_suite *suite, 
103                                                          const char *name);
104 struct torture_tcase *torture_suite_add_simple_tcase(
105                 struct torture_suite *suite, 
106                 const char *name,
107                 BOOL (*run) (struct torture_context *test, const void *test_data),
108                 const void *data);
109
110 BOOL torture_run_suite(struct torture_context *context, 
111                                            struct torture_suite *suite);
112
113 BOOL torture_run_tcase(struct torture_context *context, 
114                                            struct torture_tcase *tcase);
115
116 BOOL torture_run_test(struct torture_context *context, 
117                                           struct torture_tcase *tcase,
118                                           struct torture_test *test);
119
120 #define torture_assert(ctx,expr,string) \
121         if (!(expr)) { \
122                 torture_fail(ctx, "%s:%d (%s): %s", __FILE__, __LINE__, string, \
123                                          __STRING(expr)); \
124                 return False; \
125         }
126
127 #define torture_assert_werr_equal(ctx,got,expected,string) \
128         do { WERROR __got = got, __expected = expected; \
129         if (!W_ERROR_EQUAL(__got, __expected)) { \
130                 torture_fail(ctx, "%s:%d (%s): got %s, expected %s", __FILE__, \
131                                          __LINE__, string, win_errstr(__got), win_errstr(__expected)); \
132                 return False; \
133         } \
134         } while (0)
135
136 #define torture_assert_ntstatus_equal(ctx,got,expected,string) \
137         do { NTSTATUS __got = got, __expected = expected; \
138         if (!NT_STATUS_EQUAL(__got, __expected)) { \
139                 torture_fail(ctx, "%s:%d (%s): got %s, expected %s", __FILE__, \
140                                          __LINE__, string, nt_errstr(__got), nt_errstr(__expected)); \
141                 return False; \
142         }\
143         } while(0)
144
145
146 #define torture_assert_casestr_equal(ctx,got,expected,string) \
147         do { const char *__got = got, __expected = expected; \
148         if (strcasecmp(__got, __expected) != 0) { \
149                 torture_fail(ctx, "%s:%d (%s): got %s, expected %s", __FILE__, \
150                                          __LINE__, string, got, expected); \
151                 return False; \
152         } \
153         } while(0)
154
155 #define torture_assert_str_equal(ctx,got,expected,string) \
156         do { const char *__got = got, __expected = expected; \
157         if (strcmp(__got, __expected) != 0) { \
158                 torture_fail(ctx, "%s:%d (%s): got %s, expected %s", __FILE__, \
159                                          __LINE__, string, __got, __expected); \
160                 return False; \
161         } \
162         } while(0)
163
164
165 /* Convenience macros */
166
167 #define torture_assert_ntstatus_ok(ctx,expr,string) \
168                 torture_assert_ntstatus_equal(ctx,expr,NT_STATUS_OK,string)
169
170 #define torture_assert_werr_ok(ctx,expr,string) \
171                 torture_assert_werr_equal(ctx,expr,WERR_OK,string)
172
173 void torture_comment(struct torture_context *test, const char *comment, ...) PRINTF_ATTRIBUTE(2,3);
174 void torture_fail(struct torture_context *test, const char *reason, ...) PRINTF_ATTRIBUTE(2,3);
175 void torture_skip(struct torture_context *test, const char *reason, ...) PRINTF_ATTRIBUTE(2,3);
176 const char *torture_setting(struct torture_context *test, const char *name, 
177                                                         const char *default_value);
178
179 /* Helper function commonly used */
180 BOOL torture_teardown_free(struct torture_context *torture, void *data);
181
182 #endif /* __TORTURE_UI_H__ */