| 1 | /* |
| 2 | * Copyright 2013 Ecole Normale Superieure |
| 3 | * |
| 4 | * Use of this software is governed by the MIT license |
| 5 | * |
| 6 | * Written by Sven Verdoolaege, |
| 7 | * Ecole Normale Superieure, 45 rue d'Ulm, 75230 Paris, France |
| 8 | */ |
| 9 | |
| 10 | #include <isl/space.h> |
| 11 | #include <isl/set.h> |
| 12 | |
| 13 | #include <isl_multi_macro.h> |
| 14 | |
| 15 | /* This function is called for each element in a tuple inside |
| 16 | * isl_stream_read_multi_*. |
| 17 | * Read an EL from "s" and add it to *list. |
| 18 | */ |
| 19 | static __isl_give isl_space *FN(read_el,BASE)(__isl_keep isl_stream *s, |
| 20 | struct vars *v, __isl_take isl_space *space, int rational, void *user) |
| 21 | { |
| 22 | LIST(EL) **list = (LIST(EL) **) user; |
| 23 | EL *el; |
| 24 | |
| 25 | el = FN(isl_stream_read,BASE)(s); |
| 26 | *list = FN(LIST(EL),add)(list: *list, el); |
| 27 | if (!*list) |
| 28 | return isl_space_free(space); |
| 29 | |
| 30 | return space; |
| 31 | } |
| 32 | |
| 33 | /* Read a multi expression from "s". |
| 34 | * |
| 35 | * We first read a tuple space, collecting the element values in a list. |
| 36 | * Then we create an isl_multi_* from the space and the isl_*_list. |
| 37 | */ |
| 38 | __isl_give MULTI(BASE) *FN(isl_stream_read_multi,BASE)( |
| 39 | __isl_keep isl_stream *s) |
| 40 | { |
| 41 | struct vars *v; |
| 42 | isl_set *dom = NULL; |
| 43 | isl_space *space; |
| 44 | MULTI(BASE) *multi = NULL; |
| 45 | LIST(EL) *list; |
| 46 | |
| 47 | v = vars_new(ctx: s->ctx); |
| 48 | if (!v) |
| 49 | return NULL; |
| 50 | |
| 51 | dom = isl_set_universe(space: isl_space_params_alloc(ctx: s->ctx, nparam: 0)); |
| 52 | if (next_is_tuple(s)) { |
| 53 | dom = read_map_tuple(s, map: dom, type: isl_dim_param, v, rational: 1, comma: 0); |
| 54 | if (isl_stream_eat(s, type: ISL_TOKEN_TO)) |
| 55 | goto error; |
| 56 | } |
| 57 | if (!isl_set_plain_is_universe(set: dom)) |
| 58 | isl_die(s->ctx, isl_error_invalid, |
| 59 | "expecting universe parameter domain" , goto error); |
| 60 | if (isl_stream_eat(s, type: '{')) |
| 61 | goto error; |
| 62 | |
| 63 | space = isl_set_get_space(set: dom); |
| 64 | |
| 65 | list = FN(LIST(EL),alloc)(ctx: s->ctx, n: 0); |
| 66 | space = read_tuple_space(s, v, space, rational: 1, comma: 0, read_el: &FN(read_el,BASE), user: &list); |
| 67 | multi = FN(FN(MULTI(BASE),from),LIST(BASE))(space, list); |
| 68 | |
| 69 | if (isl_stream_eat(s, type: '}')) |
| 70 | goto error; |
| 71 | |
| 72 | vars_free(v); |
| 73 | isl_set_free(set: dom); |
| 74 | return multi; |
| 75 | error: |
| 76 | vars_free(v); |
| 77 | isl_set_free(set: dom); |
| 78 | FN(MULTI(BASE),free)(multi); |
| 79 | return NULL; |
| 80 | } |
| 81 | |
| 82 | #undef TYPE_BASE |
| 83 | #define TYPE_BASE CAT(multi_,BASE) |
| 84 | #include "isl_read_from_str_templ.c" |
| 85 | |