isl_map_coalesce: avoid ignoring constraints redundant wrt implicit equalities
[isl.git] / isl_ctx.c
blob017e4af888aa93186054d4c0d96bd1d39d2d4a97
1 /*
2 * Copyright 2008-2009 Katholieke Universiteit Leuven
4 * Use of this software is governed by the MIT license
6 * Written by Sven Verdoolaege, K.U.Leuven, Departement
7 * Computerwetenschappen, Celestijnenlaan 200A, B-3001 Leuven, Belgium
8 */
10 #include <isl_ctx_private.h>
11 #include <isl/vec.h>
12 #include <isl_options_private.h>
14 #define __isl_calloc(type,size) ((type *)calloc(1, size))
15 #define __isl_calloc_type(type) __isl_calloc(type,sizeof(type))
17 /* Construct an isl_stat indicating whether "obj" is non-NULL.
19 * That is, return isl_stat_ok if "obj" is non_NULL and
20 * isl_stat_error otherwise.
22 isl_stat isl_stat_non_null(void *obj)
24 if (obj != NULL)
25 return isl_stat_ok;
26 return isl_stat_error;
29 /* Return the negation of "b", where the negation of isl_bool_error
30 * is isl_bool_error again.
32 isl_bool isl_bool_not(isl_bool b)
34 if (b < 0)
35 return isl_bool_error;
36 if (b == isl_bool_false)
37 return isl_bool_true;
38 return isl_bool_false;
41 /* Create an isl_bool from an integer.
43 * Return isl_bool_false if b is zero, otherwise return isl_bool_true.
44 * This function never returns isl_bool_error.
46 isl_bool isl_bool_ok(int b)
48 if (b)
49 return isl_bool_true;
50 return isl_bool_false;
53 /* Check that the result of an allocation ("p") is not NULL and
54 * complain if it is.
55 * The only exception is when allocation size ("size") is equal to zero.
57 static void *check_non_null(isl_ctx *ctx, void *p, size_t size)
59 if (p || size == 0)
60 return p;
61 isl_die(ctx, isl_error_alloc, "allocation failure", return NULL);
64 /* Prepare for performing the next "operation" in the context.
65 * Return 0 if we are allowed to perform this operation and
66 * return -1 if we should abort the computation.
68 * In particular, we should stop if the user has explicitly aborted
69 * the computation or if the maximal number of operations has been exceeded.
71 int isl_ctx_next_operation(isl_ctx *ctx)
73 if (!ctx)
74 return -1;
75 if (ctx->abort) {
76 isl_ctx_set_error(ctx, isl_error_abort);
77 return -1;
79 if (ctx->max_operations && ctx->operations >= ctx->max_operations)
80 isl_die(ctx, isl_error_quota,
81 "maximal number of operations exceeded", return -1);
82 ctx->operations++;
83 return 0;
86 /* Call malloc and complain if it fails.
87 * If ctx is NULL, then return NULL.
89 void *isl_malloc_or_die(isl_ctx *ctx, size_t size)
91 if (isl_ctx_next_operation(ctx) < 0)
92 return NULL;
93 return ctx ? check_non_null(ctx, malloc(size), size) : NULL;
96 /* Call calloc and complain if it fails.
97 * If ctx is NULL, then return NULL.
99 void *isl_calloc_or_die(isl_ctx *ctx, size_t nmemb, size_t size)
101 if (isl_ctx_next_operation(ctx) < 0)
102 return NULL;
103 return ctx ? check_non_null(ctx, calloc(nmemb, size), nmemb) : NULL;
106 /* Call realloc and complain if it fails.
107 * If ctx is NULL, then return NULL.
109 void *isl_realloc_or_die(isl_ctx *ctx, void *ptr, size_t size)
111 if (isl_ctx_next_operation(ctx) < 0)
112 return NULL;
113 return ctx ? check_non_null(ctx, realloc(ptr, size), size) : NULL;
116 /* Keep track of all information about the current error ("error", "msg",
117 * "file", "line") in "ctx".
119 void isl_ctx_set_full_error(isl_ctx *ctx, enum isl_error error, const char *msg,
120 const char *file, int line)
122 if (!ctx)
123 return;
124 ctx->error = error;
125 ctx->error_msg = msg;
126 ctx->error_file = file;
127 ctx->error_line = line;
130 void isl_handle_error(isl_ctx *ctx, enum isl_error error, const char *msg,
131 const char *file, int line)
133 if (!ctx)
134 return;
136 isl_ctx_set_full_error(ctx, error, msg, file, line);
138 switch (ctx->opt->on_error) {
139 case ISL_ON_ERROR_WARN:
140 fprintf(stderr, "%s:%d: %s\n", file, line, msg);
141 return;
142 case ISL_ON_ERROR_CONTINUE:
143 return;
144 case ISL_ON_ERROR_ABORT:
145 fprintf(stderr, "%s:%d: %s\n", file, line, msg);
146 abort();
147 return;
151 static struct isl_options *find_nested_options(struct isl_args *args,
152 void *opt, struct isl_args *wanted)
154 int i;
155 struct isl_options *options;
157 if (args == wanted)
158 return opt;
160 for (i = 0; args->args[i].type != isl_arg_end; ++i) {
161 struct isl_arg *arg = &args->args[i];
162 void *child;
164 if (arg->type != isl_arg_child)
165 continue;
167 if (arg->offset == ISL_ARG_OFFSET_NONE)
168 child = opt;
169 else
170 child = *(void **)(((char *)opt) + arg->offset);
172 options = find_nested_options(arg->u.child.child,
173 child, wanted);
174 if (options)
175 return options;
178 return NULL;
181 static struct isl_options *find_nested_isl_options(struct isl_args *args,
182 void *opt)
184 return find_nested_options(args, opt, &isl_options_args);
187 void *isl_ctx_peek_options(isl_ctx *ctx, struct isl_args *args)
189 if (!ctx)
190 return NULL;
191 if (args == &isl_options_args)
192 return ctx->opt;
193 return find_nested_options(ctx->user_args, ctx->user_opt, args);
196 isl_ctx *isl_ctx_alloc_with_options(struct isl_args *args, void *user_opt)
198 struct isl_ctx *ctx = NULL;
199 struct isl_options *opt = NULL;
200 int opt_allocated = 0;
202 if (!user_opt)
203 return NULL;
205 opt = find_nested_isl_options(args, user_opt);
206 if (!opt) {
207 opt = isl_options_new_with_defaults();
208 if (!opt)
209 goto error;
210 opt_allocated = 1;
213 ctx = __isl_calloc_type(struct isl_ctx);
214 if (!ctx)
215 goto error;
217 if (isl_hash_table_init(ctx, &ctx->id_table, 0))
218 goto error;
220 ctx->stats = isl_calloc_type(ctx, struct isl_stats);
221 if (!ctx->stats)
222 goto error;
224 ctx->user_args = args;
225 ctx->user_opt = user_opt;
226 ctx->opt_allocated = opt_allocated;
227 ctx->opt = opt;
228 ctx->ref = 0;
230 isl_int_init(ctx->zero);
231 isl_int_set_si(ctx->zero, 0);
233 isl_int_init(ctx->one);
234 isl_int_set_si(ctx->one, 1);
236 isl_int_init(ctx->two);
237 isl_int_set_si(ctx->two, 2);
239 isl_int_init(ctx->negone);
240 isl_int_set_si(ctx->negone, -1);
242 isl_int_init(ctx->normalize_gcd);
244 ctx->n_cached = 0;
245 ctx->n_miss = 0;
247 isl_ctx_reset_error(ctx);
249 ctx->operations = 0;
250 isl_ctx_set_max_operations(ctx, ctx->opt->max_operations);
252 return ctx;
253 error:
254 isl_args_free(args, user_opt);
255 if (opt_allocated)
256 isl_options_free(opt);
257 free(ctx);
258 return NULL;
261 struct isl_ctx *isl_ctx_alloc()
263 struct isl_options *opt;
265 opt = isl_options_new_with_defaults();
267 return isl_ctx_alloc_with_options(&isl_options_args, opt);
270 void isl_ctx_ref(struct isl_ctx *ctx)
272 ctx->ref++;
275 void isl_ctx_deref(struct isl_ctx *ctx)
277 isl_assert(ctx, ctx->ref > 0, return);
278 ctx->ref--;
281 /* Print statistics on usage.
283 static void print_stats(isl_ctx *ctx)
285 fprintf(stderr, "operations: %lu\n", ctx->operations);
288 void isl_ctx_free(struct isl_ctx *ctx)
290 if (!ctx)
291 return;
292 if (ctx->ref != 0)
293 isl_die(ctx, isl_error_invalid,
294 "isl_ctx not freed as some objects still reference it",
295 return);
297 if (ctx->opt->print_stats)
298 print_stats(ctx);
300 isl_hash_table_clear(&ctx->id_table);
301 isl_blk_clear_cache(ctx);
302 isl_int_clear(ctx->zero);
303 isl_int_clear(ctx->one);
304 isl_int_clear(ctx->two);
305 isl_int_clear(ctx->negone);
306 isl_int_clear(ctx->normalize_gcd);
307 isl_args_free(ctx->user_args, ctx->user_opt);
308 if (ctx->opt_allocated)
309 isl_options_free(ctx->opt);
310 free(ctx->stats);
311 free(ctx);
314 struct isl_options *isl_ctx_options(isl_ctx *ctx)
316 if (!ctx)
317 return NULL;
318 return ctx->opt;
321 enum isl_error isl_ctx_last_error(isl_ctx *ctx)
323 return ctx ? ctx->error : isl_error_invalid;
326 /* Return the error message of the last error in "ctx".
328 const char *isl_ctx_last_error_msg(isl_ctx *ctx)
330 return ctx ? ctx->error_msg : NULL;
333 /* Return the file name where the last error in "ctx" occurred.
335 const char *isl_ctx_last_error_file(isl_ctx *ctx)
337 return ctx ? ctx->error_file : NULL;
340 /* Return the line number where the last error in "ctx" occurred.
342 int isl_ctx_last_error_line(isl_ctx *ctx)
344 return ctx ? ctx->error_line : -1;
347 void isl_ctx_reset_error(isl_ctx *ctx)
349 if (!ctx)
350 return;
351 ctx->error = isl_error_none;
352 ctx->error_msg = NULL;
353 ctx->error_file = NULL;
354 ctx->error_line = -1;
357 void isl_ctx_set_error(isl_ctx *ctx, enum isl_error error)
359 isl_ctx_set_full_error(ctx, error, NULL, NULL, -1);
362 void isl_ctx_abort(isl_ctx *ctx)
364 if (ctx)
365 ctx->abort = 1;
368 void isl_ctx_resume(isl_ctx *ctx)
370 if (ctx)
371 ctx->abort = 0;
374 int isl_ctx_aborted(isl_ctx *ctx)
376 return ctx ? ctx->abort : -1;
379 int isl_ctx_parse_options(isl_ctx *ctx, int argc, char **argv, unsigned flags)
381 if (!ctx)
382 return -1;
383 return isl_args_parse(ctx->user_args, argc, argv, ctx->user_opt, flags);
386 /* Set the maximal number of iterations of "ctx" to "max_operations".
388 void isl_ctx_set_max_operations(isl_ctx *ctx, unsigned long max_operations)
390 if (!ctx)
391 return;
392 ctx->max_operations = max_operations;
395 /* Return the maximal number of iterations of "ctx".
397 unsigned long isl_ctx_get_max_operations(isl_ctx *ctx)
399 return ctx ? ctx->max_operations : 0;
402 /* Reset the number of operations performed by "ctx".
404 void isl_ctx_reset_operations(isl_ctx *ctx)
406 if (!ctx)
407 return;
408 ctx->operations = 0;