the iterations where those accesses occur.
=item * The functions C<isl_basic_map_identity> and
-C<isl_map_identity> now take the dimension specification
-of a B<map> as input. An old call
-C<isl_map_identity(dim)> can be rewritten to
-C<isl_map_identity(isl_dim_map_from_set(dim))>.
+C<isl_map_identity> now take a B<map> space as input. An old call
+C<isl_map_identity(space)> can be rewritten to
+C<isl_map_identity(isl_space_map_from_set(space))>.
=item * The function C<isl_map_power> no longer takes
a parameter position as input. Instead, the exponent
C<ISL_FORMAT_ISL> output has changed.
Use C<ISL_FORMAT_C> to obtain the old output.
+=item * The C<*_fast_*> functions have been renamed to C<*_plain_*>.
+Some of the old names have been kept for backward compatibility,
+but they will be removed in the future.
+
+=back
+
+=head3 Changes since isl-0.07
+
+=over
+
+=item * The function C<isl_pw_aff_max> has been renamed to
+C<isl_pw_aff_union_max>.
+Similarly, the function C<isl_pw_aff_add> has been renamed to
+C<isl_pw_aff_union_add>.
+
+=item * The C<isl_dim> type has been renamed to C<isl_space>
+along with the associated functions.
+Some of the old names have been kept for backward compatibility,
+but they will be removed in the future.
+
+=item * Spaces of maps, sets and parameter domains are now
+treated differently. The distinction between map spaces and set spaces
+has always been made on a conceptual level, but proper use of such spaces
+was never checked. Furthermore, up until isl-0.07 there was no way
+of explicitly creating a parameter space. These can now be created
+directly using C<isl_space_params_alloc> or from other spaces using
+C<isl_space_params>.
+
+=item * The space in which C<isl_aff>, C<isl_pw_aff>, C<isl_qpolynomial>,
+C<isl_pw_qpolynomial>, C<isl_qpolynomial_fold> and C<isl_pw_qpolynomial_fold>
+objects live is now a map space
+instead of a set space. This means, for example, that the dimensions
+of the domain of an C<isl_aff> are now considered to be of type
+C<isl_dim_in> instead of C<isl_dim_set>. Extra functions have been
+added to obtain the domain space. Some of the constructors still
+take a domain space and have therefore been renamed.
+
+=item * The functions C<isl_equality_alloc> and C<isl_inequality_alloc>
+now take an C<isl_local_space> instead of an C<isl_space>.
+An C<isl_local_space> can be created from an C<isl_space>
+using C<isl_local_space_from_space>.
+
+=item * The C<isl_div> type has been removed. Functions that used
+to return an C<isl_div> now return an C<isl_aff>.
+Note that the space of an C<isl_aff> is that of relation.
+When replacing a call to C<isl_div_get_coefficient> by a call to
+C<isl_aff_get_coefficient> any C<isl_dim_set> argument needs
+to be replaced by C<isl_dim_in>.
+A call to C<isl_aff_from_div> can be replaced by a call
+to C<isl_aff_floor>.
+A call to C<isl_qpolynomial_div(div)> call be replaced by
+the nested call
+
+ isl_qpolynomial_from_aff(isl_aff_floor(div))
+
+The function C<isl_constraint_div> has also been renamed
+to C<isl_constraint_get_div>.
+
+=item * The C<nparam> argument has been removed from
+C<isl_map_read_from_str> and similar functions.
+When reading input in the original PolyLib format,
+the result will have no parameters.
+If parameters are expected, the caller may want to perform
+dimension manipulation on the result.
+
+=back
+
+=head3 Changes since isl-0.09
+
+=over
+
+=item * The C<schedule_split_parallel> option has been replaced
+by the C<schedule_split_scaled> option.
+
+=item * The first argument of C<isl_pw_aff_cond> is now
+an C<isl_pw_aff> instead of an C<isl_set>.
+A call C<isl_pw_aff_cond(a, b, c)> can be replaced by
+
+ isl_pw_aff_cond(isl_set_indicator_function(a), b, c)
+
=back
=head1 Installation
C<isl_set> and C<isl_map> represent unions of
C<isl_basic_set>s and C<isl_basic_map>s, respectively.
However, all C<isl_basic_set>s or C<isl_basic_map>s in the union need
-to have the same dimension. C<isl_union_set>s and C<isl_union_map>s
-represent unions of C<isl_set>s or C<isl_map>s of I<different> dimensions,
-where dimensions with different space names
-(see L<Dimension Specifications>) are considered different as well.
+to live in the same space. C<isl_union_set>s and C<isl_union_map>s
+represent unions of C<isl_set>s or C<isl_map>s in I<different> spaces,
+where spaces are considered different if they have a different number
+of dimensions and/or different names (see L<"Spaces">).
The difference between sets and relations (maps) is that sets have
one set of variables, while relations have two sets of variables,
input variables and output variables.
The user is then responsible for making sure that the original
object gets used somewhere else or is explicitly freed.
-The arguments and return values of all documents functions are
+The arguments and return values of all documented functions are
annotated to make clear which arguments are released and which
arguments are preserved. In particular, the following annotations
are used
If the user passes in a C<NULL> value, then this will
be treated as an error in the sense that the function will
not perform its usual operation. However, it will still
-make sure that all the the other C<__isl_take> arguments
+make sure that all the other C<__isl_take> arguments
are released.
=item C<__isl_keep>
=back
-=head2 Dimension Specifications
+=head2 Error Handling
+
+C<isl> supports different ways to react in case a runtime error is triggered.
+Runtime errors arise, e.g., if a function such as C<isl_map_intersect> is called
+with two maps that have incompatible spaces. There are three possible ways
+to react on error: to warn, to continue or to abort.
+
+The default behavior is to warn. In this mode, C<isl> prints a warning, stores
+the last error in the corresponding C<isl_ctx> and the function in which the
+error was triggered returns C<NULL>. An error does not corrupt internal state,
+such that isl can continue to be used. C<isl> also provides functions to
+read the last error and to reset the memory that stores the last error. The
+last error is only stored for information purposes. Its presence does not
+change the behavior of C<isl>. Hence, resetting an error is not required to
+continue to use isl, but only to observe new errors.
+
+ #include <isl/ctx.h>
+ enum isl_error isl_ctx_last_error(isl_ctx *ctx);
+ void isl_ctx_reset_error(isl_ctx *ctx);
+
+Another option is to continue on error. This is similar to warn on error mode,
+except that C<isl> does not print any warning. This allows a program to
+implement its own error reporting.
+
+The last option is to directly abort the execution of the program from within
+the isl library. This makes it obviously impossible to recover from an error,
+but it allows to directly spot the error location. By aborting on error,
+debuggers break at the location the error occurred and can provide a stack
+trace. Other tools that automatically provide stack traces on abort or that do
+not want to continue execution after an error was triggered may also prefer to
+abort on error.
+
+The on error behavior of isl can be specified by calling
+C<isl_options_set_on_error> or by setting the command line option
+C<--isl-on-error>. Valid arguments for the function call are
+C<ISL_ON_ERROR_WARN>, C<ISL_ON_ERROR_CONTINUE> and C<ISL_ON_ERROR_ABORT>. The
+choices for the command line option are C<warn>, C<continue> and C<abort>.
+It is also possible to query the current error mode.
+
+ #include <isl/options.h>
+ int isl_options_set_on_error(isl_ctx *ctx, int val);
+ int isl_options_get_on_error(isl_ctx *ctx);
+
+=head2 Identifiers
+
+Identifiers are used to identify both individual dimensions
+and tuples of dimensions. They consist of a name and an optional
+pointer. Identifiers with the same name but different pointer values
+are considered to be distinct.
+Identifiers can be constructed, copied, freed, inspected and printed
+using the following functions.
+
+ #include <isl/id.h>
+ __isl_give isl_id *isl_id_alloc(isl_ctx *ctx,
+ __isl_keep const char *name, void *user);
+ __isl_give isl_id *isl_id_copy(isl_id *id);
+ void *isl_id_free(__isl_take isl_id *id);
+
+ isl_ctx *isl_id_get_ctx(__isl_keep isl_id *id);
+ void *isl_id_get_user(__isl_keep isl_id *id);
+ __isl_keep const char *isl_id_get_name(__isl_keep isl_id *id);
+
+ __isl_give isl_printer *isl_printer_print_id(
+ __isl_take isl_printer *p, __isl_keep isl_id *id);
+
+Note that C<isl_id_get_name> returns a pointer to some internal
+data structure, so the result can only be used while the
+corresponding C<isl_id> is alive.
+
+=head2 Spaces
Whenever a new set or relation is created from scratch,
-its dimension needs to be specified using an C<isl_dim>.
+the space in which it lives needs to be specified using an C<isl_space>.
- #include <isl/dim.h>
- __isl_give isl_dim *isl_dim_alloc(isl_ctx *ctx,
+ #include <isl/space.h>
+ __isl_give isl_space *isl_space_alloc(isl_ctx *ctx,
unsigned nparam, unsigned n_in, unsigned n_out);
- __isl_give isl_dim *isl_dim_set_alloc(isl_ctx *ctx,
+ __isl_give isl_space *isl_space_params_alloc(isl_ctx *ctx,
+ unsigned nparam);
+ __isl_give isl_space *isl_space_set_alloc(isl_ctx *ctx,
unsigned nparam, unsigned dim);
- __isl_give isl_dim *isl_dim_copy(__isl_keep isl_dim *dim);
- void isl_dim_free(__isl_take isl_dim *dim);
- unsigned isl_dim_size(__isl_keep isl_dim *dim,
+ __isl_give isl_space *isl_space_copy(__isl_keep isl_space *space);
+ void isl_space_free(__isl_take isl_space *space);
+ unsigned isl_space_dim(__isl_keep isl_space *space,
enum isl_dim_type type);
-The dimension specification used for creating a set
-needs to be created using C<isl_dim_set_alloc>, while
-that for creating a relation
-needs to be created using C<isl_dim_alloc>.
-C<isl_dim_size> can be used
+The space used for creating a parameter domain
+needs to be created using C<isl_space_params_alloc>.
+For other sets, the space
+needs to be created using C<isl_space_set_alloc>, while
+for a relation, the space
+needs to be created using C<isl_space_alloc>.
+C<isl_space_dim> can be used
to find out the number of dimensions of each type in
-a dimension specification, where type may be
+a space, where type may be
C<isl_dim_param>, C<isl_dim_in> (only for relations),
C<isl_dim_out> (only for relations), C<isl_dim_set>
(only for sets) or C<isl_dim_all>.
+To check whether a given space is that of a set or a map
+or whether it is a parameter space, use these functions:
+
+ #include <isl/space.h>
+ int isl_space_is_params(__isl_keep isl_space *space);
+ int isl_space_is_set(__isl_keep isl_space *space);
+
It is often useful to create objects that live in the
same space as some other object. This can be accomplished
by creating the new objects
(see L<Creating New Sets and Relations> or
-L<Creating New (Piecewise) Quasipolynomials>) based on the dimension
-specification of the original object.
+L<Creating New (Piecewise) Quasipolynomials>) based on the space
+of the original object.
#include <isl/set.h>
- __isl_give isl_dim *isl_basic_set_get_dim(
+ __isl_give isl_space *isl_basic_set_get_space(
__isl_keep isl_basic_set *bset);
- __isl_give isl_dim *isl_set_get_dim(__isl_keep isl_set *set);
+ __isl_give isl_space *isl_set_get_space(__isl_keep isl_set *set);
#include <isl/union_set.h>
- __isl_give isl_dim *isl_union_set_get_dim(
+ __isl_give isl_space *isl_union_set_get_space(
__isl_keep isl_union_set *uset);
#include <isl/map.h>
- __isl_give isl_dim *isl_basic_map_get_dim(
+ __isl_give isl_space *isl_basic_map_get_space(
__isl_keep isl_basic_map *bmap);
- __isl_give isl_dim *isl_map_get_dim(__isl_keep isl_map *map);
+ __isl_give isl_space *isl_map_get_space(__isl_keep isl_map *map);
#include <isl/union_map.h>
- __isl_give isl_dim *isl_union_map_get_dim(
+ __isl_give isl_space *isl_union_map_get_space(
__isl_keep isl_union_map *umap);
#include <isl/constraint.h>
- __isl_give isl_dim *isl_constraint_get_dim(
+ __isl_give isl_space *isl_constraint_get_space(
__isl_keep isl_constraint *constraint);
#include <isl/polynomial.h>
- __isl_give isl_dim *isl_qpolynomial_get_dim(
+ __isl_give isl_space *isl_qpolynomial_get_domain_space(
+ __isl_keep isl_qpolynomial *qp);
+ __isl_give isl_space *isl_qpolynomial_get_space(
__isl_keep isl_qpolynomial *qp);
- __isl_give isl_dim *isl_qpolynomial_fold_get_dim(
+ __isl_give isl_space *isl_qpolynomial_fold_get_space(
__isl_keep isl_qpolynomial_fold *fold);
- __isl_give isl_dim *isl_pw_qpolynomial_get_dim(
+ __isl_give isl_space *isl_pw_qpolynomial_get_domain_space(
+ __isl_keep isl_pw_qpolynomial *pwqp);
+ __isl_give isl_space *isl_pw_qpolynomial_get_space(
__isl_keep isl_pw_qpolynomial *pwqp);
- __isl_give isl_dim *isl_union_pw_qpolynomial_get_dim(
+ __isl_give isl_space *isl_pw_qpolynomial_fold_get_domain_space(
+ __isl_keep isl_pw_qpolynomial_fold *pwf);
+ __isl_give isl_space *isl_pw_qpolynomial_fold_get_space(
+ __isl_keep isl_pw_qpolynomial_fold *pwf);
+ __isl_give isl_space *isl_union_pw_qpolynomial_get_space(
__isl_keep isl_union_pw_qpolynomial *upwqp);
- __isl_give isl_dim *isl_union_pw_qpolynomial_fold_get_dim(
+ __isl_give isl_space *isl_union_pw_qpolynomial_fold_get_space(
__isl_keep isl_union_pw_qpolynomial_fold *upwf);
#include <isl/aff.h>
- __isl_give isl_dim *isl_aff_get_dim(
+ __isl_give isl_space *isl_aff_get_domain_space(
__isl_keep isl_aff *aff);
- __isl_give isl_dim *isl_pw_aff_get_dim(
+ __isl_give isl_space *isl_aff_get_space(
+ __isl_keep isl_aff *aff);
+ __isl_give isl_space *isl_pw_aff_get_domain_space(
+ __isl_keep isl_pw_aff *pwaff);
+ __isl_give isl_space *isl_pw_aff_get_space(
__isl_keep isl_pw_aff *pwaff);
+ __isl_give isl_space *isl_multi_aff_get_space(
+ __isl_keep isl_multi_aff *maff);
+ __isl_give isl_space *isl_pw_multi_aff_get_domain_space(
+ __isl_keep isl_pw_multi_aff *pma);
+ __isl_give isl_space *isl_pw_multi_aff_get_space(
+ __isl_keep isl_pw_multi_aff *pma);
#include <isl/point.h>
- __isl_give isl_dim *isl_point_get_dim(
+ __isl_give isl_space *isl_point_get_space(
__isl_keep isl_point *pnt);
-The names of the individual dimensions may be set or read off
+The identifiers or names of the individual dimensions may be set or read off
using the following functions.
- #include <isl/dim.h>
- __isl_give isl_dim *isl_dim_set_name(__isl_take isl_dim *dim,
- enum isl_dim_type type, unsigned pos,
- __isl_keep const char *name);
- __isl_keep const char *isl_dim_get_name(__isl_keep isl_dim *dim,
- enum isl_dim_type type, unsigned pos);
+ #include <isl/space.h>
+ __isl_give isl_space *isl_space_set_dim_id(
+ __isl_take isl_space *space,
+ enum isl_dim_type type, unsigned pos,
+ __isl_take isl_id *id);
+ int isl_space_has_dim_id(__isl_keep isl_space *space,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_id *isl_space_get_dim_id(
+ __isl_keep isl_space *space,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_space *isl_space_set_dim_name(
+ __isl_take isl_space *space,
+ enum isl_dim_type type, unsigned pos,
+ __isl_keep const char *name);
+ int isl_space_has_dim_name(__isl_keep isl_space *space,
+ enum isl_dim_type type, unsigned pos);
+ __isl_keep const char *isl_space_get_dim_name(
+ __isl_keep isl_space *space,
+ enum isl_dim_type type, unsigned pos);
-Note that C<isl_dim_get_name> returns a pointer to some internal
+Note that C<isl_space_get_name> returns a pointer to some internal
data structure, so the result can only be used while the
-corresponding C<isl_dim> is alive.
+corresponding C<isl_space> is alive.
Also note that every function that operates on two sets or relations
requires that both arguments have the same parameters. This also
means that if one of the arguments has named parameters, then the
other needs to have named parameters too and the names need to match.
-Pairs of C<isl_union_set> and/or C<isl_union_map> arguments may
-have different parameters (as long as they are named), in which case
-the result will have as parameters the union of the parameters of
+Pairs of C<isl_set>, C<isl_map>, C<isl_union_set> and/or C<isl_union_map>
+arguments may have different parameters (as long as they are named),
+in which case the result will have as parameters the union of the parameters of
the arguments.
-The names of entire spaces may be set or read off
+Given the identifier or name of a dimension (typically a parameter),
+its position can be obtained from the following function.
+
+ #include <isl/space.h>
+ int isl_space_find_dim_by_id(__isl_keep isl_space *space,
+ enum isl_dim_type type, __isl_keep isl_id *id);
+ int isl_space_find_dim_by_name(__isl_keep isl_space *space,
+ enum isl_dim_type type, const char *name);
+
+The identifiers or names of entire spaces may be set or read off
using the following functions.
- #include <isl/dim.h>
- __isl_give isl_dim *isl_dim_set_tuple_name(
- __isl_take isl_dim *dim,
+ #include <isl/space.h>
+ __isl_give isl_space *isl_space_set_tuple_id(
+ __isl_take isl_space *space,
+ enum isl_dim_type type, __isl_take isl_id *id);
+ __isl_give isl_space *isl_space_reset_tuple_id(
+ __isl_take isl_space *space, enum isl_dim_type type);
+ int isl_space_has_tuple_id(__isl_keep isl_space *space,
+ enum isl_dim_type type);
+ __isl_give isl_id *isl_space_get_tuple_id(
+ __isl_keep isl_space *space, enum isl_dim_type type);
+ __isl_give isl_space *isl_space_set_tuple_name(
+ __isl_take isl_space *space,
enum isl_dim_type type, const char *s);
- const char *isl_dim_get_tuple_name(__isl_keep isl_dim *dim,
+ const char *isl_space_get_tuple_name(__isl_keep isl_space *space,
enum isl_dim_type type);
-The C<dim> argument needs to be one of C<isl_dim_in>, C<isl_dim_out>
-or C<isl_dim_set>. As with C<isl_dim_get_name>,
-the C<isl_dim_get_tuple_name> function returns a pointer to some internal
+The C<type> argument needs to be one of C<isl_dim_in>, C<isl_dim_out>
+or C<isl_dim_set>. As with C<isl_space_get_name>,
+the C<isl_space_get_tuple_name> function returns a pointer to some internal
data structure.
Binary operations require the corresponding spaces of their arguments
to have the same name.
Spaces can be nested. In particular, the domain of a set or
the domain or range of a relation can be a nested relation.
The following functions can be used to construct and deconstruct
-such nested dimension specifications.
-
- #include <isl/dim.h>
- int isl_dim_is_wrapping(__isl_keep isl_dim *dim);
- __isl_give isl_dim *isl_dim_wrap(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_unwrap(__isl_take isl_dim *dim);
-
-The input to C<isl_dim_is_wrapping> and C<isl_dim_unwrap> should
-be the dimension specification of a set, while that of
-C<isl_dim_wrap> should be the dimension specification of a relation.
-Conversely, the output of C<isl_dim_unwrap> is the dimension specification
-of a relation, while that of C<isl_dim_wrap> is the dimension specification
-of a set.
-
-Dimension specifications can be created from other dimension
-specifications using the following functions.
-
- __isl_give isl_dim *isl_dim_domain(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_from_domain(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_range(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_from_range(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_reverse(__isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_join(__isl_take isl_dim *left,
- __isl_take isl_dim *right);
- __isl_give isl_dim *isl_dim_align_params(
- __isl_take isl_dim *dim1, __isl_take isl_dim *dim2)
- __isl_give isl_dim *isl_dim_insert(__isl_take isl_dim *dim,
+such nested spaces.
+
+ #include <isl/space.h>
+ int isl_space_is_wrapping(__isl_keep isl_space *space);
+ __isl_give isl_space *isl_space_wrap(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_unwrap(__isl_take isl_space *space);
+
+The input to C<isl_space_is_wrapping> and C<isl_space_unwrap> should
+be the space of a set, while that of
+C<isl_space_wrap> should be the space of a relation.
+Conversely, the output of C<isl_space_unwrap> is the space
+of a relation, while that of C<isl_space_wrap> is the space of a set.
+
+Spaces can be created from other spaces
+using the following functions.
+
+ __isl_give isl_space *isl_space_domain(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_from_domain(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_range(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_from_range(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_params(
+ __isl_take isl_space *space);
+ __isl_give isl_space *isl_space_set_from_params(
+ __isl_take isl_space *space);
+ __isl_give isl_space *isl_space_reverse(__isl_take isl_space *space);
+ __isl_give isl_space *isl_space_join(__isl_take isl_space *left,
+ __isl_take isl_space *right);
+ __isl_give isl_space *isl_space_align_params(
+ __isl_take isl_space *space1, __isl_take isl_space *space2)
+ __isl_give isl_space *isl_space_insert_dims(__isl_take isl_space *space,
enum isl_dim_type type, unsigned pos, unsigned n);
- __isl_give isl_dim *isl_dim_add(__isl_take isl_dim *dim,
+ __isl_give isl_space *isl_space_add_dims(__isl_take isl_space *space,
enum isl_dim_type type, unsigned n);
- __isl_give isl_dim *isl_dim_drop(__isl_take isl_dim *dim,
+ __isl_give isl_space *isl_space_drop_dims(__isl_take isl_space *space,
enum isl_dim_type type, unsigned first, unsigned n);
- __isl_give isl_dim *isl_dim_map_from_set(
- __isl_take isl_dim *dim);
- __isl_give isl_dim *isl_dim_zip(__isl_take isl_dim *dim);
+ __isl_give isl_space *isl_space_move_dims(__isl_take isl_space *space,
+ enum isl_dim_type dst_type, unsigned dst_pos,
+ enum isl_dim_type src_type, unsigned src_pos,
+ unsigned n);
+ __isl_give isl_space *isl_space_map_from_set(
+ __isl_take isl_space *space);
+ __isl_give isl_space *isl_space_map_from_domain_and_range(
+ __isl_take isl_space *domain,
+ __isl_take isl_space *range);
+ __isl_give isl_space *isl_space_zip(__isl_take isl_space *space);
Note that if dimensions are added or removed from a space, then
the name and the internal structure are lost.
=head2 Local Spaces
-A local space is essentially a dimension specification with
+A local space is essentially a space with
zero or more existentially quantified variables.
The local space of a basic set or relation can be obtained
using the following functions.
__isl_give isl_local_space *isl_basic_map_get_local_space(
__isl_keep isl_basic_map *bmap);
-A new local space can be created from a dimension specification using
+A new local space can be created from a space using
#include <isl/local_space.h>
- __isl_give isl_local_space *isl_local_space_from_dim(
- __isl_take isl_dim *dim);
+ __isl_give isl_local_space *isl_local_space_from_space(
+ __isl_take isl_space *space);
-They can be inspected, copied and freed using the following functions.
+They can be inspected, modified, copied and freed using the following functions.
#include <isl/local_space.h>
isl_ctx *isl_local_space_get_ctx(
__isl_keep isl_local_space *ls);
+ int isl_local_space_is_set(__isl_keep isl_local_space *ls);
int isl_local_space_dim(__isl_keep isl_local_space *ls,
enum isl_dim_type type);
const char *isl_local_space_get_dim_name(
__isl_give isl_local_space *isl_local_space_set_dim_name(
__isl_take isl_local_space *ls,
enum isl_dim_type type, unsigned pos, const char *s);
- __isl_give isl_dim *isl_local_space_get_dim(
+ __isl_give isl_local_space *isl_local_space_set_dim_id(
+ __isl_take isl_local_space *ls,
+ enum isl_dim_type type, unsigned pos,
+ __isl_take isl_id *id);
+ __isl_give isl_space *isl_local_space_get_space(
__isl_keep isl_local_space *ls);
- __isl_give isl_div *isl_local_space_get_div(
+ __isl_give isl_aff *isl_local_space_get_div(
__isl_keep isl_local_space *ls, int pos);
__isl_give isl_local_space *isl_local_space_copy(
__isl_keep isl_local_space *ls);
Local spaces can be created from other local spaces
using the following functions.
+ __isl_give isl_local_space *isl_local_space_domain(
+ __isl_take isl_local_space *ls);
+ __isl_give isl_local_space *isl_local_space_range(
+ __isl_take isl_local_space *ls);
__isl_give isl_local_space *isl_local_space_from_domain(
__isl_take isl_local_space *ls);
+ __isl_give isl_local_space *isl_local_space_intersect(
+ __isl_take isl_local_space *ls1,
+ __isl_take isl_local_space *ls2);
__isl_give isl_local_space *isl_local_space_add_dims(
__isl_take isl_local_space *ls,
enum isl_dim_type type, unsigned n);
#include <isl/set.h>
__isl_give isl_basic_set *isl_basic_set_read_from_file(
- isl_ctx *ctx, FILE *input, int nparam);
+ isl_ctx *ctx, FILE *input);
__isl_give isl_basic_set *isl_basic_set_read_from_str(
- isl_ctx *ctx, const char *str, int nparam);
+ isl_ctx *ctx, const char *str);
__isl_give isl_set *isl_set_read_from_file(isl_ctx *ctx,
- FILE *input, int nparam);
+ FILE *input);
__isl_give isl_set *isl_set_read_from_str(isl_ctx *ctx,
- const char *str, int nparam);
+ const char *str);
#include <isl/map.h>
__isl_give isl_basic_map *isl_basic_map_read_from_file(
- isl_ctx *ctx, FILE *input, int nparam);
+ isl_ctx *ctx, FILE *input);
__isl_give isl_basic_map *isl_basic_map_read_from_str(
- isl_ctx *ctx, const char *str, int nparam);
+ isl_ctx *ctx, const char *str);
__isl_give isl_map *isl_map_read_from_file(
- struct isl_ctx *ctx, FILE *input, int nparam);
+ isl_ctx *ctx, FILE *input);
__isl_give isl_map *isl_map_read_from_str(isl_ctx *ctx,
- const char *str, int nparam);
+ const char *str);
#include <isl/union_set.h>
__isl_give isl_union_set *isl_union_set_read_from_file(
isl_ctx *ctx, FILE *input);
__isl_give isl_union_set *isl_union_set_read_from_str(
- struct isl_ctx *ctx, const char *str);
+ isl_ctx *ctx, const char *str);
#include <isl/union_map.h>
__isl_give isl_union_map *isl_union_map_read_from_file(
isl_ctx *ctx, FILE *input);
__isl_give isl_union_map *isl_union_map_read_from_str(
- struct isl_ctx *ctx, const char *str);
+ isl_ctx *ctx, const char *str);
The input format is autodetected and may be either the C<PolyLib> format
or the C<isl> format.
-C<nparam> specifies how many of the final columns in
-the C<PolyLib> format correspond to parameters.
-If input is given in the C<isl> format, then the number
-of parameters needs to be equal to C<nparam>.
-If C<nparam> is negative, then any number of parameters
-is accepted in the C<isl> format and zero parameters
-are assumed in the C<PolyLib> format.
=head3 Output
=item * Empty sets and relations
__isl_give isl_basic_set *isl_basic_set_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_basic_map *isl_basic_map_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_set *isl_set_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_map *isl_map_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_union_set *isl_union_set_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_union_map *isl_union_map_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
-For C<isl_union_set>s and C<isl_union_map>s, the dimensions specification
+For C<isl_union_set>s and C<isl_union_map>s, the space
is only used to specify the parameters.
=item * Universe sets and relations
__isl_give isl_basic_set *isl_basic_set_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_basic_map *isl_basic_map_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_set *isl_set_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_map *isl_map_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_union_set *isl_union_set_universe(
__isl_take isl_union_set *uset);
__isl_give isl_union_map *isl_union_map_universe(
functions below only contain non-negative values.
__isl_give isl_basic_set *isl_basic_set_nat_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_basic_map *isl_basic_map_nat_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_set *isl_set_nat_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_map *isl_map_nat_universe(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
=item * Identity relations
__isl_give isl_basic_map *isl_basic_map_identity(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_map *isl_map_identity(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
-The number of input and output dimensions in C<dim> needs
+The number of input and output dimensions in C<space> needs
to be the same.
=item * Lexicographic order
__isl_give isl_map *isl_map_lex_lt(
- __isl_take isl_dim *set_dim);
+ __isl_take isl_space *set_space);
__isl_give isl_map *isl_map_lex_le(
- __isl_take isl_dim *set_dim);
+ __isl_take isl_space *set_space);
__isl_give isl_map *isl_map_lex_gt(
- __isl_take isl_dim *set_dim);
+ __isl_take isl_space *set_space);
__isl_give isl_map *isl_map_lex_ge(
- __isl_take isl_dim *set_dim);
+ __isl_take isl_space *set_space);
__isl_give isl_map *isl_map_lex_lt_first(
- __isl_take isl_dim *dim, unsigned n);
+ __isl_take isl_space *space, unsigned n);
__isl_give isl_map *isl_map_lex_le_first(
- __isl_take isl_dim *dim, unsigned n);
+ __isl_take isl_space *space, unsigned n);
__isl_give isl_map *isl_map_lex_gt_first(
- __isl_take isl_dim *dim, unsigned n);
+ __isl_take isl_space *space, unsigned n);
__isl_give isl_map *isl_map_lex_ge_first(
- __isl_take isl_dim *dim, unsigned n);
+ __isl_take isl_space *space, unsigned n);
-The first four functions take a dimension specification for a B<set>
+The first four functions take a space for a B<set>
and return relations that express that the elements in the domain
are lexicographically less
(C<isl_map_lex_lt>), less or equal (C<isl_map_lex_le>),
greater (C<isl_map_lex_gt>) or greater or equal (C<isl_map_lex_ge>)
than the elements in the range.
-The last four functions take a dimension specification for a map
+The last four functions take a space for a map
and return relations that express that the first C<n> dimensions
in the domain are lexicographically less
(C<isl_map_lex_lt_first>), less or equal (C<isl_map_lex_le_first>),
__isl_give isl_union_set *isl_union_set_from_set(
__isl_take isl_set *set);
+The inverse conversions below can only be used if the input
+union set or relation is known to contain elements in exactly one
+space.
+
+ __isl_give isl_set *isl_set_from_union_set(
+ __isl_take isl_union_set *uset);
+ __isl_give isl_map *isl_map_from_union_map(
+ __isl_take isl_union_map *umap);
+
+A zero-dimensional set can be constructed on a given parameter domain
+using the following function.
+
+ __isl_give isl_set *isl_set_from_params(
+ __isl_take isl_set *set);
+
Sets and relations can be copied and freed again using the following
functions.
__isl_keep isl_union_map *umap);
void isl_basic_set_free(__isl_take isl_basic_set *bset);
void isl_set_free(__isl_take isl_set *set);
- void isl_union_set_free(__isl_take isl_union_set *uset);
+ void *isl_union_set_free(__isl_take isl_union_set *uset);
void isl_basic_map_free(__isl_take isl_basic_map *bmap);
void isl_map_free(__isl_take isl_map *map);
- void isl_union_map_free(__isl_take isl_union_map *umap);
+ void *isl_union_map_free(__isl_take isl_union_map *umap);
Other sets and relations can be constructed by starting
from a universe set or relation, adding equality and/or
#include <isl/constraint.h>
__isl_give isl_constraint *isl_equality_alloc(
- __isl_take isl_dim *dim);
+ __isl_take isl_local_space *ls);
__isl_give isl_constraint *isl_inequality_alloc(
- __isl_take isl_dim *dim);
- void isl_constraint_set_constant(
- __isl_keep isl_constraint *constraint, isl_int v);
- void isl_constraint_set_coefficient(
- __isl_keep isl_constraint *constraint,
+ __isl_take isl_local_space *ls);
+ __isl_give isl_constraint *isl_constraint_set_constant(
+ __isl_take isl_constraint *constraint, isl_int v);
+ __isl_give isl_constraint *isl_constraint_set_constant_si(
+ __isl_take isl_constraint *constraint, int v);
+ __isl_give isl_constraint *isl_constraint_set_coefficient(
+ __isl_take isl_constraint *constraint,
enum isl_dim_type type, int pos, isl_int v);
+ __isl_give isl_constraint *isl_constraint_set_coefficient_si(
+ __isl_take isl_constraint *constraint,
+ enum isl_dim_type type, int pos, int v);
__isl_give isl_basic_map *isl_basic_map_add_constraint(
__isl_take isl_basic_map *bmap,
__isl_take isl_constraint *constraint);
For example, to create a set containing the even integers
between 10 and 42, you would use the following code.
- isl_int v;
- struct isl_dim *dim;
- struct isl_constraint *c;
- struct isl_basic_set *bset;
+ isl_space *space;
+ isl_local_space *ls;
+ isl_constraint *c;
+ isl_basic_set *bset;
- isl_int_init(v);
- dim = isl_dim_set_alloc(ctx, 0, 2);
- bset = isl_basic_set_universe(isl_dim_copy(dim));
+ space = isl_space_set_alloc(ctx, 0, 2);
+ bset = isl_basic_set_universe(isl_space_copy(space));
+ ls = isl_local_space_from_space(space);
- c = isl_equality_alloc(isl_dim_copy(dim));
- isl_int_set_si(v, -1);
- isl_constraint_set_coefficient(c, isl_dim_set, 0, v);
- isl_int_set_si(v, 2);
- isl_constraint_set_coefficient(c, isl_dim_set, 1, v);
+ c = isl_equality_alloc(isl_local_space_copy(ls));
+ c = isl_constraint_set_coefficient_si(c, isl_dim_set, 0, -1);
+ c = isl_constraint_set_coefficient_si(c, isl_dim_set, 1, 2);
bset = isl_basic_set_add_constraint(bset, c);
- c = isl_inequality_alloc(isl_dim_copy(dim));
- isl_int_set_si(v, -10);
- isl_constraint_set_constant(c, v);
- isl_int_set_si(v, 1);
- isl_constraint_set_coefficient(c, isl_dim_set, 0, v);
+ c = isl_inequality_alloc(isl_local_space_copy(ls));
+ c = isl_constraint_set_constant_si(c, -10);
+ c = isl_constraint_set_coefficient_si(c, isl_dim_set, 0, 1);
bset = isl_basic_set_add_constraint(bset, c);
- c = isl_inequality_alloc(dim);
- isl_int_set_si(v, 42);
- isl_constraint_set_constant(c, v);
- isl_int_set_si(v, -1);
- isl_constraint_set_coefficient(c, isl_dim_set, 0, v);
+ c = isl_inequality_alloc(ls);
+ c = isl_constraint_set_constant_si(c, 42);
+ c = isl_constraint_set_coefficient_si(c, isl_dim_set, 0, -1);
bset = isl_basic_set_add_constraint(bset, c);
bset = isl_basic_set_project_out(bset, isl_dim_set, 1, 1);
- isl_int_clear(v);
-
Or, alternatively,
- struct isl_basic_set *bset;
+ isl_basic_set *bset;
bset = isl_basic_set_read_from_str(ctx,
- "{[i] : exists (a : i = 2a and i >= 10 and i <= 42)}", -1);
+ "{[i] : exists (a : i = 2a and i >= 10 and i <= 42)}");
A basic set or relation can also be constructed from two matrices
describing the equalities and the inequalities.
__isl_give isl_basic_set *isl_basic_set_from_constraint_matrices(
- __isl_take isl_dim *dim,
+ __isl_take isl_space *space,
__isl_take isl_mat *eq, __isl_take isl_mat *ineq,
enum isl_dim_type c1,
enum isl_dim_type c2, enum isl_dim_type c3,
enum isl_dim_type c4);
__isl_give isl_basic_map *isl_basic_map_from_constraint_matrices(
- __isl_take isl_dim *dim,
+ __isl_take isl_space *space,
__isl_take isl_mat *eq, __isl_take isl_mat *ineq,
enum isl_dim_type c1,
enum isl_dim_type c2, enum isl_dim_type c3,
of C<isl_dim_cst>, C<isl_dim_param>,
C<isl_dim_in>, C<isl_dim_out> and C<isl_dim_div> for relations.
-A (basic) relation can also be constructed from a (piecewise) affine expression
-or a list of affine expressions (See L<"Piecewise Quasi Affine Expressions">).
+A (basic) set or relation can also be constructed from a (piecewise)
+(multiple) affine expression
+or a list of affine expressions
+(See L<"Piecewise Quasi Affine Expressions"> and
+L<"Piecewise Multiple Quasi Affine Expressions">).
__isl_give isl_basic_map *isl_basic_map_from_aff(
__isl_take isl_aff *aff);
+ __isl_give isl_set *isl_set_from_pw_aff(
+ __isl_take isl_pw_aff *pwaff);
__isl_give isl_map *isl_map_from_pw_aff(
__isl_take isl_pw_aff *pwaff);
__isl_give isl_basic_map *isl_basic_map_from_aff_list(
- __isl_take isl_dim *domain_dim,
+ __isl_take isl_space *domain_space,
__isl_take isl_aff_list *list);
+ __isl_give isl_basic_map *isl_basic_map_from_multi_aff(
+ __isl_take isl_multi_aff *maff)
+ __isl_give isl_set *isl_set_from_pw_multi_aff(
+ __isl_take isl_pw_multi_aff *pma);
+ __isl_give isl_map *isl_map_from_pw_multi_aff(
+ __isl_take isl_pw_multi_aff *pma);
The C<domain_dim> argument describes the domain of the resulting
basic relation. It is required because the C<list> may consist
int isl_union_set_n_set(__isl_keep isl_union_set *uset);
int isl_union_map_n_map(__isl_keep isl_union_map *umap);
-To extract the set or map from a union with a given dimension
-specification, use
+To extract the set or map in a given space from a union, use
__isl_give isl_set *isl_union_set_extract_set(
__isl_keep isl_union_set *uset,
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_map *isl_union_map_extract_map(
__isl_keep isl_union_map *umap,
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
To iterate over all the basic sets or maps in a set or map, use
__isl_keep isl_basic_map *bmap,
int (*fn)(__isl_take isl_constraint *c, void *user),
void *user);
- void isl_constraint_free(struct isl_constraint *c);
+ void *isl_constraint_free(__isl_take isl_constraint *c);
Again, the callback function C<fn> should return 0 if successful and
-1 if an error occurs. In the latter case, or if any other error
enum isl_dim_type type, unsigned first, unsigned n);
The explicit representations of the existentially quantified
-variables can be inspected using the following functions.
-Note that the user is only allowed to use these functions
+variables can be inspected using the following function.
+Note that the user is only allowed to use this function
if the inspected set or map is the result of a call
to C<isl_set_compute_divs> or C<isl_map_compute_divs>.
+The existentially quantified variable is equal to the floor
+of the returned affine expression. The affine expression
+itself can be inspected using the functions in
+L<"Piecewise Quasi Affine Expressions">.
- __isl_give isl_div *isl_constraint_div(
+ __isl_give isl_aff *isl_constraint_get_div(
__isl_keep isl_constraint *constraint, int pos);
- isl_ctx *isl_div_get_ctx(__isl_keep isl_div *div);
- void isl_div_get_constant(__isl_keep isl_div *div,
- isl_int *v);
- void isl_div_get_denominator(__isl_keep isl_div *div,
- isl_int *v);
- void isl_div_get_coefficient(__isl_keep isl_div *div,
- enum isl_dim_type type, int pos, isl_int *v);
To obtain the constraints of a basic set or map in matrix
form, use the following functions.
and should be a permutation of C<isl_dim_cst>, C<isl_dim_param>,
C<isl_dim_in>, C<isl_dim_out> and C<isl_dim_div>.
-The names of the domain and range spaces of a set or relation can be
-read off or set using the following functions.
+The number of parameters, input, output or set dimensions can
+be obtained using the following functions.
+
+ unsigned isl_basic_set_dim(__isl_keep isl_basic_set *bset,
+ enum isl_dim_type type);
+ unsigned isl_basic_map_dim(__isl_keep isl_basic_map *bmap,
+ enum isl_dim_type type);
+ unsigned isl_set_dim(__isl_keep isl_set *set,
+ enum isl_dim_type type);
+ unsigned isl_map_dim(__isl_keep isl_map *map,
+ enum isl_dim_type type);
+
+To check whether the description of a set or relation depends
+on one or more given dimensions, it is not necessary to iterate over all
+constraints. Instead the following functions can be used.
+
+ int isl_basic_set_involves_dims(
+ __isl_keep isl_basic_set *bset,
+ enum isl_dim_type type, unsigned first, unsigned n);
+ int isl_set_involves_dims(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned first, unsigned n);
+ int isl_basic_map_involves_dims(
+ __isl_keep isl_basic_map *bmap,
+ enum isl_dim_type type, unsigned first, unsigned n);
+ int isl_map_involves_dims(__isl_keep isl_map *map,
+ enum isl_dim_type type, unsigned first, unsigned n);
+
+Similarly, the following functions can be used to check whether
+a given dimension is involved in any lower or upper bound.
+
+ int isl_set_dim_has_lower_bound(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned pos);
+ int isl_set_dim_has_upper_bound(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned pos);
+
+The identifiers or names of the domain and range spaces of a set
+or relation can be read off or set using the following functions.
+
+ __isl_give isl_set *isl_set_set_tuple_id(
+ __isl_take isl_set *set, __isl_take isl_id *id);
+ __isl_give isl_set *isl_set_reset_tuple_id(
+ __isl_take isl_set *set);
+ int isl_set_has_tuple_id(__isl_keep isl_set *set);
+ __isl_give isl_id *isl_set_get_tuple_id(
+ __isl_keep isl_set *set);
+ __isl_give isl_map *isl_map_set_tuple_id(
+ __isl_take isl_map *map, enum isl_dim_type type,
+ __isl_take isl_id *id);
+ __isl_give isl_map *isl_map_reset_tuple_id(
+ __isl_take isl_map *map, enum isl_dim_type type);
+ int isl_map_has_tuple_id(__isl_keep isl_map *map,
+ enum isl_dim_type type);
+ __isl_give isl_id *isl_map_get_tuple_id(
+ __isl_keep isl_map *map, enum isl_dim_type type);
const char *isl_basic_set_get_tuple_name(
__isl_keep isl_basic_set *bset);
const char *isl_basic_map_get_tuple_name(
__isl_keep isl_basic_map *bmap,
enum isl_dim_type type);
+ __isl_give isl_basic_map *isl_basic_map_set_tuple_name(
+ __isl_take isl_basic_map *bmap,
+ enum isl_dim_type type, const char *s);
const char *isl_map_get_tuple_name(
__isl_keep isl_map *map,
enum isl_dim_type type);
-As with C<isl_dim_get_tuple_name>, the value returned points to
+As with C<isl_space_get_tuple_name>, the value returned points to
an internal data structure.
-The names of individual dimensions can be read off using
-the following functions.
+The identifiers, positions or names of individual dimensions can be
+read off using the following functions.
+
+ __isl_give isl_set *isl_set_set_dim_id(
+ __isl_take isl_set *set, enum isl_dim_type type,
+ unsigned pos, __isl_take isl_id *id);
+ int isl_set_has_dim_id(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_id *isl_set_get_dim_id(
+ __isl_keep isl_set *set, enum isl_dim_type type,
+ unsigned pos);
+ int isl_basic_map_has_dim_id(
+ __isl_keep isl_basic_map *bmap,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_map *isl_map_set_dim_id(
+ __isl_take isl_map *map, enum isl_dim_type type,
+ unsigned pos, __isl_take isl_id *id);
+ int isl_map_has_dim_id(__isl_keep isl_map *map,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_id *isl_map_get_dim_id(
+ __isl_keep isl_map *map, enum isl_dim_type type,
+ unsigned pos);
+
+ int isl_set_find_dim_by_id(__isl_keep isl_set *set,
+ enum isl_dim_type type, __isl_keep isl_id *id);
+ int isl_map_find_dim_by_id(__isl_keep isl_map *map,
+ enum isl_dim_type type, __isl_keep isl_id *id);
+ int isl_set_find_dim_by_name(__isl_keep isl_set *set,
+ enum isl_dim_type type, const char *name);
+ int isl_map_find_dim_by_name(__isl_keep isl_map *map,
+ enum isl_dim_type type, const char *name);
const char *isl_constraint_get_dim_name(
__isl_keep isl_constraint *constraint,
const char *isl_basic_set_get_dim_name(
__isl_keep isl_basic_set *bset,
enum isl_dim_type type, unsigned pos);
+ int isl_set_has_dim_name(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned pos);
const char *isl_set_get_dim_name(
__isl_keep isl_set *set,
enum isl_dim_type type, unsigned pos);
__isl_keep isl_map *map,
enum isl_dim_type type, unsigned pos);
-These functions are mostly useful to obtain the names
-of the parameters.
+These functions are mostly useful to obtain the identifiers, positions
+or names of the parameters. Identifiers of individual dimensions are
+essentially only useful for printing. They are ignored by all other
+operations and may not be preserved across those operations.
=head2 Properties
=item * Single-valuedness
+ int isl_map_plain_is_single_valued(
+ __isl_keep isl_map *map);
int isl_map_is_single_valued(__isl_keep isl_map *map);
int isl_union_map_is_single_valued(__isl_keep isl_union_map *umap);
int isl_map_is_bijective(__isl_keep isl_map *map);
int isl_union_map_is_bijective(__isl_keep isl_union_map *umap);
+=item * Position
+
+ int isl_basic_map_plain_is_fixed(
+ __isl_keep isl_basic_map *bmap,
+ enum isl_dim_type type, unsigned pos,
+ isl_int *val);
+ int isl_set_plain_is_fixed(__isl_keep isl_set *set,
+ enum isl_dim_type type, unsigned pos,
+ isl_int *val);
+ int isl_map_plain_is_fixed(__isl_keep isl_map *map,
+ enum isl_dim_type type, unsigned pos,
+ isl_int *val);
+
+Check if the relation obviously lies on a hyperplane where the given dimension
+has a fixed value and if so, return that value in C<*val>.
+
+=item * Space
+
+To check whether a set is a parameter domain, use this function:
+
+ int isl_set_is_params(__isl_keep isl_set *set);
+ int isl_union_set_is_params(
+ __isl_keep isl_union_set *uset);
+
=item * Wrapping
The following functions check whether the domain of the given
=item * Subset
+ int isl_basic_set_is_subset(
+ __isl_keep isl_basic_set *bset1,
+ __isl_keep isl_basic_set *bset2);
int isl_set_is_subset(__isl_keep isl_set *set1,
__isl_keep isl_set *set2);
int isl_set_is_strict_subset(
__isl_give isl_set *isl_set_complement(
__isl_take isl_set *set);
+ __isl_give isl_map *isl_map_complement(
+ __isl_take isl_map *map);
=item * Inverse map
enum isl_dim_type type, unsigned first, unsigned n);
__isl_give isl_map *isl_map_project_out(__isl_take isl_map *map,
enum isl_dim_type type, unsigned first, unsigned n);
+ __isl_give isl_basic_set *isl_basic_set_params(
+ __isl_take isl_basic_set *bset);
__isl_give isl_basic_set *isl_basic_map_domain(
__isl_take isl_basic_map *bmap);
__isl_give isl_basic_set *isl_basic_map_range(
__isl_take isl_basic_map *bmap);
+ __isl_give isl_set *isl_set_params(__isl_take isl_set *set);
+ __isl_give isl_set *isl_map_params(__isl_take isl_map *map);
__isl_give isl_set *isl_map_domain(
__isl_take isl_map *bmap);
__isl_give isl_set *isl_map_range(
__isl_take isl_map *map);
+ __isl_give isl_set *isl_union_set_params(
+ __isl_take isl_union_set *uset);
+ __isl_give isl_set *isl_union_map_params(
+ __isl_take isl_union_map *umap);
__isl_give isl_union_set *isl_union_map_domain(
__isl_take isl_union_map *umap);
__isl_give isl_union_set *isl_union_map_range(
__isl_give isl_set *isl_set_eliminate(
__isl_take isl_set *set, enum isl_dim_type type,
unsigned first, unsigned n);
+ __isl_give isl_basic_map *isl_basic_map_eliminate(
+ __isl_take isl_basic_map *bmap,
+ enum isl_dim_type type,
+ unsigned first, unsigned n);
+ __isl_give isl_map *isl_map_eliminate(
+ __isl_take isl_map *map, enum isl_dim_type type,
+ unsigned first, unsigned n);
Eliminate the coefficients for the given dimensions from the constraints,
without removing the dimensions.
Intersect the set or relation with the hyperplane where the given
dimension has the fixed given value.
+ __isl_give isl_basic_map *isl_basic_map_lower_bound_si(
+ __isl_take isl_basic_map *bmap,
+ enum isl_dim_type type, unsigned pos, int value);
+ __isl_give isl_set *isl_set_lower_bound(
+ __isl_take isl_set *set,
+ enum isl_dim_type type, unsigned pos,
+ isl_int value);
+ __isl_give isl_set *isl_set_lower_bound_si(
+ __isl_take isl_set *set,
+ enum isl_dim_type type, unsigned pos, int value);
+ __isl_give isl_map *isl_map_lower_bound_si(
+ __isl_take isl_map *map,
+ enum isl_dim_type type, unsigned pos, int value);
+ __isl_give isl_set *isl_set_upper_bound(
+ __isl_take isl_set *set,
+ enum isl_dim_type type, unsigned pos,
+ isl_int value);
+ __isl_give isl_set *isl_set_upper_bound_si(
+ __isl_take isl_set *set,
+ enum isl_dim_type type, unsigned pos, int value);
+ __isl_give isl_map *isl_map_upper_bound_si(
+ __isl_take isl_map *map,
+ enum isl_dim_type type, unsigned pos, int value);
+
+Intersect the set or relation with the half-space where the given
+dimension has a value bounded by the fixed given value.
+
+ __isl_give isl_set *isl_set_equate(__isl_take isl_set *set,
+ enum isl_dim_type type1, int pos1,
+ enum isl_dim_type type2, int pos2);
+ __isl_give isl_map *isl_map_equate(__isl_take isl_map *map,
+ enum isl_dim_type type1, int pos1,
+ enum isl_dim_type type2, int pos2);
+
+Intersect the set or relation with the hyperplane where the given
+dimensions are equal to each other.
+
+ __isl_give isl_map *isl_map_oppose(__isl_take isl_map *map,
+ enum isl_dim_type type1, int pos1,
+ enum isl_dim_type type2, int pos2);
+
+Intersect the relation with the hyperplane where the given
+dimensions have opposite values.
+
=item * Identity
__isl_give isl_map *isl_set_identity(
__isl_give isl_union_map *isl_union_map_coalesce(
__isl_take isl_union_map *umap);
+One of the methods for combining pairs of basic sets or relations
+can result in coefficients that are much larger than those that appear
+in the constraints of the input. By default, the coefficients are
+not allowed to grow larger, but this can be changed by unsetting
+the following option.
+
+ int isl_options_set_coalesce_bounded_wrapping(
+ isl_ctx *ctx, int val);
+ int isl_options_get_coalesce_bounded_wrapping(
+ isl_ctx *ctx);
+
=item * Detecting equalities
__isl_give isl_basic_set *isl_basic_set_detect_equalities(
In case of union sets and relations, the polyhedral hull is computed
per space.
+=item * Feasibility
+
+ __isl_give isl_basic_set *isl_basic_set_sample(
+ __isl_take isl_basic_set *bset);
+ __isl_give isl_basic_set *isl_set_sample(
+ __isl_take isl_set *set);
+ __isl_give isl_basic_map *isl_basic_map_sample(
+ __isl_take isl_basic_map *bmap);
+ __isl_give isl_basic_map *isl_map_sample(
+ __isl_take isl_map *map);
+
+If the input (basic) set or relation is non-empty, then return
+a singleton subset of the input. Otherwise, return an empty set.
+
=item * Optimization
#include <isl/ilp.h>
enum isl_lp_result isl_basic_set_max(
__isl_keep isl_basic_set *bset,
__isl_keep isl_aff *obj, isl_int *opt)
+ enum isl_lp_result isl_set_min(__isl_keep isl_set *set,
+ __isl_keep isl_aff *obj, isl_int *opt);
enum isl_lp_result isl_set_max(__isl_keep isl_set *set,
__isl_keep isl_aff *obj, isl_int *opt);
-Compute the maximum of the integer affine expression C<obj>
+Compute the minimum or maximum of the integer affine expression C<obj>
over the points in C<set>, returning the result in C<opt>.
The return value may be one of C<isl_lp_error>,
C<isl_lp_ok>, C<isl_lp_unbounded> or C<isl_lp_empty>.
=item * Parametric optimization
+ __isl_give isl_pw_aff *isl_set_dim_min(
+ __isl_take isl_set *set, int pos);
__isl_give isl_pw_aff *isl_set_dim_max(
__isl_take isl_set *set, int pos);
+ __isl_give isl_pw_aff *isl_map_dim_max(
+ __isl_take isl_map *map, int pos);
-Compute the maximum of the given set dimension as a function of the
-parameters, but independently of the other set dimensions.
+Compute the minimum or maximum of the given set or output dimension
+as a function of the parameters (and input dimensions), but independently
+of the other set or output dimensions.
For lexicographic optimization, see L<"Lexicographic Optimization">.
=item * Dual
=item * Power
+ __isl_give isl_map *isl_map_fixed_power(
+ __isl_take isl_map *map, isl_int exp);
+ __isl_give isl_union_map *isl_union_map_fixed_power(
+ __isl_take isl_union_map *umap, isl_int exp);
+
+Compute the given power of C<map>, where C<exp> is assumed to be non-zero.
+If the exponent C<exp> is negative, then the -C<exp> th power of the inverse
+of C<map> is computed.
+
__isl_give isl_map *isl_map_power(__isl_take isl_map *map,
int *exact);
__isl_give isl_union_map *isl_union_map_power(
__isl_take isl_basic_set *bset);
__isl_give isl_set *isl_set_flatten(
__isl_take isl_set *set);
+ __isl_give isl_basic_map *isl_basic_map_flatten_domain(
+ __isl_take isl_basic_map *bmap);
__isl_give isl_basic_map *isl_basic_map_flatten_range(
__isl_take isl_basic_map *bmap);
__isl_give isl_map *isl_map_flatten_range(
__isl_take isl_map *map);
+ __isl_give isl_map *isl_map_flatten_domain(
+ __isl_take isl_map *map);
__isl_give isl_basic_map *isl_basic_map_flatten(
__isl_take isl_basic_map *bmap);
__isl_give isl_map *isl_map_flatten(
__isl_give isl_union_set *isl_union_set_lift(
__isl_take isl_union_set *uset);
+Given a local space that contains the existentially quantified
+variables of a set, a basic relation that, when applied to
+a basic set, has essentially the same effect as C<isl_basic_set_lift>,
+can be constructed using the following function.
+
+ #include <isl/local_space.h>
+ __isl_give isl_basic_map *isl_local_space_lifting(
+ __isl_take isl_local_space *ls);
+
=item * Internal Product
__isl_give isl_basic_map *isl_basic_map_zip(
__isl_give isl_set *isl_set_align_params(
__isl_take isl_set *set,
- __isl_take isl_dim *model);
+ __isl_take isl_space *model);
__isl_give isl_map *isl_map_align_params(
__isl_take isl_map *map,
- __isl_take isl_dim *model);
+ __isl_take isl_space *model);
Change the order of the parameters of the given set or relation
such that the first parameters match those of C<model>.
__isl_give isl_map *isl_map_add_dims(
__isl_take isl_map *map,
enum isl_dim_type type, unsigned n);
+ __isl_give isl_set *isl_set_insert_dims(
+ __isl_take isl_set *set,
+ enum isl_dim_type type, unsigned pos, unsigned n);
+ __isl_give isl_map *isl_map_insert_dims(
+ __isl_take isl_map *map,
+ enum isl_dim_type type, unsigned pos, unsigned n);
+ __isl_give isl_basic_set *isl_basic_set_move_dims(
+ __isl_take isl_basic_set *bset,
+ enum isl_dim_type dst_type, unsigned dst_pos,
+ enum isl_dim_type src_type, unsigned src_pos,
+ unsigned n);
+ __isl_give isl_basic_map *isl_basic_map_move_dims(
+ __isl_take isl_basic_map *bmap,
+ enum isl_dim_type dst_type, unsigned dst_pos,
+ enum isl_dim_type src_type, unsigned src_pos,
+ unsigned n);
+ __isl_give isl_set *isl_set_move_dims(
+ __isl_take isl_set *set,
+ enum isl_dim_type dst_type, unsigned dst_pos,
+ enum isl_dim_type src_type, unsigned src_pos,
+ unsigned n);
+ __isl_give isl_map *isl_map_move_dims(
+ __isl_take isl_map *map,
+ enum isl_dim_type dst_type, unsigned dst_pos,
+ enum isl_dim_type src_type, unsigned src_pos,
+ unsigned n);
It is usually not advisable to directly change the (input or output)
space of a set or a relation as this removes the name and the internal
=item * Intersection
+ __isl_give isl_basic_set *isl_basic_set_intersect_params(
+ __isl_take isl_basic_set *bset1,
+ __isl_take isl_basic_set *bset2);
__isl_give isl_basic_set *isl_basic_set_intersect(
__isl_take isl_basic_set *bset1,
__isl_take isl_basic_set *bset2);
__isl_give isl_set *isl_set_intersect(
__isl_take isl_set *set1,
__isl_take isl_set *set2);
+ __isl_give isl_union_set *isl_union_set_intersect_params(
+ __isl_take isl_union_set *uset,
+ __isl_take isl_set *set);
+ __isl_give isl_union_map *isl_union_map_intersect_params(
+ __isl_take isl_union_map *umap,
+ __isl_take isl_set *set);
__isl_give isl_union_set *isl_union_set_intersect(
__isl_take isl_union_set *uset1,
__isl_take isl_union_set *uset2);
__isl_give isl_map *isl_map_subtract(
__isl_take isl_map *map1,
__isl_take isl_map *map2);
+ __isl_give isl_map *isl_map_subtract_domain(
+ __isl_take isl_map *map,
+ __isl_take isl_set *dom);
+ __isl_give isl_map *isl_map_subtract_range(
+ __isl_take isl_map *map,
+ __isl_take isl_set *dom);
__isl_give isl_union_set *isl_union_set_subtract(
__isl_take isl_union_set *uset1,
__isl_take isl_union_set *uset2);
__isl_give isl_union_set *isl_union_set_product(
__isl_take isl_union_set *uset1,
__isl_take isl_union_set *uset2);
+ __isl_give isl_basic_map *isl_basic_map_domain_product(
+ __isl_take isl_basic_map *bmap1,
+ __isl_take isl_basic_map *bmap2);
__isl_give isl_basic_map *isl_basic_map_range_product(
__isl_take isl_basic_map *bmap1,
__isl_take isl_basic_map *bmap2);
+ __isl_give isl_map *isl_map_domain_product(
+ __isl_take isl_map *map1,
+ __isl_take isl_map *map2);
__isl_give isl_map *isl_map_range_product(
__isl_take isl_map *map1,
__isl_take isl_map *map2);
__isl_give isl_basic_map *isl_basic_map_flat_range_product(
__isl_take isl_basic_map *bmap1,
__isl_take isl_basic_map *bmap2);
+ __isl_give isl_map *isl_map_flat_domain_product(
+ __isl_take isl_map *map1,
+ __isl_take isl_map *map2);
__isl_give isl_map *isl_map_flat_range_product(
__isl_take isl_map *map1,
__isl_take isl_map *map2);
__isl_take isl_basic_set *context);
__isl_give isl_set *isl_set_gist(__isl_take isl_set *set,
__isl_take isl_set *context);
+ __isl_give isl_set *isl_set_gist_params(
+ __isl_take isl_set *set,
+ __isl_take isl_set *context);
__isl_give isl_union_set *isl_union_set_gist(
__isl_take isl_union_set *uset,
__isl_take isl_union_set *context);
+ __isl_give isl_union_set *isl_union_set_gist_params(
+ __isl_take isl_union_set *uset,
+ __isl_take isl_set *set);
__isl_give isl_basic_map *isl_basic_map_gist(
__isl_take isl_basic_map *bmap,
__isl_take isl_basic_map *context);
__isl_give isl_map *isl_map_gist(__isl_take isl_map *map,
__isl_take isl_map *context);
+ __isl_give isl_map *isl_map_gist_params(
+ __isl_take isl_map *map,
+ __isl_take isl_set *context);
+ __isl_give isl_map *isl_map_gist_domain(
+ __isl_take isl_map *map,
+ __isl_take isl_set *context);
+ __isl_give isl_map *isl_map_gist_range(
+ __isl_take isl_map *map,
+ __isl_take isl_set *context);
__isl_give isl_union_map *isl_union_map_gist(
__isl_take isl_union_map *umap,
__isl_take isl_union_map *context);
+ __isl_give isl_union_map *isl_union_map_gist_params(
+ __isl_take isl_union_map *umap,
+ __isl_take isl_set *set);
+ __isl_give isl_union_map *isl_union_map_gist_domain(
+ __isl_take isl_union_map *umap,
+ __isl_take isl_union_set *uset);
+ __isl_give isl_union_map *isl_union_map_gist_range(
+ __isl_take isl_union_map *umap,
+ __isl_take isl_union_set *uset);
The gist operation returns a set or relation that has the
same intersection with the context as the input set or relation.
__isl_give isl_union_map *isl_union_map_lexmax(
__isl_take isl_union_map *umap);
+The following functions return their result in the form of
+a piecewise multi-affine expression
+(See L<"Piecewise Multiple Quasi Affine Expressions">),
+but are otherwise equivalent to the corresponding functions
+returning a basic set or relation.
+
+ __isl_give isl_pw_multi_aff *
+ isl_basic_map_lexmin_pw_multi_aff(
+ __isl_take isl_basic_map *bmap);
+ __isl_give isl_pw_multi_aff *
+ isl_basic_set_partial_lexmin_pw_multi_aff(
+ __isl_take isl_basic_set *bset,
+ __isl_take isl_basic_set *dom,
+ __isl_give isl_set **empty);
+ __isl_give isl_pw_multi_aff *
+ isl_basic_set_partial_lexmax_pw_multi_aff(
+ __isl_take isl_basic_set *bset,
+ __isl_take isl_basic_set *dom,
+ __isl_give isl_set **empty);
+ __isl_give isl_pw_multi_aff *
+ isl_basic_map_partial_lexmin_pw_multi_aff(
+ __isl_take isl_basic_map *bmap,
+ __isl_take isl_basic_set *dom,
+ __isl_give isl_set **empty);
+ __isl_give isl_pw_multi_aff *
+ isl_basic_map_partial_lexmax_pw_multi_aff(
+ __isl_take isl_basic_map *bmap,
+ __isl_take isl_basic_set *dom,
+ __isl_give isl_set **empty);
+
=head2 Lists
Lists are defined over several element types, including
-C<isl_aff>, C<isl_basic_set> and C<isl_set>.
+C<isl_aff>, C<isl_pw_aff>, C<isl_basic_set> and C<isl_set>.
Here we take lists of C<isl_set>s as an example.
Lists can be created, copied and freed using the following functions.
#include <isl/list.h>
+ __isl_give isl_set_list *isl_set_list_from_set(
+ __isl_take isl_set *el);
__isl_give isl_set_list *isl_set_list_alloc(
isl_ctx *ctx, int n);
__isl_give isl_set_list *isl_set_list_copy(
__isl_give isl_set_list *isl_set_list_add(
__isl_take isl_set_list *list,
__isl_take isl_set *el);
- void isl_set_list_free(__isl_take isl_set_list *list);
+ __isl_give isl_set_list *isl_set_list_concat(
+ __isl_take isl_set_list *list1,
+ __isl_take isl_set_list *list2);
+ void *isl_set_list_free(__isl_take isl_set_list *list);
C<isl_set_list_alloc> creates an empty list with a capacity for
-C<n> elements.
+C<n> elements. C<isl_set_list_from_set> creates a list with a single
+element.
Lists can be inspected using the following functions.
#include <isl/list.h>
isl_ctx *isl_set_list_get_ctx(__isl_keep isl_set_list *list);
int isl_set_list_n_set(__isl_keep isl_set_list *list);
- __isl_give struct isl_set *isl_set_list_get_set(
+ __isl_give isl_set *isl_set_list_get_set(
__isl_keep isl_set_list *list, int index);
int isl_set_list_foreach(__isl_keep isl_set_list *list,
- int (*fn)(__isl_take struct isl_set *el, void *user),
+ int (*fn)(__isl_take isl_set *el, void *user),
void *user);
Lists can be printed using
__isl_take isl_printer *p,
__isl_keep isl_set_list *list);
+=head2 Vectors
+
+Vectors can be created, copied and freed using the following functions.
+
+ #include <isl/vec.h>
+ __isl_give isl_vec *isl_vec_alloc(isl_ctx *ctx,
+ unsigned size);
+ __isl_give isl_vec *isl_vec_copy(__isl_keep isl_vec *vec);
+ void isl_vec_free(__isl_take isl_vec *vec);
+
+Note that the elements of a newly created vector may have arbitrary values.
+The elements can be changed and inspected using the following functions.
+
+ isl_ctx *isl_vec_get_ctx(__isl_keep isl_vec *vec);
+ int isl_vec_size(__isl_keep isl_vec *vec);
+ int isl_vec_get_element(__isl_keep isl_vec *vec,
+ int pos, isl_int *v);
+ __isl_give isl_vec *isl_vec_set_element(
+ __isl_take isl_vec *vec, int pos, isl_int v);
+ __isl_give isl_vec *isl_vec_set_element_si(
+ __isl_take isl_vec *vec, int pos, int v);
+ __isl_give isl_vec *isl_vec_set(__isl_take isl_vec *vec,
+ isl_int v);
+
+C<isl_vec_get_element> will return a negative value if anything went wrong.
+In that case, the value of C<*v> is undefined.
+
=head2 Matrices
Matrices can be created, copied and freed using the following functions.
#include <isl/mat.h>
- __isl_give isl_mat *isl_mat_alloc(struct isl_ctx *ctx,
+ __isl_give isl_mat *isl_mat_alloc(isl_ctx *ctx,
unsigned n_row, unsigned n_col);
__isl_give isl_mat *isl_mat_copy(__isl_keep isl_mat *mat);
void isl_mat_free(__isl_take isl_mat *mat);
=head2 Piecewise Quasi Affine Expressions
-The zero quasi affine expression can be created using
+The zero quasi affine expression on a given domain can be created using
- __isl_give isl_aff *isl_aff_zero(
+ __isl_give isl_aff *isl_aff_zero_on_domain(
__isl_take isl_local_space *ls);
-A quasi affine expression can also be initialized from an C<isl_div>:
-
- #include <isl/div.h>
- __isl_give isl_aff *isl_aff_from_div(__isl_take isl_div *div);
+Note that the space in which the resulting object lives is a map space
+with the given space as domain and a one-dimensional range.
An empty piecewise quasi affine expression (one with no cells)
or a piecewise quasi affine expression with a single cell can
#include <isl/aff.h>
__isl_give isl_pw_aff *isl_pw_aff_empty(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_pw_aff *isl_pw_aff_alloc(
__isl_take isl_set *set, __isl_take isl_aff *aff);
+ __isl_give isl_pw_aff *isl_pw_aff_from_aff(
+ __isl_take isl_aff *aff);
+
+A piecewise quasi affine expression that is equal to 1 on a set
+and 0 outside the set can be created using the following function.
+
+ #include <isl/aff.h>
+ __isl_give isl_pw_aff *isl_set_indicator_function(
+ __isl_take isl_set *set);
Quasi affine expressions can be copied and freed using
isl_ctx *isl_aff_get_ctx(__isl_keep isl_aff *aff);
int isl_aff_dim(__isl_keep isl_aff *aff,
enum isl_dim_type type);
+ __isl_give isl_local_space *isl_aff_get_domain_local_space(
+ __isl_keep isl_aff *aff);
__isl_give isl_local_space *isl_aff_get_local_space(
__isl_keep isl_aff *aff);
const char *isl_aff_get_dim_name(__isl_keep isl_aff *aff,
enum isl_dim_type type, unsigned pos);
+ const char *isl_pw_aff_get_dim_name(
+ __isl_keep isl_pw_aff *pa,
+ enum isl_dim_type type, unsigned pos);
+ int isl_pw_aff_has_dim_id(__isl_keep isl_pw_aff *pa,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_id *isl_pw_aff_get_dim_id(
+ __isl_keep isl_pw_aff *pa,
+ enum isl_dim_type type, unsigned pos);
int isl_aff_get_constant(__isl_keep isl_aff *aff,
isl_int *v);
int isl_aff_get_coefficient(__isl_keep isl_aff *aff,
enum isl_dim_type type, int pos, isl_int *v);
int isl_aff_get_denominator(__isl_keep isl_aff *aff,
isl_int *v);
- __isl_give isl_div *isl_aff_get_div(
+ __isl_give isl_aff *isl_aff_get_div(
__isl_keep isl_aff *aff, int pos);
+ int isl_pw_aff_n_piece(__isl_keep isl_pw_aff *pwaff);
+ int isl_pw_aff_foreach_piece(__isl_keep isl_pw_aff *pwaff,
+ int (*fn)(__isl_take isl_set *set,
+ __isl_take isl_aff *aff,
+ void *user), void *user);
+
+ int isl_aff_is_cst(__isl_keep isl_aff *aff);
+ int isl_pw_aff_is_cst(__isl_keep isl_pw_aff *pwaff);
+
int isl_aff_involves_dims(__isl_keep isl_aff *aff,
enum isl_dim_type type, unsigned first, unsigned n);
int isl_pw_aff_involves_dims(__isl_keep isl_pw_aff *pwaff,
It can be modified using
#include <isl/aff.h>
+ __isl_give isl_pw_aff *isl_pw_aff_set_tuple_id(
+ __isl_take isl_pw_aff *pwaff,
+ enum isl_dim_type type, __isl_take isl_id *id);
__isl_give isl_aff *isl_aff_set_dim_name(
__isl_take isl_aff *aff, enum isl_dim_type type,
unsigned pos, const char *s);
+ __isl_give isl_aff *isl_aff_set_dim_id(
+ __isl_take isl_aff *aff, enum isl_dim_type type,
+ unsigned pos, __isl_take isl_id *id);
+ __isl_give isl_pw_aff *isl_pw_aff_set_dim_id(
+ __isl_take isl_pw_aff *pma,
+ enum isl_dim_type type, unsigned pos,
+ __isl_take isl_id *id);
__isl_give isl_aff *isl_aff_set_constant(
__isl_take isl_aff *aff, isl_int v);
__isl_give isl_aff *isl_aff_set_constant_si(
int isl_aff_plain_is_zero(__isl_keep isl_aff *aff);
int isl_aff_plain_is_equal(__isl_keep isl_aff *aff1,
__isl_keep isl_aff *aff2);
+ int isl_pw_aff_plain_is_equal(
+ __isl_keep isl_pw_aff *pwaff1,
+ __isl_keep isl_pw_aff *pwaff2);
Operations include
__isl_give isl_pw_aff *isl_pw_aff_add(
__isl_take isl_pw_aff *pwaff1,
__isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_pw_aff *isl_pw_aff_min(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_pw_aff *isl_pw_aff_max(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
__isl_give isl_aff *isl_aff_sub(__isl_take isl_aff *aff1,
__isl_take isl_aff *aff2);
__isl_give isl_pw_aff *isl_pw_aff_sub(
__isl_give isl_aff *isl_aff_floor(__isl_take isl_aff *aff);
__isl_give isl_pw_aff *isl_pw_aff_floor(
__isl_take isl_pw_aff *pwaff);
+ __isl_give isl_aff *isl_aff_mod(__isl_take isl_aff *aff,
+ isl_int mod);
+ __isl_give isl_pw_aff *isl_pw_aff_mod(
+ __isl_take isl_pw_aff *pwaff, isl_int mod);
__isl_give isl_aff *isl_aff_scale(__isl_take isl_aff *aff,
isl_int f);
+ __isl_give isl_pw_aff *isl_pw_aff_scale(
+ __isl_take isl_pw_aff *pwaff, isl_int f);
__isl_give isl_aff *isl_aff_scale_down(__isl_take isl_aff *aff,
isl_int f);
__isl_give isl_aff *isl_aff_scale_down_ui(
__isl_give isl_pw_aff *isl_pw_aff_scale_down(
__isl_take isl_pw_aff *pwaff, isl_int f);
+ __isl_give isl_pw_aff *isl_pw_aff_list_min(
+ __isl_take isl_pw_aff_list *list);
+ __isl_give isl_pw_aff *isl_pw_aff_list_max(
+ __isl_take isl_pw_aff_list *list);
+
__isl_give isl_pw_aff *isl_pw_aff_coalesce(
__isl_take isl_pw_aff *pwqp);
+ __isl_give isl_aff *isl_aff_align_params(
+ __isl_take isl_aff *aff,
+ __isl_take isl_space *model);
__isl_give isl_pw_aff *isl_pw_aff_align_params(
__isl_take isl_pw_aff *pwaff,
- __isl_take isl_dim *model);
+ __isl_take isl_space *model);
+
+ __isl_give isl_aff *isl_aff_project_domain_on_params(
+ __isl_take isl_aff *aff);
+ __isl_give isl_aff *isl_aff_gist_params(
+ __isl_take isl_aff *aff,
+ __isl_take isl_set *context);
__isl_give isl_aff *isl_aff_gist(__isl_take isl_aff *aff,
__isl_take isl_set *context);
+ __isl_give isl_pw_aff *isl_pw_aff_gist_params(
+ __isl_take isl_pw_aff *pwaff,
+ __isl_take isl_set *context);
__isl_give isl_pw_aff *isl_pw_aff_gist(
__isl_take isl_pw_aff *pwaff,
__isl_take isl_set *context);
__isl_give isl_set *isl_pw_aff_domain(
__isl_take isl_pw_aff *pwaff);
+ __isl_give isl_pw_aff *isl_pw_aff_intersect_domain(
+ __isl_take isl_pw_aff *pa,
+ __isl_take isl_set *set);
+ __isl_give isl_pw_aff *isl_pw_aff_intersect_params(
+ __isl_take isl_pw_aff *pa,
+ __isl_take isl_set *set);
+
+ __isl_give isl_aff *isl_aff_mul(__isl_take isl_aff *aff1,
+ __isl_take isl_aff *aff2);
+ __isl_give isl_pw_aff *isl_pw_aff_mul(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
+When multiplying two affine expressions, at least one of the two needs
+to be a constant.
+
+ #include <isl/aff.h>
+ __isl_give isl_basic_set *isl_aff_le_basic_set(
+ __isl_take isl_aff *aff1, __isl_take isl_aff *aff2);
__isl_give isl_basic_set *isl_aff_ge_basic_set(
__isl_take isl_aff *aff1, __isl_take isl_aff *aff2);
__isl_give isl_set *isl_pw_aff_eq_set(
__isl_take isl_pw_aff *pwaff1,
__isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_set *isl_pw_aff_ne_set(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_set *isl_pw_aff_le_set(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
__isl_give isl_set *isl_pw_aff_lt_set(
__isl_take isl_pw_aff *pwaff1,
__isl_take isl_pw_aff *pwaff2);
__isl_take isl_pw_aff *pwaff1,
__isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_set *isl_pw_aff_list_eq_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+ __isl_give isl_set *isl_pw_aff_list_ne_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+ __isl_give isl_set *isl_pw_aff_list_le_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+ __isl_give isl_set *isl_pw_aff_list_lt_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+ __isl_give isl_set *isl_pw_aff_list_ge_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+ __isl_give isl_set *isl_pw_aff_list_gt_set(
+ __isl_take isl_pw_aff_list *list1,
+ __isl_take isl_pw_aff_list *list2);
+
The function C<isl_aff_ge_basic_set> returns a basic set
containing those elements in the shared space
of C<aff1> and C<aff2> where C<aff1> is greater than or equal to C<aff2>.
The function C<isl_aff_ge_set> returns a set
containing those elements in the shared domain
of C<pwaff1> and C<pwaff2> where C<pwaff1> is greater than or equal to C<pwaff2>.
+The functions operating on C<isl_pw_aff_list> apply the corresponding
+C<isl_pw_aff> function to each pair of elements in the two lists.
#include <isl/aff.h>
__isl_give isl_set *isl_pw_aff_nonneg_set(
__isl_take isl_pw_aff *pwaff);
+ __isl_give isl_set *isl_pw_aff_zero_set(
+ __isl_take isl_pw_aff *pwaff);
+ __isl_give isl_set *isl_pw_aff_non_zero_set(
+ __isl_take isl_pw_aff *pwaff);
The function C<isl_pw_aff_nonneg_set> returns a set
containing those elements in the domain
#include <isl/aff.h>
__isl_give isl_pw_aff *isl_pw_aff_cond(
- __isl_take isl_set *cond,
+ __isl_take isl_pw_aff *cond,
__isl_take isl_pw_aff *pwaff_true,
__isl_take isl_pw_aff *pwaff_false);
The function C<isl_pw_aff_cond> performs a conditional operator
and returns an expression that is equal to C<pwaff_true>
-for elements in C<cond> and equal to C<pwaff_false> for elements
-not in C<cond>.
+for elements where C<cond> is non-zero and equal to C<pwaff_false> for elements
+where C<cond> is zero.
#include <isl/aff.h>
- __isl_give isl_pw_aff *isl_pw_aff_max(
+ __isl_give isl_pw_aff *isl_pw_aff_union_min(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_pw_aff *isl_pw_aff_union_max(
+ __isl_take isl_pw_aff *pwaff1,
+ __isl_take isl_pw_aff *pwaff2);
+ __isl_give isl_pw_aff *isl_pw_aff_union_add(
__isl_take isl_pw_aff *pwaff1,
__isl_take isl_pw_aff *pwaff2);
-The function C<isl_pw_aff_max> computes a piecewise quasi-affine
+The function C<isl_pw_aff_union_max> computes a piecewise quasi-affine
expression with a domain that is the union of those of C<pwaff1> and
C<pwaff2> and such that on each cell, the quasi-affine expression is
the maximum of those of C<pwaff1> and C<pwaff2>. If only one of
C<pwaff1> or C<pwaff2> is defined on a given cell, then the
associated expression is the defined one.
+An expression can be read from input using
+
+ #include <isl/aff.h>
+ __isl_give isl_aff *isl_aff_read_from_str(
+ isl_ctx *ctx, const char *str);
+ __isl_give isl_pw_aff *isl_pw_aff_read_from_str(
+ isl_ctx *ctx, const char *str);
+
An expression can be printed using
#include <isl/aff.h>
__isl_take isl_printer *p,
__isl_keep isl_pw_aff *pwaff);
+=head2 Piecewise Multiple Quasi Affine Expressions
+
+An C<isl_multi_aff> object represents a sequence of
+zero or more affine expressions, all defined on the same domain space.
+
+An C<isl_multi_aff> can be constructed from a C<isl_aff_list> using the
+following function.
+
+ #include <isl/aff.h>
+ __isl_give isl_multi_aff *isl_multi_aff_from_aff_list(
+ __isl_take isl_space *space,
+ __isl_take isl_aff_list *list);
+
+An empty piecewise multiple quasi affine expression (one with no cells) or
+a piecewise multiple quasi affine expression with a single cell can
+be created using the following functions.
+
+ #include <isl/aff.h>
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_empty(
+ __isl_take isl_space *space);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_alloc(
+ __isl_take isl_set *set,
+ __isl_take isl_multi_aff *maff);
+
+A piecewise multiple quasi affine expression can also be initialized
+from an C<isl_set> or C<isl_map>, provided the C<isl_set> is a singleton
+and the C<isl_map> is single-valued.
+
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_from_set(
+ __isl_take isl_set *set);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_from_map(
+ __isl_take isl_map *map);
+
+Multiple quasi affine expressions can be copied and freed using
+
+ #include <isl/aff.h>
+ __isl_give isl_multi_aff *isl_multi_aff_copy(
+ __isl_keep isl_multi_aff *maff);
+ void *isl_multi_aff_free(__isl_take isl_multi_aff *maff);
+
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_copy(
+ __isl_keep isl_pw_multi_aff *pma);
+ void *isl_pw_multi_aff_free(
+ __isl_take isl_pw_multi_aff *pma);
+
+The expression can be inspected using
+
+ #include <isl/aff.h>
+ isl_ctx *isl_multi_aff_get_ctx(
+ __isl_keep isl_multi_aff *maff);
+ isl_ctx *isl_pw_multi_aff_get_ctx(
+ __isl_keep isl_pw_multi_aff *pma);
+ unsigned isl_multi_aff_dim(__isl_keep isl_multi_aff *maff,
+ enum isl_dim_type type);
+ unsigned isl_pw_multi_aff_dim(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type);
+ __isl_give isl_aff *isl_multi_aff_get_aff(
+ __isl_keep isl_multi_aff *multi, int pos);
+ __isl_give isl_pw_aff *isl_pw_multi_aff_get_pw_aff(
+ __isl_keep isl_pw_multi_aff *pma, int pos);
+ const char *isl_pw_multi_aff_get_dim_name(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type, unsigned pos);
+ __isl_give isl_id *isl_pw_multi_aff_get_dim_id(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type, unsigned pos);
+ const char *isl_multi_aff_get_tuple_name(
+ __isl_keep isl_multi_aff *multi,
+ enum isl_dim_type type);
+ const char *isl_pw_multi_aff_get_tuple_name(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type);
+ int isl_pw_multi_aff_has_tuple_id(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type);
+ __isl_give isl_id *isl_pw_multi_aff_get_tuple_id(
+ __isl_keep isl_pw_multi_aff *pma,
+ enum isl_dim_type type);
+
+ int isl_pw_multi_aff_foreach_piece(
+ __isl_keep isl_pw_multi_aff *pma,
+ int (*fn)(__isl_take isl_set *set,
+ __isl_take isl_multi_aff *maff,
+ void *user), void *user);
+
+It can be modified using
+
+ #include <isl/aff.h>
+ __isl_give isl_multi_aff *isl_multi_aff_set_dim_name(
+ __isl_take isl_multi_aff *maff,
+ enum isl_dim_type type, unsigned pos, const char *s);
+ __isl_give isl_multi_aff *isl_multi_aff_set_tuple_id(
+ __isl_take isl_multi_aff *maff,
+ enum isl_dim_type type, __isl_take isl_id *id);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_set_tuple_id(
+ __isl_take isl_pw_multi_aff *pma,
+ enum isl_dim_type type, __isl_take isl_id *id);
+
+ __isl_give isl_multi_aff *isl_multi_aff_drop_dims(
+ __isl_take isl_multi_aff *maff,
+ enum isl_dim_type type, unsigned first, unsigned n);
+
+To check whether two multiple affine expressions are
+obviously equal to each other, use
+
+ int isl_multi_aff_plain_is_equal(__isl_keep isl_multi_aff *maff1,
+ __isl_keep isl_multi_aff *maff2);
+ int isl_pw_multi_aff_plain_is_equal(
+ __isl_keep isl_pw_multi_aff *pma1,
+ __isl_keep isl_pw_multi_aff *pma2);
+
+Operations include
+
+ #include <isl/aff.h>
+ __isl_give isl_multi_aff *isl_multi_aff_add(
+ __isl_take isl_multi_aff *maff1,
+ __isl_take isl_multi_aff *maff2);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_add(
+ __isl_take isl_pw_multi_aff *pma1,
+ __isl_take isl_pw_multi_aff *pma2);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_union_add(
+ __isl_take isl_pw_multi_aff *pma1,
+ __isl_take isl_pw_multi_aff *pma2);
+ __isl_give isl_multi_aff *isl_multi_aff_scale(
+ __isl_take isl_multi_aff *maff,
+ isl_int f);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_intersect_params(
+ __isl_take isl_pw_multi_aff *pma,
+ __isl_take isl_set *set);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_intersect_domain(
+ __isl_take isl_pw_multi_aff *pma,
+ __isl_take isl_set *set);
+ __isl_give isl_multi_aff *isl_multi_aff_lift(
+ __isl_take isl_multi_aff *maff,
+ __isl_give isl_local_space **ls);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_coalesce(
+ __isl_take isl_pw_multi_aff *pma);
+ __isl_give isl_multi_aff *isl_multi_aff_gist_params(
+ __isl_take isl_multi_aff *maff,
+ __isl_take isl_set *context);
+ __isl_give isl_multi_aff *isl_multi_aff_gist(
+ __isl_take isl_multi_aff *maff,
+ __isl_take isl_set *context);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_gist_params(
+ __isl_take isl_pw_multi_aff *pma,
+ __isl_take isl_set *set);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_gist(
+ __isl_take isl_pw_multi_aff *pma,
+ __isl_take isl_set *set);
+ __isl_give isl_set *isl_pw_multi_aff_domain(
+ __isl_take isl_pw_multi_aff *pma);
+
+If the C<ls> argument of C<isl_multi_aff_lift> is not C<NULL>,
+then it is assigned the local space that lies at the basis of
+the lifting applied.
+
+An expression can be read from input using
+
+ #include <isl/aff.h>
+ __isl_give isl_multi_aff *isl_multi_aff_read_from_str(
+ isl_ctx *ctx, const char *str);
+ __isl_give isl_pw_multi_aff *isl_pw_multi_aff_read_from_str(
+ isl_ctx *ctx, const char *str);
+
+An expression can be printed using
+
+ #include <isl/aff.h>
+ __isl_give isl_printer *isl_printer_print_multi_aff(
+ __isl_take isl_printer *p,
+ __isl_keep isl_multi_aff *maff);
+ __isl_give isl_printer *isl_printer_print_pw_multi_aff(
+ __isl_take isl_printer *p,
+ __isl_keep isl_pw_multi_aff *pma);
+
=head2 Points
Points are elements of a set. They can be used to construct
individual elements of a set.
The zero point (the origin) can be created using
- __isl_give isl_point *isl_point_zero(__isl_take isl_dim *dim);
+ __isl_give isl_point *isl_point_zero(__isl_take isl_space *space);
The coordinates of a point can be inspected, set and changed
using
- void isl_point_get_coordinate(__isl_keep isl_point *pnt,
+ int isl_point_get_coordinate(__isl_keep isl_point *pnt,
enum isl_dim_type type, int pos, isl_int *v);
__isl_give isl_point *isl_point_set_coordinate(
__isl_take isl_point *pnt,
[n] -> { [x] -> [y] : x,y >= 0 and 0 <= x + y <= n }
-=head3 Printing (Piecewise) Quasipolynomials
+=head3 Input and Output
+
+Piecewise quasipolynomials can be read from input using
+
+ __isl_give isl_union_pw_qpolynomial *
+ isl_union_pw_qpolynomial_read_from_str(
+ isl_ctx *ctx, const char *str);
Quasipolynomials and piecewise quasipolynomials can be printed
using the following functions.
operations such as addition and multiplication
on the resulting quasipolynomials
- __isl_give isl_qpolynomial *isl_qpolynomial_zero(
- __isl_take isl_dim *dim);
- __isl_give isl_qpolynomial *isl_qpolynomial_one(
- __isl_take isl_dim *dim);
- __isl_give isl_qpolynomial *isl_qpolynomial_infty(
- __isl_take isl_dim *dim);
- __isl_give isl_qpolynomial *isl_qpolynomial_neginfty(
- __isl_take isl_dim *dim);
- __isl_give isl_qpolynomial *isl_qpolynomial_nan(
- __isl_take isl_dim *dim);
- __isl_give isl_qpolynomial *isl_qpolynomial_rat_cst(
- __isl_take isl_dim *dim,
+ __isl_give isl_qpolynomial *isl_qpolynomial_zero_on_domain(
+ __isl_take isl_space *domain);
+ __isl_give isl_qpolynomial *isl_qpolynomial_one_on_domain(
+ __isl_take isl_space *domain);
+ __isl_give isl_qpolynomial *isl_qpolynomial_infty_on_domain(
+ __isl_take isl_space *domain);
+ __isl_give isl_qpolynomial *isl_qpolynomial_neginfty_on_domain(
+ __isl_take isl_space *domain);
+ __isl_give isl_qpolynomial *isl_qpolynomial_nan_on_domain(
+ __isl_take isl_space *domain);
+ __isl_give isl_qpolynomial *isl_qpolynomial_rat_cst_on_domain(
+ __isl_take isl_space *domain,
const isl_int n, const isl_int d);
- __isl_give isl_qpolynomial *isl_qpolynomial_div(
- __isl_take isl_div *div);
- __isl_give isl_qpolynomial *isl_qpolynomial_var(
- __isl_take isl_dim *dim,
+ __isl_give isl_qpolynomial *isl_qpolynomial_var_on_domain(
+ __isl_take isl_space *domain,
enum isl_dim_type type, unsigned pos);
__isl_give isl_qpolynomial *isl_qpolynomial_from_aff(
__isl_take isl_aff *aff);
+Note that the space in which a quasipolynomial lives is a map space
+with a one-dimensional range. The C<domain> argument in some of
+the functions above corresponds to the domain of this map space.
+
The zero piecewise quasipolynomial or a piecewise quasipolynomial
with a single cell can be created using the following functions.
Multiple of these single cell piecewise quasipolynomials can
be combined to create more complicated piecewise quasipolynomials.
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_zero(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_alloc(
__isl_take isl_set *set,
__isl_take isl_qpolynomial *qp);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_from_qpolynomial(
+ __isl_take isl_qpolynomial *qp);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_from_pw_aff(
+ __isl_take isl_pw_aff *pwaff);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_zero(
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_from_pw_qpolynomial(
__isl_take isl_pw_qpolynomial *pwqp);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_add_pw_qpolynomial(
__isl_give isl_qpolynomial *isl_qpolynomial_copy(
__isl_keep isl_qpolynomial *qp);
- void isl_qpolynomial_free(__isl_take isl_qpolynomial *qp);
+ void *isl_qpolynomial_free(__isl_take isl_qpolynomial *qp);
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_copy(
__isl_keep isl_pw_qpolynomial *pwqp);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_copy(
__isl_keep isl_union_pw_qpolynomial *upwqp);
- void isl_union_pw_qpolynomial_free(
+ void *isl_union_pw_qpolynomial_free(
__isl_take isl_union_pw_qpolynomial *upwqp);
=head3 Inspecting (Piecewise) Quasipolynomials
int (*fn)(__isl_take isl_pw_qpolynomial *pwqp, void *user),
void *user);
-To extract the piecewise quasipolynomial from a union with a given dimension
-specification, use
+To extract the piecewise quasipolynomial in a given space from a union, use
__isl_give isl_pw_qpolynomial *
isl_union_pw_qpolynomial_extract_pw_qpolynomial(
__isl_keep isl_union_pw_qpolynomial *upwqp,
- __isl_take isl_dim *dim);
+ __isl_take isl_space *space);
To iterate over the cells in a piecewise quasipolynomial,
use either of the following two functions
isl_int *d);
int isl_term_get_exp(__isl_keep isl_term *term,
enum isl_dim_type type, unsigned pos);
- __isl_give isl_div *isl_term_get_div(
+ __isl_give isl_aff *isl_term_get_div(
__isl_keep isl_term *term, unsigned pos);
void isl_term_free(__isl_take isl_term *term);
then the numerator and denominator of the constant
are returned in C<*n> and C<*d>, respectively.
+To check whether two union piecewise quasipolynomials are
+obviously equal, use
+
+ int isl_union_pw_qpolynomial_plain_is_equal(
+ __isl_keep isl_union_pw_qpolynomial *upwqp1,
+ __isl_keep isl_union_pw_qpolynomial *upwqp2);
+
=head3 Operations on (Piecewise) Quasipolynomials
__isl_give isl_qpolynomial *isl_qpolynomial_scale(
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_mul(
__isl_take isl_pw_qpolynomial *pwqp1,
__isl_take isl_pw_qpolynomial *pwqp2);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_pow(
+ __isl_take isl_pw_qpolynomial *pwqp, unsigned exponent);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_add(
__isl_take isl_union_pw_qpolynomial *upwqp1,
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_intersect_domain(
__isl_take isl_pw_qpolynomial *pwpq,
__isl_take isl_set *set);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_intersect_params(
+ __isl_take isl_pw_qpolynomial *pwpq,
+ __isl_take isl_set *set);
__isl_give isl_union_set *isl_union_pw_qpolynomial_domain(
__isl_take isl_union_pw_qpolynomial *upwqp);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_intersect_domain(
__isl_take isl_union_pw_qpolynomial *upwpq,
__isl_take isl_union_set *uset);
+ __isl_give isl_union_pw_qpolynomial *
+ isl_union_pw_qpolynomial_intersect_params(
+ __isl_take isl_union_pw_qpolynomial *upwpq,
+ __isl_take isl_set *set);
__isl_give isl_qpolynomial *isl_qpolynomial_align_params(
__isl_take isl_qpolynomial *qp,
- __isl_take isl_dim *model);
+ __isl_take isl_space *model);
+
+ __isl_give isl_qpolynomial *isl_qpolynomial_project_domain_on_params(
+ __isl_take isl_qpolynomial *qp);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_project_domain_on_params(
+ __isl_take isl_pw_qpolynomial *pwqp);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_coalesce(
__isl_take isl_union_pw_qpolynomial *upwqp);
+ __isl_give isl_qpolynomial *isl_qpolynomial_gist_params(
+ __isl_take isl_qpolynomial *qp,
+ __isl_take isl_set *context);
__isl_give isl_qpolynomial *isl_qpolynomial_gist(
__isl_take isl_qpolynomial *qp,
__isl_take isl_set *context);
+ __isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_gist_params(
+ __isl_take isl_pw_qpolynomial *pwqp,
+ __isl_take isl_set *context);
__isl_give isl_pw_qpolynomial *isl_pw_qpolynomial_gist(
__isl_take isl_pw_qpolynomial *pwqp,
__isl_take isl_set *context);
+ __isl_give isl_union_pw_qpolynomial *
+ isl_union_pw_qpolynomial_gist_params(
+ __isl_take isl_union_pw_qpolynomial *upwqp,
+ __isl_take isl_set *context);
__isl_give isl_union_pw_qpolynomial *isl_union_pw_qpolynomial_gist(
__isl_take isl_union_pw_qpolynomial *upwqp,
__isl_take isl_union_set *context);
__isl_take isl_qpolynomial_fold *fold);
void *isl_pw_qpolynomial_fold_free(
__isl_take isl_pw_qpolynomial_fold *pwf);
- void isl_union_pw_qpolynomial_fold_free(
+ void *isl_union_pw_qpolynomial_fold_free(
__isl_take isl_union_pw_qpolynomial_fold *upwf);
=head3 Printing Piecewise Quasipolynomial Reductions
int (*fn)(__isl_take isl_qpolynomial *qp,
void *user), void *user);
+=head3 Properties of Piecewise Quasipolynomial Reductions
+
+To check whether two union piecewise quasipolynomial reductions are
+obviously equal, use
+
+ int isl_union_pw_qpolynomial_fold_plain_is_equal(
+ __isl_keep isl_union_pw_qpolynomial_fold *upwf1,
+ __isl_keep isl_union_pw_qpolynomial_fold *upwf2);
+
=head3 Operations on Piecewise Quasipolynomial Reductions
__isl_give isl_qpolynomial_fold *isl_qpolynomial_fold_scale(
__isl_take isl_union_pw_qpolynomial_fold *upwf,
__isl_take isl_point *pnt);
+ __isl_give isl_pw_qpolynomial_fold *
+ sl_pw_qpolynomial_fold_intersect_params(
+ __isl_take isl_pw_qpolynomial_fold *pwf,
+ __isl_take isl_set *set);
+
__isl_give isl_union_set *isl_union_pw_qpolynomial_fold_domain(
__isl_take isl_union_pw_qpolynomial_fold *upwf);
__isl_give isl_union_pw_qpolynomial_fold *isl_union_pw_qpolynomial_fold_intersect_domain(
__isl_take isl_union_pw_qpolynomial_fold *upwf,
__isl_take isl_union_set *uset);
+ __isl_give isl_union_pw_qpolynomial_fold *
+ isl_union_pw_qpolynomial_fold_intersect_params(
+ __isl_take isl_union_pw_qpolynomial_fold *upwf,
+ __isl_take isl_set *set);
+
+ __isl_give isl_pw_qpolynomial_fold *isl_pw_qpolynomial_fold_project_domain_on_params(
+ __isl_take isl_pw_qpolynomial_fold *pwf);
__isl_give isl_pw_qpolynomial_fold *isl_pw_qpolynomial_fold_coalesce(
__isl_take isl_pw_qpolynomial_fold *pwf);
__isl_give isl_union_pw_qpolynomial_fold *isl_union_pw_qpolynomial_fold_coalesce(
__isl_take isl_union_pw_qpolynomial_fold *upwf);
+ __isl_give isl_qpolynomial_fold *isl_qpolynomial_fold_gist_params(
+ __isl_take isl_qpolynomial_fold *fold,
+ __isl_take isl_set *context);
+ __isl_give isl_qpolynomial_fold *isl_qpolynomial_fold_gist(
+ __isl_take isl_qpolynomial_fold *fold,
+ __isl_take isl_set *context);
+
__isl_give isl_pw_qpolynomial_fold *isl_pw_qpolynomial_fold_gist(
__isl_take isl_pw_qpolynomial_fold *pwf,
__isl_take isl_set *context);
+ __isl_give isl_pw_qpolynomial_fold *isl_pw_qpolynomial_fold_gist_params(
+ __isl_take isl_pw_qpolynomial_fold *pwf,
+ __isl_take isl_set *context);
__isl_give isl_union_pw_qpolynomial_fold *isl_union_pw_qpolynomial_fold_gist(
__isl_take isl_union_pw_qpolynomial_fold *upwf,
__isl_take isl_union_set *context);
+ __isl_give isl_union_pw_qpolynomial_fold *
+ isl_union_pw_qpolynomial_fold_gist_params(
+ __isl_take isl_union_pw_qpolynomial_fold *upwf,
+ __isl_take isl_set *context);
The gist operation applies the gist operation to each of
the cells in the domain of the input piecewise quasipolynomial reduction.
of which of the source access relations was the last
to access the same data element before the given iteration
of the sink access.
+The resulting dependence relations map source iterations
+to the corresponding sink iterations.
To compute standard flow dependences, the sink should be
a read, while the sources should be writes.
If any of the source accesses are marked as being I<may>
-accesses, then there will be a dependence to the last
-I<must> access B<and> to any I<may> access that follows
+accesses, then there will be a dependence from the last
+I<must> access B<and> from any I<may> access that follows
this last I<must> access.
In particular, if I<all> sources are I<may> accesses,
then memory based dependence analysis is performed.
or C<may_no_source> may be C<NULL>, but a C<NULL> value for
any of the other arguments is treated as an error.
+=head3 Interaction with Dependence Analysis
+
+During the dependence analysis, we frequently need to perform
+the following operation. Given a relation between sink iterations
+and potential soure iterations from a particular source domain,
+what is the last potential source iteration corresponding to each
+sink iteration. It can sometimes be convenient to adjust
+the set of potential source iterations before or after each such operation.
+The prototypical example is fuzzy array dataflow analysis,
+where we need to analyze if, based on data-dependent constraints,
+the sink iteration can ever be executed without one or more of
+the corresponding potential source iterations being executed.
+If so, we can introduce extra parameters and select an unknown
+but fixed source iteration from the potential source iterations.
+To be able to perform such manipulations, C<isl> provides the following
+function.
+
+ #include <isl/flow.h>
+
+ typedef __isl_give isl_restriction *(*isl_access_restrict)(
+ __isl_keep isl_map *source_map,
+ __isl_keep isl_set *sink, void *source_user,
+ void *user);
+ __isl_give isl_access_info *isl_access_info_set_restrict(
+ __isl_take isl_access_info *acc,
+ isl_access_restrict fn, void *user);
+
+The function C<isl_access_info_set_restrict> should be called
+before calling C<isl_access_info_compute_flow> and registers a callback function
+that will be called any time C<isl> is about to compute the last
+potential source. The first argument is the (reverse) proto-dependence,
+mapping sink iterations to potential source iterations.
+The second argument represents the sink iterations for which
+we want to compute the last source iteration.
+The third argument is the token corresponding to the source
+and the final argument is the token passed to C<isl_access_info_set_restrict>.
+The callback is expected to return a restriction on either the input or
+the output of the operation computing the last potential source.
+If the input needs to be restricted then restrictions are needed
+for both the source and the sink iterations. The sink iterations
+and the potential source iterations will be intersected with these sets.
+If the output needs to be restricted then only a restriction on the source
+iterations is required.
+If any error occurs, the callback should return C<NULL>.
+An C<isl_restriction> object can be created and freed using the following
+functions.
+
+ #include <isl/flow.h>
+
+ __isl_give isl_restriction *isl_restriction_input(
+ __isl_take isl_set *source_restr,
+ __isl_take isl_set *sink_restr);
+ __isl_give isl_restriction *isl_restriction_output(
+ __isl_take isl_set *source_restr);
+ __isl_give isl_restriction *isl_restriction_none(
+ __isl_keep isl_map *source_map);
+ __isl_give isl_restriction *isl_restriction_empty(
+ __isl_keep isl_map *source_map);
+ void *isl_restriction_free(
+ __isl_take isl_restriction *restr);
+
+C<isl_restriction_none> and C<isl_restriction_empty> are special
+cases of C<isl_restriction_input>. C<isl_restriction_none>
+is essentially equivalent to
+
+ isl_restriction_input(isl_set_universe(
+ isl_space_range(isl_map_get_space(source_map))),
+ isl_set_universe(
+ isl_space_domain(isl_map_get_space(source_map))));
+
+whereas C<isl_restriction_empty> is essentially equivalent to
+
+ isl_restriction_input(isl_set_empty(
+ isl_space_range(isl_map_get_space(source_map))),
+ isl_set_universe(
+ isl_space_domain(isl_map_get_space(source_map))));
+
=head2 Scheduling
B<The functionality described in this section is fairly new
and may be subject to change.>
The following function can be used to compute a schedule
-for a union of domains. The generated schedule respects
-all C<validity> dependences. That is, all dependence distances
-over these dependences in the scheduled space are lexicographically
-positive. The generated schedule schedule also tries to minimize
-the dependence distances over C<proximity> dependences.
+for a union of domains.
+By default, the algorithm used to construct the schedule is similar
+to that of C<Pluto>.
+Alternatively, Feautrier's multi-dimensional scheduling algorithm can
+be selected.
+The generated schedule respects all C<validity> dependences.
+That is, all dependence distances over these dependences in the
+scheduled space are lexicographically positive.
+The default algorithm tries to minimize the dependence distances over
+C<proximity> dependences.
Moreover, it tries to obtain sequences (bands) of schedule dimensions
for groups of domains where the dependence distances have only
non-negative values.
-The algorithm used to construct the schedule is similar to that
-of C<Pluto>.
+When using Feautrier's algorithm, the C<proximity> dependence
+distances are only minimized during the extension to a
+full-dimensional schedule.
#include <isl/schedule.h>
__isl_give isl_schedule *isl_union_set_compute_schedule(
__isl_take isl_printer *p,
__isl_keep isl_band *band);
+=head3 Options
+
+ #include <isl/schedule.h>
+ int isl_options_set_schedule_max_coefficient(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_max_coefficient(
+ isl_ctx *ctx);
+ int isl_options_set_schedule_max_constant_term(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_max_constant_term(
+ isl_ctx *ctx);
+ int isl_options_set_schedule_maximize_band_depth(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_maximize_band_depth(
+ isl_ctx *ctx);
+ int isl_options_set_schedule_outer_zero_distance(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_outer_zero_distance(
+ isl_ctx *ctx);
+ int isl_options_set_schedule_split_scaled(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_split_scaled(
+ isl_ctx *ctx);
+ int isl_options_set_schedule_algorithm(
+ isl_ctx *ctx, int val);
+ int isl_options_get_schedule_algorithm(
+ isl_ctx *ctx);
+
+
+=over
+
+=item * schedule_max_coefficient
+
+This option enforces that the coefficients for variable and parameter
+dimensions in the calculated schedule are not larger than the specified value.
+This option can significantly increase the speed of the scheduling calculation
+and may also prevent fusing of unrelated dimensions. A value of -1 means that
+this option does not introduce bounds on the variable or parameter
+coefficients.
+
+=item * schedule_max_constant_term
+
+This option enforces that the constant coefficients in the calculated schedule
+are not larger than the maximal constant term. This option can significantly
+increase the speed of the scheduling calculation and may also prevent fusing of
+unrelated dimensions. A value of -1 means that this option does not introduce
+bounds on the constant coefficients.
+
+=item * schedule_maximize_band_depth
+
+If this option is set, we do not split bands at the point
+where we detect splitting is necessary. Instead, we
+backtrack and split bands as early as possible. This
+reduces the number of splits and maximizes the width of
+the bands. Wider bands give more possibilities for tiling.
+
+=item * schedule_outer_zero_distance
+
+If this option is set, then we try to construct schedules
+where the outermost scheduling dimension in each band
+results in a zero dependence distance over the proximity
+dependences.
+
+=item * schedule_split_scaled
+
+If this option is set, then we try to construct schedules in which the
+constant term is split off from the linear part if the linear parts of
+the scheduling rows for all nodes in the graphs have a common non-trivial
+divisor.
+The constant term is then placed in a separate band and the linear
+part is reduced.
+
+=item * schedule_algorithm
+
+Selects the scheduling algorithm to be used.
+Available scheduling algorithms are C<ISL_SCHEDULE_ALGORITHM_ISL>
+and C<ISL_SCHEDULE_ALGORITHM_FEAUTRIER>.
+
+=back
+
=head2 Parametric Vertex Enumeration
The parametric vertex enumeration described in this section