[polly] r330496 - Update isl to isl-0.19-107-gc4fe33d8

Tobias Grosser via llvm-commits llvm-commits at lists.llvm.org
Sat Apr 21 01:34:22 PDT 2018


Author: grosser
Date: Sat Apr 21 01:34:22 2018
New Revision: 330496

URL: http://llvm.org/viewvc/llvm-project?rev=330496&view=rev
Log:
Update isl to isl-0.19-107-gc4fe33d8

This is a regular maintenance update.

Added:
    polly/trunk/lib/External/isl/include/isl/stride_info.h
    polly/trunk/lib/External/isl/isl_multi_align_set.c
    polly/trunk/lib/External/isl/isl_multi_align_templ.c
    polly/trunk/lib/External/isl/isl_multi_align_union_set.c
    polly/trunk/lib/External/isl/isl_multi_explicit_domain.c
    polly/trunk/lib/External/isl/isl_multi_no_explicit_domain.c
    polly/trunk/lib/External/isl/isl_multi_pw_aff_explicit_domain.c
    polly/trunk/lib/External/isl/isl_multi_union_pw_aff_explicit_domain.c
    polly/trunk/lib/External/isl/isl_pw_eval.c
    polly/trunk/lib/External/isl/isl_pw_templ.h
    polly/trunk/lib/External/isl/test_inputs/codegen/component7.c
    polly/trunk/lib/External/isl/test_inputs/codegen/component7.st
    polly/trunk/lib/External/isl/uset_from_umap.c
Modified:
    polly/trunk/lib/External/CMakeLists.txt
    polly/trunk/lib/External/isl/AUTHORS
    polly/trunk/lib/External/isl/ChangeLog
    polly/trunk/lib/External/isl/GIT_HEAD_ID
    polly/trunk/lib/External/isl/Makefile.am
    polly/trunk/lib/External/isl/Makefile.in
    polly/trunk/lib/External/isl/aclocal.m4
    polly/trunk/lib/External/isl/config.guess
    polly/trunk/lib/External/isl/config.sub
    polly/trunk/lib/External/isl/configure
    polly/trunk/lib/External/isl/configure.ac
    polly/trunk/lib/External/isl/depcomp
    polly/trunk/lib/External/isl/doc/Makefile.in
    polly/trunk/lib/External/isl/doc/user.pod
    polly/trunk/lib/External/isl/include/isl/aff.h
    polly/trunk/lib/External/isl/include/isl/map.h
    polly/trunk/lib/External/isl/include/isl/set.h
    polly/trunk/lib/External/isl/include/isl/val.h
    polly/trunk/lib/External/isl/include/isl/vec.h
    polly/trunk/lib/External/isl/isl_aff.c
    polly/trunk/lib/External/isl/isl_aff_private.h
    polly/trunk/lib/External/isl/isl_ast.c
    polly/trunk/lib/External/isl/isl_ast_build.c
    polly/trunk/lib/External/isl/isl_ast_build_expr.c
    polly/trunk/lib/External/isl/isl_ast_build_private.h
    polly/trunk/lib/External/isl/isl_ast_codegen.c
    polly/trunk/lib/External/isl/isl_ast_graft.c
    polly/trunk/lib/External/isl/isl_convex_hull.c
    polly/trunk/lib/External/isl/isl_fold.c
    polly/trunk/lib/External/isl/isl_id_to_ast_expr.c
    polly/trunk/lib/External/isl/isl_id_to_id.c
    polly/trunk/lib/External/isl/isl_id_to_pw_aff.c
    polly/trunk/lib/External/isl/isl_input.c
    polly/trunk/lib/External/isl/isl_local.c
    polly/trunk/lib/External/isl/isl_local.h
    polly/trunk/lib/External/isl/isl_local_space.c
    polly/trunk/lib/External/isl/isl_local_space_private.h
    polly/trunk/lib/External/isl/isl_map.c
    polly/trunk/lib/External/isl/isl_map_private.h
    polly/trunk/lib/External/isl/isl_multi_apply_templ.c
    polly/trunk/lib/External/isl/isl_multi_cmp.c
    polly/trunk/lib/External/isl/isl_multi_coalesce.c
    polly/trunk/lib/External/isl/isl_multi_dims.c
    polly/trunk/lib/External/isl/isl_multi_floor.c
    polly/trunk/lib/External/isl/isl_multi_hash.c
    polly/trunk/lib/External/isl/isl_multi_intersect.c
    polly/trunk/lib/External/isl/isl_multi_templ.c
    polly/trunk/lib/External/isl/isl_multi_templ.h
    polly/trunk/lib/External/isl/isl_output.c
    polly/trunk/lib/External/isl/isl_point.c
    polly/trunk/lib/External/isl/isl_point_private.h
    polly/trunk/lib/External/isl/isl_polynomial.c
    polly/trunk/lib/External/isl/isl_polynomial_private.h
    polly/trunk/lib/External/isl/isl_printer.c
    polly/trunk/lib/External/isl/isl_pw_templ.c
    polly/trunk/lib/External/isl/isl_reordering.c
    polly/trunk/lib/External/isl/isl_schedule.c
    polly/trunk/lib/External/isl/isl_schedule_node.c
    polly/trunk/lib/External/isl/isl_schedule_read.c
    polly/trunk/lib/External/isl/isl_schedule_tree.c
    polly/trunk/lib/External/isl/isl_scheduler.c
    polly/trunk/lib/External/isl/isl_space.c
    polly/trunk/lib/External/isl/isl_space_private.h
    polly/trunk/lib/External/isl/isl_stride.c
    polly/trunk/lib/External/isl/isl_tab_pip.c
    polly/trunk/lib/External/isl/isl_test.c
    polly/trunk/lib/External/isl/isl_union_eval.c
    polly/trunk/lib/External/isl/isl_union_map.c
    polly/trunk/lib/External/isl/isl_union_map_private.h
    polly/trunk/lib/External/isl/isl_union_templ.c
    polly/trunk/lib/External/isl/isl_val.c
    polly/trunk/lib/External/isl/isl_vec.c
    polly/trunk/lib/External/isl/ltmain.sh
    polly/trunk/lib/External/isl/test_inputs/codegen/shift2.c
    polly/trunk/lib/External/isl/test_inputs/codegen/stride7.c

Modified: polly/trunk/lib/External/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/CMakeLists.txt?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/CMakeLists.txt (original)
+++ polly/trunk/lib/External/CMakeLists.txt Sat Apr 21 01:34:22 2018
@@ -254,6 +254,10 @@ if (POLLY_BUNDLED_ISL)
     isl/isl_version.c
     isl/isl_vertices.c
     isl/print.c
+    isl/set_to_map.c
+    isl/set_from_map.c
+    isl/uset_to_umap.c
+    isl/uset_from_umap.c
     isl/imath/gmp_compat.c
     isl/imath/imath.c
     isl/imath/imrat.c

Modified: polly/trunk/lib/External/isl/AUTHORS
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/AUTHORS?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/AUTHORS (original)
+++ polly/trunk/lib/External/isl/AUTHORS Sat Apr 21 01:34:22 2018
@@ -30,17 +30,22 @@ Contributions by
 Mythri Alle
 Riyadh Baghdadi
 Serge Belyshev
+Albert Cohen
 Ray Donnelly
 Johannes Doerfert
+Armin Groesslinger
 Tobias Grosser
 Alexandre Isoard
 Andreas Kloeckner
 Michael Kruse
+Alexander Matz
 Sebastian Pop
 Louis-Noel Pouchet
 Benoit Pradelle
 Uday Kumar Reddy
 Andreas Simbuerger
+Malhar Thakkar
 Sven van Haastregt
+Oleksandr Zinenko
 
 The merge sort implementation was written by Jeffrey Stedfast.

Modified: polly/trunk/lib/External/isl/ChangeLog
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/ChangeLog?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/ChangeLog (original)
+++ polly/trunk/lib/External/isl/ChangeLog Sat Apr 21 01:34:22 2018
@@ -1,3 +1,14 @@
+version: 0.19
+date: Sat Mar  3 10:44:49 CET 2018
+changes:
+	- minor improvements to coalescing
+	- minor improvement to parametric integer programming
+	- try harder to avoid large coefficients in scheduler
+	- support kill accesses in dependence analysis
+	- drop deprecated isl_int
+	- drop deprecated band forests
+	- drop deprecated functions
+---
 version: 0.18
 date: Sun Dec 18 11:01:58 CET 2016
 changes:

Modified: polly/trunk/lib/External/isl/GIT_HEAD_ID
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/GIT_HEAD_ID?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/GIT_HEAD_ID (original)
+++ polly/trunk/lib/External/isl/GIT_HEAD_ID Sat Apr 21 01:34:22 2018
@@ -1 +1 @@
-isl-0.18-1047-g4a20ef8
+isl-0.19-107-gc4fe33d8

Modified: polly/trunk/lib/External/isl/Makefile.am
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/Makefile.am?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/Makefile.am (original)
+++ polly/trunk/lib/External/isl/Makefile.am Sat Apr 21 01:34:22 2018
@@ -311,6 +311,7 @@ pkginclude_HEADERS = \
 	include/isl/set_type.h \
 	include/isl/space.h \
 	include/isl/stream.h \
+	include/isl/stride_info.h \
 	include/isl/union_map.h \
 	include/isl/union_map_type.h \
 	include/isl/union_set.h \
@@ -344,8 +345,15 @@ EXTRA_DIST = \
 	isl_map_lexopt_templ.c \
 	isl_maybe_map.h \
 	isl_multi_macro.h \
+	isl_multi_explicit_domain.c \
+	isl_multi_pw_aff_explicit_domain.c \
+	isl_multi_union_pw_aff_explicit_domain.c \
+	isl_multi_no_explicit_domain.c \
 	isl_multi_templ.c \
 	isl_multi_templ.h \
+	isl_multi_align_templ.c \
+	isl_multi_align_set.c \
+	isl_multi_align_union_set.c \
 	isl_multi_apply_templ.c \
 	isl_multi_apply_set.c \
 	isl_multi_apply_union_set.c \
@@ -361,6 +369,8 @@ EXTRA_DIST = \
 	isl_power_templ.c \
 	isl_pw_macro.h \
 	isl_pw_templ.c \
+	isl_pw_templ.h \
+	isl_pw_eval.c \
 	isl_pw_hash.c \
 	isl_pw_union_opt.c \
 	read_in_string_templ.c \
@@ -368,6 +378,7 @@ EXTRA_DIST = \
 	set_from_map.c \
 	isl_tab_lexopt_templ.c \
 	uset_to_umap.c \
+	uset_from_umap.c \
 	isl_union_macro.h \
 	isl_union_templ.c \
 	isl_union_single.c \

Modified: polly/trunk/lib/External/isl/Makefile.in
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/Makefile.in?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/Makefile.in (original)
+++ polly/trunk/lib/External/isl/Makefile.in Sat Apr 21 01:34:22 2018
@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.15 from Makefile.am.
+# Makefile.in generated by automake 1.15.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2014 Free Software Foundation, Inc.
+# Copyright (C) 1994-2017 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -433,10 +433,11 @@ am__pkginclude_HEADERS_DIST = include/is
 	include/isl/schedule.h include/isl/schedule_node.h \
 	include/isl/schedule_type.h include/isl/set.h \
 	include/isl/set_type.h include/isl/space.h \
-	include/isl/stream.h include/isl/union_map.h \
-	include/isl/union_map_type.h include/isl/union_set.h \
-	include/isl/union_set_type.h include/isl/val.h \
-	include/isl/vec.h include/isl/version.h include/isl/vertices.h
+	include/isl/stream.h include/isl/stride_info.h \
+	include/isl/union_map.h include/isl/union_map_type.h \
+	include/isl/union_set.h include/isl/union_set_type.h \
+	include/isl/val.h include/isl/vec.h include/isl/version.h \
+	include/isl/vertices.h
 HEADERS = $(nodist_pkginclude_HEADERS) $(pkginclude_HEADERS)
 RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive	\
   distclean-recursive maintainer-clean-recursive
@@ -1110,6 +1111,7 @@ pkginclude_HEADERS = \
 	include/isl/set_type.h \
 	include/isl/space.h \
 	include/isl/stream.h \
+	include/isl/stride_info.h \
 	include/isl/union_map.h \
 	include/isl/union_map_type.h \
 	include/isl/union_set.h \
@@ -1142,8 +1144,15 @@ EXTRA_DIST = \
 	isl_map_lexopt_templ.c \
 	isl_maybe_map.h \
 	isl_multi_macro.h \
+	isl_multi_explicit_domain.c \
+	isl_multi_pw_aff_explicit_domain.c \
+	isl_multi_union_pw_aff_explicit_domain.c \
+	isl_multi_no_explicit_domain.c \
 	isl_multi_templ.c \
 	isl_multi_templ.h \
+	isl_multi_align_templ.c \
+	isl_multi_align_set.c \
+	isl_multi_align_union_set.c \
 	isl_multi_apply_templ.c \
 	isl_multi_apply_set.c \
 	isl_multi_apply_union_set.c \
@@ -1159,6 +1168,8 @@ EXTRA_DIST = \
 	isl_power_templ.c \
 	isl_pw_macro.h \
 	isl_pw_templ.c \
+	isl_pw_templ.h \
+	isl_pw_eval.c \
 	isl_pw_hash.c \
 	isl_pw_union_opt.c \
 	read_in_string_templ.c \
@@ -1166,6 +1177,7 @@ EXTRA_DIST = \
 	set_from_map.c \
 	isl_tab_lexopt_templ.c \
 	uset_to_umap.c \
+	uset_from_umap.c \
 	isl_union_macro.h \
 	isl_union_templ.c \
 	isl_union_single.c \
@@ -1975,7 +1987,7 @@ distdir: $(DISTFILES)
 	  ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \
 	|| chmod -R a+r "$(distdir)"
 dist-gzip: distdir
-	tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz
+	tardir=$(distdir) && $(am__tar) | eval GZIP= gzip $(GZIP_ENV) -c >$(distdir).tar.gz
 	$(am__post_remove_distdir)
 
 dist-bzip2: distdir
@@ -2001,7 +2013,7 @@ dist-shar: distdir
 	@echo WARNING: "Support for shar distribution archives is" \
 	               "deprecated." >&2
 	@echo WARNING: "It will be removed altogether in Automake 2.0" >&2
-	shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz
+	shar $(distdir) | eval GZIP= gzip $(GZIP_ENV) -c >$(distdir).shar.gz
 	$(am__post_remove_distdir)
 
 dist-zip: distdir
@@ -2019,7 +2031,7 @@ dist dist-all:
 distcheck: dist
 	case '$(DIST_ARCHIVES)' in \
 	*.tar.gz*) \
-	  GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\
+	  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).tar.gz | $(am__untar) ;;\
 	*.tar.bz2*) \
 	  bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\
 	*.tar.lz*) \
@@ -2029,7 +2041,7 @@ distcheck: dist
 	*.tar.Z*) \
 	  uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
 	*.shar.gz*) \
-	  GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\
+	  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).shar.gz | unshar ;;\
 	*.zip*) \
 	  unzip $(distdir).zip ;;\
 	esac

Modified: polly/trunk/lib/External/isl/aclocal.m4
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/aclocal.m4?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/aclocal.m4 (original)
+++ polly/trunk/lib/External/isl/aclocal.m4 Sat Apr 21 01:34:22 2018
@@ -1,6 +1,6 @@
-# generated automatically by aclocal 1.15 -*- Autoconf -*-
+# generated automatically by aclocal 1.15.1 -*- Autoconf -*-
 
-# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+# Copyright (C) 1996-2017 Free Software Foundation, Inc.
 
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -20,7 +20,7 @@ You have another version of autoconf.  I
 If you have problems, you may need to regenerate the build system entirely.
 To do so, use the procedure documented by the package, typically 'autoreconf'.])])
 
-# Copyright (C) 2002-2014 Free Software Foundation, Inc.
+# Copyright (C) 2002-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -35,7 +35,7 @@ AC_DEFUN([AM_AUTOMAKE_VERSION],
 [am__api_version='1.15'
 dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
 dnl require some minimum version.  Point them to the right macro.
-m4_if([$1], [1.15], [],
+m4_if([$1], [1.15.1], [],
       [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
 ])
 
@@ -51,14 +51,14 @@ m4_define([_AM_AUTOCONF_VERSION], [])
 # Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
 # This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
 AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
-[AM_AUTOMAKE_VERSION([1.15])dnl
+[AM_AUTOMAKE_VERSION([1.15.1])dnl
 m4_ifndef([AC_AUTOCONF_VERSION],
   [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
 _AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])
 
 # AM_AUX_DIR_EXPAND                                         -*- Autoconf -*-
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -110,7 +110,7 @@ am_aux_dir=`cd "$ac_aux_dir" && pwd`
 
 # AM_CONDITIONAL                                            -*- Autoconf -*-
 
-# Copyright (C) 1997-2014 Free Software Foundation, Inc.
+# Copyright (C) 1997-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -141,7 +141,7 @@ AC_CONFIG_COMMANDS_PRE(
 Usually this means the macro was only invoked conditionally.]])
 fi])])
 
-# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Copyright (C) 1999-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -332,7 +332,7 @@ _AM_SUBST_NOTMAKE([am__nodep])dnl
 
 # Generate code to set up dependency tracking.              -*- Autoconf -*-
 
-# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Copyright (C) 1999-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -408,7 +408,7 @@ AC_DEFUN([AM_OUTPUT_DEPENDENCY_COMMANDS]
 
 # Do all the work for Automake.                             -*- Autoconf -*-
 
-# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+# Copyright (C) 1996-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -605,7 +605,7 @@ for _am_header in $config_headers :; do
 done
 echo "timestamp for $_am_arg" >`AS_DIRNAME(["$_am_arg"])`/stamp-h[]$_am_stamp_count])
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -626,7 +626,7 @@ if test x"${install_sh+set}" != xset; th
 fi
 AC_SUBST([install_sh])])
 
-# Copyright (C) 2003-2014 Free Software Foundation, Inc.
+# Copyright (C) 2003-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -647,7 +647,7 @@ AC_SUBST([am__leading_dot])])
 
 # Check to see how 'make' treats includes.	            -*- Autoconf -*-
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -697,7 +697,7 @@ rm -f confinc confmf
 
 # Fake the existence of programs that GNU maintainers use.  -*- Autoconf -*-
 
-# Copyright (C) 1997-2014 Free Software Foundation, Inc.
+# Copyright (C) 1997-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -736,7 +736,7 @@ fi
 
 # Helper functions for option handling.                     -*- Autoconf -*-
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -765,7 +765,7 @@ AC_DEFUN([_AM_SET_OPTIONS],
 AC_DEFUN([_AM_IF_OPTION],
 [m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])])
 
-# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Copyright (C) 1999-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -812,7 +812,7 @@ AC_LANG_POP([C])])
 # For backward compatibility.
 AC_DEFUN_ONCE([AM_PROG_CC_C_O], [AC_REQUIRE([AC_PROG_CC])])
 
-# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Copyright (C) 1999-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -845,8 +845,9 @@ AC_DEFUN([AM_PATH_PYTHON],
  [
   dnl Find a Python interpreter.  Python versions prior to 2.0 are not
   dnl supported. (2.0 was released on October 16, 2000).
+  dnl FIXME: Remove the need to hard-code Python versions here.
   m4_define_default([_AM_PYTHON_INTERPRETER_LIST],
-[python python2 python3 python3.3 python3.2 python3.1 python3.0 python2.7 dnl
+[python python2 python3 python3.8 python3.7 python3.6 python3.5 python3.4 python3.3 python3.2 python3.1 python3.0 python2.7 dnl
  python2.6 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0])
 
   AC_ARG_VAR([PYTHON], [the Python interpreter])
@@ -1047,7 +1048,7 @@ for i in list(range(0, 4)): minverhex =
 sys.exit(sys.hexversion < minverhex)"
   AS_IF([AM_RUN_LOG([$1 -c "$prog"])], [$3], [$4])])
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1066,7 +1067,7 @@ AC_DEFUN([AM_RUN_LOG],
 
 # Check to make sure that the build environment is sane.    -*- Autoconf -*-
 
-# Copyright (C) 1996-2014 Free Software Foundation, Inc.
+# Copyright (C) 1996-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1147,7 +1148,7 @@ AC_CONFIG_COMMANDS_PRE(
 rm -f conftest.file
 ])
 
-# Copyright (C) 2009-2014 Free Software Foundation, Inc.
+# Copyright (C) 2009-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1207,7 +1208,7 @@ AC_SUBST([AM_BACKSLASH])dnl
 _AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl
 ])
 
-# Copyright (C) 2001-2014 Free Software Foundation, Inc.
+# Copyright (C) 2001-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1235,7 +1236,7 @@ fi
 INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s"
 AC_SUBST([INSTALL_STRIP_PROGRAM])])
 
-# Copyright (C) 2006-2014 Free Software Foundation, Inc.
+# Copyright (C) 2006-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,
@@ -1254,7 +1255,7 @@ AC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_
 
 # Check how to create a tarball.                            -*- Autoconf -*-
 
-# Copyright (C) 2004-2014 Free Software Foundation, Inc.
+# Copyright (C) 2004-2017 Free Software Foundation, Inc.
 #
 # This file is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,

Modified: polly/trunk/lib/External/isl/config.guess
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/config.guess?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/config.guess (original)
+++ polly/trunk/lib/External/isl/config.guess Sat Apr 21 01:34:22 2018
@@ -1,8 +1,8 @@
 #! /bin/sh
 # Attempt to guess a canonical system name.
-#   Copyright 1992-2016 Free Software Foundation, Inc.
+#   Copyright 1992-2018 Free Software Foundation, Inc.
 
-timestamp='2016-04-02'
+timestamp='2018-02-24'
 
 # This file is free software; you can redistribute it and/or modify it
 # under the terms of the GNU General Public License as published by
@@ -15,7 +15,7 @@ timestamp='2016-04-02'
 # General Public License for more details.
 #
 # You should have received a copy of the GNU General Public License
-# along with this program; if not, see <http://www.gnu.org/licenses/>.
+# along with this program; if not, see <https://www.gnu.org/licenses/>.
 #
 # As a special exception to the GNU General Public License, if you
 # distribute this file as part of a program that contains a
@@ -27,7 +27,7 @@ timestamp='2016-04-02'
 # Originally written by Per Bothner; maintained since 2000 by Ben Elliston.
 #
 # You can get the latest version of this script from:
-# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess
+# https://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess
 #
 # Please send patches to <config-patches at gnu.org>.
 
@@ -39,7 +39,7 @@ Usage: $0 [OPTION]
 
 Output the configuration name of the system \`$me' is run on.
 
-Operation modes:
+Options:
   -h, --help         print this help, then exit
   -t, --time-stamp   print date of last modification, then exit
   -v, --version      print version number, then exit
@@ -50,7 +50,7 @@ version="\
 GNU config.guess ($timestamp)
 
 Originally written by Per Bothner.
-Copyright 1992-2016 Free Software Foundation, Inc.
+Copyright 1992-2018 Free Software Foundation, Inc.
 
 This is free software; see the source for copying conditions.  There is NO
 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -107,9 +107,9 @@ trap "rm -f \$tmpfiles 2>/dev/null; rmdi
 dummy=$tmp/dummy ;
 tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ;
 case $CC_FOR_BUILD,$HOST_CC,$CC in
- ,,)    echo "int x;" > $dummy.c ;
+ ,,)    echo "int x;" > "$dummy.c" ;
 	for c in cc gcc c89 c99 ; do
-	  if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then
+	  if ($c -c -o "$dummy.o" "$dummy.c") >/dev/null 2>&1 ; then
 	     CC_FOR_BUILD="$c"; break ;
 	  fi ;
 	done ;
@@ -132,14 +132,14 @@ UNAME_RELEASE=`(uname -r) 2>/dev/null` |
 UNAME_SYSTEM=`(uname -s) 2>/dev/null`  || UNAME_SYSTEM=unknown
 UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
 
-case "${UNAME_SYSTEM}" in
+case "$UNAME_SYSTEM" in
 Linux|GNU|GNU/*)
 	# If the system lacks a compiler, then just pick glibc.
 	# We could probably try harder.
 	LIBC=gnu
 
-	eval $set_cc_for_build
-	cat <<-EOF > $dummy.c
+	eval "$set_cc_for_build"
+	cat <<-EOF > "$dummy.c"
 	#include <features.h>
 	#if defined(__UCLIBC__)
 	LIBC=uclibc
@@ -149,13 +149,20 @@ Linux|GNU|GNU/*)
 	LIBC=gnu
 	#endif
 	EOF
-	eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC' | sed 's, ,,g'`
+	eval "`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^LIBC' | sed 's, ,,g'`"
+
+	# If ldd exists, use it to detect musl libc.
+	if command -v ldd >/dev/null && \
+		ldd --version 2>&1 | grep -q ^musl
+	then
+	    LIBC=musl
+	fi
 	;;
 esac
 
 # Note: order is significant - the case branches are not exclusive.
 
-case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
+case "$UNAME_MACHINE:$UNAME_SYSTEM:$UNAME_RELEASE:$UNAME_VERSION" in
     *:NetBSD:*:*)
 	# NetBSD (nbsd) targets should (where applicable) match one or
 	# more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*,
@@ -169,27 +176,30 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 	# portion of the name.  We always set it to "unknown".
 	sysctl="sysctl -n hw.machine_arch"
 	UNAME_MACHINE_ARCH=`(uname -p 2>/dev/null || \
-	    /sbin/$sysctl 2>/dev/null || \
-	    /usr/sbin/$sysctl 2>/dev/null || \
+	    "/sbin/$sysctl" 2>/dev/null || \
+	    "/usr/sbin/$sysctl" 2>/dev/null || \
 	    echo unknown)`
-	case "${UNAME_MACHINE_ARCH}" in
+	case "$UNAME_MACHINE_ARCH" in
 	    armeb) machine=armeb-unknown ;;
 	    arm*) machine=arm-unknown ;;
 	    sh3el) machine=shl-unknown ;;
 	    sh3eb) machine=sh-unknown ;;
 	    sh5el) machine=sh5le-unknown ;;
 	    earmv*)
-		arch=`echo ${UNAME_MACHINE_ARCH} | sed -e 's,^e\(armv[0-9]\).*$,\1,'`
-		endian=`echo ${UNAME_MACHINE_ARCH} | sed -ne 's,^.*\(eb\)$,\1,p'`
-		machine=${arch}${endian}-unknown
+		arch=`echo "$UNAME_MACHINE_ARCH" | sed -e 's,^e\(armv[0-9]\).*$,\1,'`
+		endian=`echo "$UNAME_MACHINE_ARCH" | sed -ne 's,^.*\(eb\)$,\1,p'`
+		machine="${arch}${endian}"-unknown
 		;;
-	    *) machine=${UNAME_MACHINE_ARCH}-unknown ;;
+	    *) machine="$UNAME_MACHINE_ARCH"-unknown ;;
 	esac
 	# The Operating System including object format, if it has switched
-	# to ELF recently, or will in the future.
-	case "${UNAME_MACHINE_ARCH}" in
-	    arm*|earm*|i386|m68k|ns32k|sh3*|sparc|vax)
-		eval $set_cc_for_build
+	# to ELF recently (or will in the future) and ABI.
+	case "$UNAME_MACHINE_ARCH" in
+	    earm*)
+		os=netbsdelf
+		;;
+	    arm*|i386|m68k|ns32k|sh3*|sparc|vax)
+		eval "$set_cc_for_build"
 		if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \
 			| grep -q __ELF__
 		then
@@ -205,10 +215,10 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 		;;
 	esac
 	# Determine ABI tags.
-	case "${UNAME_MACHINE_ARCH}" in
+	case "$UNAME_MACHINE_ARCH" in
 	    earm*)
 		expr='s/^earmv[0-9]/-eabi/;s/eb$//'
-		abi=`echo ${UNAME_MACHINE_ARCH} | sed -e "$expr"`
+		abi=`echo "$UNAME_MACHINE_ARCH" | sed -e "$expr"`
 		;;
 	esac
 	# The OS release
@@ -216,46 +226,55 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 	# thus, need a distinct triplet. However, they do not need
 	# kernel version information, so it can be replaced with a
 	# suitable tag, in the style of linux-gnu.
-	case "${UNAME_VERSION}" in
+	case "$UNAME_VERSION" in
 	    Debian*)
 		release='-gnu'
 		;;
 	    *)
-		release=`echo ${UNAME_RELEASE} | sed -e 's/[-_].*//' | cut -d. -f1,2`
+		release=`echo "$UNAME_RELEASE" | sed -e 's/[-_].*//' | cut -d. -f1,2`
 		;;
 	esac
 	# Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:
 	# contains redundant information, the shorter form:
 	# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
-	echo "${machine}-${os}${release}${abi}"
+	echo "$machine-${os}${release}${abi}"
 	exit ;;
     *:Bitrig:*:*)
 	UNAME_MACHINE_ARCH=`arch | sed 's/Bitrig.//'`
-	echo ${UNAME_MACHINE_ARCH}-unknown-bitrig${UNAME_RELEASE}
+	echo "$UNAME_MACHINE_ARCH"-unknown-bitrig"$UNAME_RELEASE"
 	exit ;;
     *:OpenBSD:*:*)
 	UNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'`
-	echo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE}
+	echo "$UNAME_MACHINE_ARCH"-unknown-openbsd"$UNAME_RELEASE"
 	exit ;;
     *:LibertyBSD:*:*)
 	UNAME_MACHINE_ARCH=`arch | sed 's/^.*BSD\.//'`
-	echo ${UNAME_MACHINE_ARCH}-unknown-libertybsd${UNAME_RELEASE}
+	echo "$UNAME_MACHINE_ARCH"-unknown-libertybsd"$UNAME_RELEASE"
+	exit ;;
+    *:MidnightBSD:*:*)
+	echo "$UNAME_MACHINE"-unknown-midnightbsd"$UNAME_RELEASE"
 	exit ;;
     *:ekkoBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-ekkobsd${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-unknown-ekkobsd"$UNAME_RELEASE"
 	exit ;;
     *:SolidBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-solidbsd${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-unknown-solidbsd"$UNAME_RELEASE"
 	exit ;;
     macppc:MirBSD:*:*)
-	echo powerpc-unknown-mirbsd${UNAME_RELEASE}
+	echo powerpc-unknown-mirbsd"$UNAME_RELEASE"
 	exit ;;
     *:MirBSD:*:*)
-	echo ${UNAME_MACHINE}-unknown-mirbsd${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-unknown-mirbsd"$UNAME_RELEASE"
 	exit ;;
     *:Sortix:*:*)
-	echo ${UNAME_MACHINE}-unknown-sortix
+	echo "$UNAME_MACHINE"-unknown-sortix
 	exit ;;
+    *:Redox:*:*)
+	echo "$UNAME_MACHINE"-unknown-redox
+	exit ;;
+    mips:OSF1:*.*)
+        echo mips-dec-osf1
+        exit ;;
     alpha:OSF1:*:*)
 	case $UNAME_RELEASE in
 	*4.0)
@@ -307,28 +326,19 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 	# A Tn.n version is a released field test version.
 	# A Xn.n version is an unreleased experimental baselevel.
 	# 1.2 uses "1.2" for uname -r.
-	echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz`
+	echo "$UNAME_MACHINE"-dec-osf"`echo "$UNAME_RELEASE" | sed -e 's/^[PVTX]//' | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz`"
 	# Reset EXIT trap before exiting to avoid spurious non-zero exit code.
 	exitcode=$?
 	trap '' 0
 	exit $exitcode ;;
-    Alpha\ *:Windows_NT*:*)
-	# How do we know it's Interix rather than the generic POSIX subsystem?
-	# Should we change UNAME_MACHINE based on the output of uname instead
-	# of the specific Alpha model?
-	echo alpha-pc-interix
-	exit ;;
-    21064:Windows_NT:50:3)
-	echo alpha-dec-winnt3.5
-	exit ;;
     Amiga*:UNIX_System_V:4.0:*)
 	echo m68k-unknown-sysv4
 	exit ;;
     *:[Aa]miga[Oo][Ss]:*:*)
-	echo ${UNAME_MACHINE}-unknown-amigaos
+	echo "$UNAME_MACHINE"-unknown-amigaos
 	exit ;;
     *:[Mm]orph[Oo][Ss]:*:*)
-	echo ${UNAME_MACHINE}-unknown-morphos
+	echo "$UNAME_MACHINE"-unknown-morphos
 	exit ;;
     *:OS/390:*:*)
 	echo i370-ibm-openedition
@@ -340,7 +350,7 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 	echo powerpc-ibm-os400
 	exit ;;
     arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
-	echo arm-acorn-riscix${UNAME_RELEASE}
+	echo arm-acorn-riscix"$UNAME_RELEASE"
 	exit ;;
     arm*:riscos:*:*|arm*:RISCOS:*:*)
 	echo arm-unknown-riscos
@@ -367,19 +377,19 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 	    sparc) echo sparc-icl-nx7; exit ;;
 	esac ;;
     s390x:SunOS:*:*)
-	echo ${UNAME_MACHINE}-ibm-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo "$UNAME_MACHINE"-ibm-solaris2"`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'`"
 	exit ;;
     sun4H:SunOS:5.*:*)
-	echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo sparc-hal-solaris2"`echo "$UNAME_RELEASE"|sed -e 's/[^.]*//'`"
 	exit ;;
     sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)
-	echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo sparc-sun-solaris2"`echo "$UNAME_RELEASE" | sed -e 's/[^.]*//'`"
 	exit ;;
     i86pc:AuroraUX:5.*:* | i86xen:AuroraUX:5.*:*)
-	echo i386-pc-auroraux${UNAME_RELEASE}
+	echo i386-pc-auroraux"$UNAME_RELEASE"
 	exit ;;
     i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*)
-	eval $set_cc_for_build
+	eval "$set_cc_for_build"
 	SUN_ARCH=i386
 	# If there is a compiler, see if it is configured for 64-bit objects.
 	# Note that the Sun cc does not turn __LP64__ into 1 like gcc does.
@@ -392,13 +402,13 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 		SUN_ARCH=x86_64
 	    fi
 	fi
-	echo ${SUN_ARCH}-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo "$SUN_ARCH"-pc-solaris2"`echo "$UNAME_RELEASE"|sed -e 's/[^.]*//'`"
 	exit ;;
     sun4*:SunOS:6*:*)
 	# According to config.sub, this is the proper way to canonicalize
 	# SunOS6.  Hard to guess exactly what SunOS6 will be like, but
 	# it's likely to be more like Solaris than SunOS4.
-	echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo sparc-sun-solaris3"`echo "$UNAME_RELEASE"|sed -e 's/[^.]*//'`"
 	exit ;;
     sun4*:SunOS:*:*)
 	case "`/usr/bin/arch -k`" in
@@ -407,25 +417,25 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 		;;
 	esac
 	# Japanese Language versions have a version number like `4.1.3-JL'.
-	echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'`
+	echo sparc-sun-sunos"`echo "$UNAME_RELEASE"|sed -e 's/-/_/'`"
 	exit ;;
     sun3*:SunOS:*:*)
-	echo m68k-sun-sunos${UNAME_RELEASE}
+	echo m68k-sun-sunos"$UNAME_RELEASE"
 	exit ;;
     sun*:*:4.2BSD:*)
 	UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
-	test "x${UNAME_RELEASE}" = x && UNAME_RELEASE=3
+	test "x$UNAME_RELEASE" = x && UNAME_RELEASE=3
 	case "`/bin/arch`" in
 	    sun3)
-		echo m68k-sun-sunos${UNAME_RELEASE}
+		echo m68k-sun-sunos"$UNAME_RELEASE"
 		;;
 	    sun4)
-		echo sparc-sun-sunos${UNAME_RELEASE}
+		echo sparc-sun-sunos"$UNAME_RELEASE"
 		;;
 	esac
 	exit ;;
     aushp:SunOS:*:*)
-	echo sparc-auspex-sunos${UNAME_RELEASE}
+	echo sparc-auspex-sunos"$UNAME_RELEASE"
 	exit ;;
     # The situation for MiNT is a little confusing.  The machine name
     # can be virtually everything (everything which is not
@@ -436,44 +446,44 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
     # MiNT.  But MiNT is downward compatible to TOS, so this should
     # be no problem.
     atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)
-	echo m68k-atari-mint${UNAME_RELEASE}
+	echo m68k-atari-mint"$UNAME_RELEASE"
 	exit ;;
     atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)
-	echo m68k-atari-mint${UNAME_RELEASE}
+	echo m68k-atari-mint"$UNAME_RELEASE"
 	exit ;;
     *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)
-	echo m68k-atari-mint${UNAME_RELEASE}
+	echo m68k-atari-mint"$UNAME_RELEASE"
 	exit ;;
     milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)
-	echo m68k-milan-mint${UNAME_RELEASE}
+	echo m68k-milan-mint"$UNAME_RELEASE"
 	exit ;;
     hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)
-	echo m68k-hades-mint${UNAME_RELEASE}
+	echo m68k-hades-mint"$UNAME_RELEASE"
 	exit ;;
     *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
-	echo m68k-unknown-mint${UNAME_RELEASE}
+	echo m68k-unknown-mint"$UNAME_RELEASE"
 	exit ;;
     m68k:machten:*:*)
-	echo m68k-apple-machten${UNAME_RELEASE}
+	echo m68k-apple-machten"$UNAME_RELEASE"
 	exit ;;
     powerpc:machten:*:*)
-	echo powerpc-apple-machten${UNAME_RELEASE}
+	echo powerpc-apple-machten"$UNAME_RELEASE"
 	exit ;;
     RISC*:Mach:*:*)
 	echo mips-dec-mach_bsd4.3
 	exit ;;
     RISC*:ULTRIX:*:*)
-	echo mips-dec-ultrix${UNAME_RELEASE}
+	echo mips-dec-ultrix"$UNAME_RELEASE"
 	exit ;;
     VAX*:ULTRIX*:*:*)
-	echo vax-dec-ultrix${UNAME_RELEASE}
+	echo vax-dec-ultrix"$UNAME_RELEASE"
 	exit ;;
     2020:CLIX:*:* | 2430:CLIX:*:*)
-	echo clipper-intergraph-clix${UNAME_RELEASE}
+	echo clipper-intergraph-clix"$UNAME_RELEASE"
 	exit ;;
     mips:*:*:UMIPS | mips:*:*:RISCos)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
+	eval "$set_cc_for_build"
+	sed 's/^	//' << EOF > "$dummy.c"
 #ifdef __cplusplus
 #include <stdio.h>  /* for printf() prototype */
 	int main (int argc, char *argv[]) {
@@ -482,23 +492,23 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:$
 #endif
 	#if defined (host_mips) && defined (MIPSEB)
 	#if defined (SYSTYPE_SYSV)
-	  printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0);
+	  printf ("mips-mips-riscos%ssysv\\n", argv[1]); exit (0);
 	#endif
 	#if defined (SYSTYPE_SVR4)
-	  printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0);
+	  printf ("mips-mips-riscos%ssvr4\\n", argv[1]); exit (0);
 	#endif
 	#if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD)
-	  printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0);
+	  printf ("mips-mips-riscos%sbsd\\n", argv[1]); exit (0);
 	#endif
 	#endif
 	  exit (-1);
 	}
 EOF
-	$CC_FOR_BUILD -o $dummy $dummy.c &&
-	  dummyarg=`echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` &&
-	  SYSTEM_NAME=`$dummy $dummyarg` &&
+	$CC_FOR_BUILD -o "$dummy" "$dummy.c" &&
+	  dummyarg=`echo "$UNAME_RELEASE" | sed -n 's/\([0-9]*\).*/\1/p'` &&
+	  SYSTEM_NAME=`"$dummy" "$dummyarg"` &&
 	    { echo "$SYSTEM_NAME"; exit; }
-	echo mips-mips-riscos${UNAME_RELEASE}
+	echo mips-mips-riscos"$UNAME_RELEASE"
 	exit ;;
     Motorola:PowerMAX_OS:*:*)
 	echo powerpc-motorola-powermax
@@ -524,17 +534,17 @@ EOF
     AViiON:dgux:*:*)
 	# DG/UX returns AViiON for all architectures
 	UNAME_PROCESSOR=`/usr/bin/uname -p`
-	if [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]
+	if [ "$UNAME_PROCESSOR" = mc88100 ] || [ "$UNAME_PROCESSOR" = mc88110 ]
 	then
-	    if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \
-	       [ ${TARGET_BINARY_INTERFACE}x = x ]
+	    if [ "$TARGET_BINARY_INTERFACE"x = m88kdguxelfx ] || \
+	       [ "$TARGET_BINARY_INTERFACE"x = x ]
 	    then
-		echo m88k-dg-dgux${UNAME_RELEASE}
+		echo m88k-dg-dgux"$UNAME_RELEASE"
 	    else
-		echo m88k-dg-dguxbcs${UNAME_RELEASE}
+		echo m88k-dg-dguxbcs"$UNAME_RELEASE"
 	    fi
 	else
-	    echo i586-dg-dgux${UNAME_RELEASE}
+	    echo i586-dg-dgux"$UNAME_RELEASE"
 	fi
 	exit ;;
     M88*:DolphinOS:*:*)	# DolphinOS (SVR3)
@@ -551,7 +561,7 @@ EOF
 	echo m68k-tektronix-bsd
 	exit ;;
     *:IRIX*:*:*)
-	echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'`
+	echo mips-sgi-irix"`echo "$UNAME_RELEASE"|sed -e 's/-/_/g'`"
 	exit ;;
     ????????:AIX?:[12].1:2)   # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.
 	echo romp-ibm-aix     # uname -m gives an 8 hex-code CPU id
@@ -563,14 +573,14 @@ EOF
 	if [ -x /usr/bin/oslevel ] ; then
 		IBM_REV=`/usr/bin/oslevel`
 	else
-		IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+		IBM_REV="$UNAME_VERSION.$UNAME_RELEASE"
 	fi
-	echo ${UNAME_MACHINE}-ibm-aix${IBM_REV}
+	echo "$UNAME_MACHINE"-ibm-aix"$IBM_REV"
 	exit ;;
     *:AIX:2:3)
 	if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then
-		eval $set_cc_for_build
-		sed 's/^		//' << EOF >$dummy.c
+		eval "$set_cc_for_build"
+		sed 's/^		//' << EOF > "$dummy.c"
 		#include <sys/systemcfg.h>
 
 		main()
@@ -581,7 +591,7 @@ EOF
 			exit(0);
 			}
 EOF
-		if $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy`
+		if $CC_FOR_BUILD -o "$dummy" "$dummy.c" && SYSTEM_NAME=`"$dummy"`
 		then
 			echo "$SYSTEM_NAME"
 		else
@@ -595,7 +605,7 @@ EOF
 	exit ;;
     *:AIX:*:[4567])
 	IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
-	if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
+	if /usr/sbin/lsattr -El "$IBM_CPU_ID" | grep ' POWER' >/dev/null 2>&1; then
 		IBM_ARCH=rs6000
 	else
 		IBM_ARCH=powerpc
@@ -604,18 +614,18 @@ EOF
 		IBM_REV=`/usr/bin/lslpp -Lqc bos.rte.libc |
 			   awk -F: '{ print $3 }' | sed s/[0-9]*$/0/`
 	else
-		IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+		IBM_REV="$UNAME_VERSION.$UNAME_RELEASE"
 	fi
-	echo ${IBM_ARCH}-ibm-aix${IBM_REV}
+	echo "$IBM_ARCH"-ibm-aix"$IBM_REV"
 	exit ;;
     *:AIX:*:*)
 	echo rs6000-ibm-aix
 	exit ;;
-    ibmrt:4.4BSD:*|romp-ibm:BSD:*)
+    ibmrt:4.4BSD:*|romp-ibm:4.4BSD:*)
 	echo romp-ibm-bsd4.4
 	exit ;;
     ibmrt:*BSD:*|romp-ibm:BSD:*)            # covers RT/PC BSD and
-	echo romp-ibm-bsd${UNAME_RELEASE}   # 4.3 with uname added to
+	echo romp-ibm-bsd"$UNAME_RELEASE"   # 4.3 with uname added to
 	exit ;;                             # report: romp-ibm BSD 4.3
     *:BOSX:*:*)
 	echo rs6000-bull-bosx
@@ -630,28 +640,28 @@ EOF
 	echo m68k-hp-bsd4.4
 	exit ;;
     9000/[34678]??:HP-UX:*:*)
-	HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
-	case "${UNAME_MACHINE}" in
-	    9000/31? )            HP_ARCH=m68000 ;;
-	    9000/[34]?? )         HP_ARCH=m68k ;;
+	HPUX_REV=`echo "$UNAME_RELEASE"|sed -e 's/[^.]*.[0B]*//'`
+	case "$UNAME_MACHINE" in
+	    9000/31?)            HP_ARCH=m68000 ;;
+	    9000/[34]??)         HP_ARCH=m68k ;;
 	    9000/[678][0-9][0-9])
 		if [ -x /usr/bin/getconf ]; then
 		    sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
 		    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
-		    case "${sc_cpu_version}" in
+		    case "$sc_cpu_version" in
 		      523) HP_ARCH=hppa1.0 ;; # CPU_PA_RISC1_0
 		      528) HP_ARCH=hppa1.1 ;; # CPU_PA_RISC1_1
 		      532)                      # CPU_PA_RISC2_0
-			case "${sc_kernel_bits}" in
+			case "$sc_kernel_bits" in
 			  32) HP_ARCH=hppa2.0n ;;
 			  64) HP_ARCH=hppa2.0w ;;
 			  '') HP_ARCH=hppa2.0 ;;   # HP-UX 10.20
 			esac ;;
 		    esac
 		fi
-		if [ "${HP_ARCH}" = "" ]; then
-		    eval $set_cc_for_build
-		    sed 's/^		//' << EOF >$dummy.c
+		if [ "$HP_ARCH" = "" ]; then
+		    eval "$set_cc_for_build"
+		    sed 's/^		//' << EOF > "$dummy.c"
 
 		#define _HPUX_SOURCE
 		#include <stdlib.h>
@@ -684,13 +694,13 @@ EOF
 		    exit (0);
 		}
 EOF
-		    (CCOPTS="" $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
+		    (CCOPTS="" $CC_FOR_BUILD -o "$dummy" "$dummy.c" 2>/dev/null) && HP_ARCH=`"$dummy"`
 		    test -z "$HP_ARCH" && HP_ARCH=hppa
 		fi ;;
 	esac
-	if [ ${HP_ARCH} = hppa2.0w ]
+	if [ "$HP_ARCH" = hppa2.0w ]
 	then
-	    eval $set_cc_for_build
+	    eval "$set_cc_for_build"
 
 	    # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating
 	    # 32-bit code.  hppa64-hp-hpux* has the same kernel and a compiler
@@ -709,15 +719,15 @@ EOF
 		HP_ARCH=hppa64
 	    fi
 	fi
-	echo ${HP_ARCH}-hp-hpux${HPUX_REV}
+	echo "$HP_ARCH"-hp-hpux"$HPUX_REV"
 	exit ;;
     ia64:HP-UX:*:*)
-	HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
-	echo ia64-hp-hpux${HPUX_REV}
+	HPUX_REV=`echo "$UNAME_RELEASE"|sed -e 's/[^.]*.[0B]*//'`
+	echo ia64-hp-hpux"$HPUX_REV"
 	exit ;;
     3050*:HI-UX:*:*)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
+	eval "$set_cc_for_build"
+	sed 's/^	//' << EOF > "$dummy.c"
 	#include <unistd.h>
 	int
 	main ()
@@ -742,11 +752,11 @@ EOF
 	  exit (0);
 	}
 EOF
-	$CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` &&
+	$CC_FOR_BUILD -o "$dummy" "$dummy.c" && SYSTEM_NAME=`"$dummy"` &&
 		{ echo "$SYSTEM_NAME"; exit; }
 	echo unknown-hitachi-hiuxwe2
 	exit ;;
-    9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )
+    9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:*)
 	echo hppa1.1-hp-bsd
 	exit ;;
     9000/8??:4.3bsd:*:*)
@@ -755,7 +765,7 @@ EOF
     *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*)
 	echo hppa1.0-hp-mpeix
 	exit ;;
-    hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* )
+    hp7??:OSF1:*:* | hp8?[79]:OSF1:*:*)
 	echo hppa1.1-hp-osf
 	exit ;;
     hp8??:OSF1:*:*)
@@ -763,9 +773,9 @@ EOF
 	exit ;;
     i*86:OSF1:*:*)
 	if [ -x /usr/sbin/sysversion ] ; then
-	    echo ${UNAME_MACHINE}-unknown-osf1mk
+	    echo "$UNAME_MACHINE"-unknown-osf1mk
 	else
-	    echo ${UNAME_MACHINE}-unknown-osf1
+	    echo "$UNAME_MACHINE"-unknown-osf1
 	fi
 	exit ;;
     parisc*:Lites*:*:*)
@@ -790,127 +800,109 @@ EOF
 	echo c4-convex-bsd
 	exit ;;
     CRAY*Y-MP:*:*:*)
-	echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+	echo ymp-cray-unicos"$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
     CRAY*[A-Z]90:*:*:*)
-	echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \
+	echo "$UNAME_MACHINE"-cray-unicos"$UNAME_RELEASE" \
 	| sed -e 's/CRAY.*\([A-Z]90\)/\1/' \
 	      -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \
 	      -e 's/\.[^.]*$/.X/'
 	exit ;;
     CRAY*TS:*:*:*)
-	echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+	echo t90-cray-unicos"$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
     CRAY*T3E:*:*:*)
-	echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+	echo alphaev5-cray-unicosmk"$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
     CRAY*SV1:*:*:*)
-	echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+	echo sv1-cray-unicos"$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
     *:UNICOS/mp:*:*)
-	echo craynv-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
+	echo craynv-cray-unicosmp"$UNAME_RELEASE" | sed -e 's/\.[^.]*$/.X/'
 	exit ;;
     F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
 	FUJITSU_PROC=`uname -m | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz`
 	FUJITSU_SYS=`uname -p | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/\///'`
-	FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
+	FUJITSU_REL=`echo "$UNAME_RELEASE" | sed -e 's/ /_/'`
 	echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
 	exit ;;
     5000:UNIX_System_V:4.*:*)
 	FUJITSU_SYS=`uname -p | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/\///'`
-	FUJITSU_REL=`echo ${UNAME_RELEASE} | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/ /_/'`
+	FUJITSU_REL=`echo "$UNAME_RELEASE" | tr ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrstuvwxyz | sed -e 's/ /_/'`
 	echo "sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
 	exit ;;
     i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
-	echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-pc-bsdi"$UNAME_RELEASE"
 	exit ;;
     sparc*:BSD/OS:*:*)
-	echo sparc-unknown-bsdi${UNAME_RELEASE}
+	echo sparc-unknown-bsdi"$UNAME_RELEASE"
 	exit ;;
     *:BSD/OS:*:*)
-	echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-unknown-bsdi"$UNAME_RELEASE"
 	exit ;;
     *:FreeBSD:*:*)
 	UNAME_PROCESSOR=`/usr/bin/uname -p`
-	case ${UNAME_PROCESSOR} in
+	case "$UNAME_PROCESSOR" in
 	    amd64)
-		echo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
-	    *)
-		echo ${UNAME_PROCESSOR}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;
+		UNAME_PROCESSOR=x86_64 ;;
+	    i386)
+		UNAME_PROCESSOR=i586 ;;
 	esac
+	echo "$UNAME_PROCESSOR"-unknown-freebsd"`echo "$UNAME_RELEASE"|sed -e 's/[-(].*//'`"
 	exit ;;
     i*:CYGWIN*:*)
-	echo ${UNAME_MACHINE}-pc-cygwin
+	echo "$UNAME_MACHINE"-pc-cygwin
 	exit ;;
     *:MINGW64*:*)
-	echo ${UNAME_MACHINE}-pc-mingw64
+	echo "$UNAME_MACHINE"-pc-mingw64
 	exit ;;
     *:MINGW*:*)
-	echo ${UNAME_MACHINE}-pc-mingw32
+	echo "$UNAME_MACHINE"-pc-mingw32
 	exit ;;
     *:MSYS*:*)
-	echo ${UNAME_MACHINE}-pc-msys
-	exit ;;
-    i*:windows32*:*)
-	# uname -m includes "-pc" on this system.
-	echo ${UNAME_MACHINE}-mingw32
+	echo "$UNAME_MACHINE"-pc-msys
 	exit ;;
     i*:PW*:*)
-	echo ${UNAME_MACHINE}-pc-pw32
+	echo "$UNAME_MACHINE"-pc-pw32
 	exit ;;
     *:Interix*:*)
-	case ${UNAME_MACHINE} in
+	case "$UNAME_MACHINE" in
 	    x86)
-		echo i586-pc-interix${UNAME_RELEASE}
+		echo i586-pc-interix"$UNAME_RELEASE"
 		exit ;;
 	    authenticamd | genuineintel | EM64T)
-		echo x86_64-unknown-interix${UNAME_RELEASE}
+		echo x86_64-unknown-interix"$UNAME_RELEASE"
 		exit ;;
 	    IA64)
-		echo ia64-unknown-interix${UNAME_RELEASE}
+		echo ia64-unknown-interix"$UNAME_RELEASE"
 		exit ;;
 	esac ;;
-    [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)
-	echo i${UNAME_MACHINE}-pc-mks
-	exit ;;
-    8664:Windows_NT:*)
-	echo x86_64-pc-mks
-	exit ;;
-    i*:Windows_NT*:* | Pentium*:Windows_NT*:*)
-	# How do we know it's Interix rather than the generic POSIX subsystem?
-	# It also conflicts with pre-2.0 versions of AT&T UWIN. Should we
-	# UNAME_MACHINE based on the output of uname instead of i386?
-	echo i586-pc-interix
-	exit ;;
     i*:UWIN*:*)
-	echo ${UNAME_MACHINE}-pc-uwin
+	echo "$UNAME_MACHINE"-pc-uwin
 	exit ;;
     amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*)
 	echo x86_64-unknown-cygwin
 	exit ;;
-    p*:CYGWIN*:*)
-	echo powerpcle-unknown-cygwin
-	exit ;;
     prep*:SunOS:5.*:*)
-	echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
+	echo powerpcle-unknown-solaris2"`echo "$UNAME_RELEASE"|sed -e 's/[^.]*//'`"
 	exit ;;
     *:GNU:*:*)
 	# the GNU system
-	echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-${LIBC}`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
+	echo "`echo "$UNAME_MACHINE"|sed -e 's,[-/].*$,,'`-unknown-$LIBC`echo "$UNAME_RELEASE"|sed -e 's,/.*$,,'`"
 	exit ;;
     *:GNU/*:*:*)
 	# other systems with GNU libc and userland
-	echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr "[:upper:]" "[:lower:]"``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-${LIBC}
+	echo "$UNAME_MACHINE-unknown-`echo "$UNAME_SYSTEM" | sed 's,^[^/]*/,,' | tr "[:upper:]" "[:lower:]"``echo "$UNAME_RELEASE"|sed -e 's/[-(].*//'`-$LIBC"
 	exit ;;
     i*86:Minix:*:*)
-	echo ${UNAME_MACHINE}-pc-minix
+	echo "$UNAME_MACHINE"-pc-minix
 	exit ;;
     aarch64:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     aarch64_be:Linux:*:*)
 	UNAME_MACHINE=aarch64_be
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     alpha:Linux:*:*)
 	case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
@@ -924,63 +916,63 @@ EOF
 	esac
 	objdump --private-headers /bin/sh | grep -q ld.so.1
 	if test "$?" = 0 ; then LIBC=gnulibc1 ; fi
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     arc:Linux:*:* | arceb:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     arm*:Linux:*:*)
-	eval $set_cc_for_build
+	eval "$set_cc_for_build"
 	if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
 	    | grep -q __ARM_EABI__
 	then
-	    echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	    echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	else
 	    if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \
 		| grep -q __ARM_PCS_VFP
 	    then
-		echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabi
+		echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"eabi
 	    else
-		echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabihf
+		echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"eabihf
 	    fi
 	fi
 	exit ;;
     avr32*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     cris:Linux:*:*)
-	echo ${UNAME_MACHINE}-axis-linux-${LIBC}
+	echo "$UNAME_MACHINE"-axis-linux-"$LIBC"
 	exit ;;
     crisv32:Linux:*:*)
-	echo ${UNAME_MACHINE}-axis-linux-${LIBC}
+	echo "$UNAME_MACHINE"-axis-linux-"$LIBC"
 	exit ;;
     e2k:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     frv:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     hexagon:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     i*86:Linux:*:*)
-	echo ${UNAME_MACHINE}-pc-linux-${LIBC}
+	echo "$UNAME_MACHINE"-pc-linux-"$LIBC"
 	exit ;;
     ia64:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     k1om:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     m32r*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     m68*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     mips:Linux:*:* | mips64:Linux:*:*)
-	eval $set_cc_for_build
-	sed 's/^	//' << EOF >$dummy.c
+	eval "$set_cc_for_build"
+	sed 's/^	//' << EOF > "$dummy.c"
 	#undef CPU
 	#undef ${UNAME_MACHINE}
 	#undef ${UNAME_MACHINE}el
@@ -994,64 +986,74 @@ EOF
 	#endif
 	#endif
 EOF
-	eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`
-	test x"${CPU}" != x && { echo "${CPU}-unknown-linux-${LIBC}"; exit; }
+	eval "`$CC_FOR_BUILD -E "$dummy.c" 2>/dev/null | grep '^CPU'`"
+	test "x$CPU" != x && { echo "$CPU-unknown-linux-$LIBC"; exit; }
 	;;
+    mips64el:Linux:*:*)
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
+	exit ;;
     openrisc*:Linux:*:*)
-	echo or1k-unknown-linux-${LIBC}
+	echo or1k-unknown-linux-"$LIBC"
 	exit ;;
     or32:Linux:*:* | or1k*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     padre:Linux:*:*)
-	echo sparc-unknown-linux-${LIBC}
+	echo sparc-unknown-linux-"$LIBC"
 	exit ;;
     parisc64:Linux:*:* | hppa64:Linux:*:*)
-	echo hppa64-unknown-linux-${LIBC}
+	echo hppa64-unknown-linux-"$LIBC"
 	exit ;;
     parisc:Linux:*:* | hppa:Linux:*:*)
 	# Look for CPU level
 	case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
-	  PA7*) echo hppa1.1-unknown-linux-${LIBC} ;;
-	  PA8*) echo hppa2.0-unknown-linux-${LIBC} ;;
-	  *)    echo hppa-unknown-linux-${LIBC} ;;
+	  PA7*) echo hppa1.1-unknown-linux-"$LIBC" ;;
+	  PA8*) echo hppa2.0-unknown-linux-"$LIBC" ;;
+	  *)    echo hppa-unknown-linux-"$LIBC" ;;
 	esac
 	exit ;;
     ppc64:Linux:*:*)
-	echo powerpc64-unknown-linux-${LIBC}
+	echo powerpc64-unknown-linux-"$LIBC"
 	exit ;;
     ppc:Linux:*:*)
-	echo powerpc-unknown-linux-${LIBC}
+	echo powerpc-unknown-linux-"$LIBC"
 	exit ;;
     ppc64le:Linux:*:*)
-	echo powerpc64le-unknown-linux-${LIBC}
+	echo powerpc64le-unknown-linux-"$LIBC"
 	exit ;;
     ppcle:Linux:*:*)
-	echo powerpcle-unknown-linux-${LIBC}
+	echo powerpcle-unknown-linux-"$LIBC"
+	exit ;;
+    riscv32:Linux:*:* | riscv64:Linux:*:*)
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     s390:Linux:*:* | s390x:Linux:*:*)
-	echo ${UNAME_MACHINE}-ibm-linux-${LIBC}
+	echo "$UNAME_MACHINE"-ibm-linux-"$LIBC"
 	exit ;;
     sh64*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     sh*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     sparc:Linux:*:* | sparc64:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     tile*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     vax:Linux:*:*)
-	echo ${UNAME_MACHINE}-dec-linux-${LIBC}
+	echo "$UNAME_MACHINE"-dec-linux-"$LIBC"
 	exit ;;
     x86_64:Linux:*:*)
-	echo ${UNAME_MACHINE}-pc-linux-${LIBC}
+	if objdump -f /bin/sh | grep -q elf32-x86-64; then
+	    echo "$UNAME_MACHINE"-pc-linux-"$LIBC"x32
+	else
+	    echo "$UNAME_MACHINE"-pc-linux-"$LIBC"
+	fi
 	exit ;;
     xtensa*:Linux:*:*)
-	echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
+	echo "$UNAME_MACHINE"-unknown-linux-"$LIBC"
 	exit ;;
     i*86:DYNIX/ptx:4*:*)
 	# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
@@ -1065,34 +1067,34 @@ EOF
 	# I am not positive that other SVR4 systems won't match this,
 	# I just have to hope.  -- rms.
 	# Use sysv4.2uw... so that sysv4* matches it.
-	echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
+	echo "$UNAME_MACHINE"-pc-sysv4.2uw"$UNAME_VERSION"
 	exit ;;
     i*86:OS/2:*:*)
 	# If we were able to find `uname', then EMX Unix compatibility
 	# is probably installed.
-	echo ${UNAME_MACHINE}-pc-os2-emx
+	echo "$UNAME_MACHINE"-pc-os2-emx
 	exit ;;
     i*86:XTS-300:*:STOP)
-	echo ${UNAME_MACHINE}-unknown-stop
+	echo "$UNAME_MACHINE"-unknown-stop
 	exit ;;
     i*86:atheos:*:*)
-	echo ${UNAME_MACHINE}-unknown-atheos
+	echo "$UNAME_MACHINE"-unknown-atheos
 	exit ;;
     i*86:syllable:*:*)
-	echo ${UNAME_MACHINE}-pc-syllable
+	echo "$UNAME_MACHINE"-pc-syllable
 	exit ;;
     i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.[02]*:*)
-	echo i386-unknown-lynxos${UNAME_RELEASE}
+	echo i386-unknown-lynxos"$UNAME_RELEASE"
 	exit ;;
     i*86:*DOS:*:*)
-	echo ${UNAME_MACHINE}-pc-msdosdjgpp
+	echo "$UNAME_MACHINE"-pc-msdosdjgpp
 	exit ;;
-    i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
-	UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
+    i*86:*:4.*:*)
+	UNAME_REL=`echo "$UNAME_RELEASE" | sed 's/\/MP$//'`
 	if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
-		echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}
+		echo "$UNAME_MACHINE"-univel-sysv"$UNAME_REL"
 	else
-		echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}
+		echo "$UNAME_MACHINE"-pc-sysv"$UNAME_REL"
 	fi
 	exit ;;
     i*86:*:5:[678]*)
@@ -1102,12 +1104,12 @@ EOF
 	    *Pentium)	     UNAME_MACHINE=i586 ;;
 	    *Pent*|*Celeron) UNAME_MACHINE=i686 ;;
 	esac
-	echo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION}
+	echo "$UNAME_MACHINE-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}{$UNAME_VERSION}"
 	exit ;;
     i*86:*:3.2:*)
 	if test -f /usr/options/cb.name; then
 		UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
-		echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
+		echo "$UNAME_MACHINE"-pc-isc"$UNAME_REL"
 	elif /bin/uname -X 2>/dev/null >/dev/null ; then
 		UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`
 		(/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486
@@ -1117,9 +1119,9 @@ EOF
 			&& UNAME_MACHINE=i686
 		(/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \
 			&& UNAME_MACHINE=i686
-		echo ${UNAME_MACHINE}-pc-sco$UNAME_REL
+		echo "$UNAME_MACHINE"-pc-sco"$UNAME_REL"
 	else
-		echo ${UNAME_MACHINE}-pc-sysv32
+		echo "$UNAME_MACHINE"-pc-sysv32
 	fi
 	exit ;;
     pc:*:*:*)
@@ -1139,9 +1141,9 @@ EOF
 	exit ;;
     i860:*:4.*:*) # i860-SVR4
 	if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then
-	  echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4
+	  echo i860-stardent-sysv"$UNAME_RELEASE" # Stardent Vistra i860-SVR4
 	else # Add other i860-SVR4 vendors below as they are discovered.
-	  echo i860-unknown-sysv${UNAME_RELEASE}  # Unknown i860-SVR4
+	  echo i860-unknown-sysv"$UNAME_RELEASE"  # Unknown i860-SVR4
 	fi
 	exit ;;
     mini*:CTIX:SYS*5:*)
@@ -1161,9 +1163,9 @@ EOF
 	test -r /etc/.relid \
 	&& OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
 	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-	  && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
+	  && { echo i486-ncr-sysv4.3"$OS_REL"; exit; }
 	/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
-	  && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
+	  && { echo i586-ncr-sysv4.3"$OS_REL"; exit; } ;;
     3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
 	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
 	  && { echo i486-ncr-sysv4; exit; } ;;
@@ -1172,28 +1174,28 @@ EOF
 	test -r /etc/.relid \
 	    && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
 	/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
-	    && { echo i486-ncr-sysv4.3${OS_REL}; exit; }
+	    && { echo i486-ncr-sysv4.3"$OS_REL"; exit; }
 	/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \
-	    && { echo i586-ncr-sysv4.3${OS_REL}; exit; }
+	    && { echo i586-ncr-sysv4.3"$OS_REL"; exit; }
 	/bin/uname -p 2>/dev/null | /bin/grep pteron >/dev/null \
-	    && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;
+	    && { echo i586-ncr-sysv4.3"$OS_REL"; exit; } ;;
     m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)
-	echo m68k-unknown-lynxos${UNAME_RELEASE}
+	echo m68k-unknown-lynxos"$UNAME_RELEASE"
 	exit ;;
     mc68030:UNIX_System_V:4.*:*)
 	echo m68k-atari-sysv4
 	exit ;;
     TSUNAMI:LynxOS:2.*:*)
-	echo sparc-unknown-lynxos${UNAME_RELEASE}
+	echo sparc-unknown-lynxos"$UNAME_RELEASE"
 	exit ;;
     rs6000:LynxOS:2.*:*)
-	echo rs6000-unknown-lynxos${UNAME_RELEASE}
+	echo rs6000-unknown-lynxos"$UNAME_RELEASE"
 	exit ;;
     PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.[02]*:*)
-	echo powerpc-unknown-lynxos${UNAME_RELEASE}
+	echo powerpc-unknown-lynxos"$UNAME_RELEASE"
 	exit ;;
     SM[BE]S:UNIX_SV:*:*)
-	echo mips-dde-sysv${UNAME_RELEASE}
+	echo mips-dde-sysv"$UNAME_RELEASE"
 	exit ;;
     RM*:ReliantUNIX-*:*:*)
 	echo mips-sni-sysv4
@@ -1204,7 +1206,7 @@ EOF
     *:SINIX-*:*:*)
 	if uname -p 2>/dev/null >/dev/null ; then
 		UNAME_MACHINE=`(uname -p) 2>/dev/null`
-		echo ${UNAME_MACHINE}-sni-sysv4
+		echo "$UNAME_MACHINE"-sni-sysv4
 	else
 		echo ns32k-sni-sysv
 	fi
@@ -1224,23 +1226,23 @@ EOF
 	exit ;;
     i*86:VOS:*:*)
 	# From Paul.Green at stratus.com.
-	echo ${UNAME_MACHINE}-stratus-vos
+	echo "$UNAME_MACHINE"-stratus-vos
 	exit ;;
     *:VOS:*:*)
 	# From Paul.Green at stratus.com.
 	echo hppa1.1-stratus-vos
 	exit ;;
     mc68*:A/UX:*:*)
-	echo m68k-apple-aux${UNAME_RELEASE}
+	echo m68k-apple-aux"$UNAME_RELEASE"
 	exit ;;
     news*:NEWS-OS:6*:*)
 	echo mips-sony-newsos6
 	exit ;;
     R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)
 	if [ -d /usr/nec ]; then
-		echo mips-nec-sysv${UNAME_RELEASE}
+		echo mips-nec-sysv"$UNAME_RELEASE"
 	else
-		echo mips-unknown-sysv${UNAME_RELEASE}
+		echo mips-unknown-sysv"$UNAME_RELEASE"
 	fi
 	exit ;;
     BeBox:BeOS:*:*)	# BeOS running on hardware made by Be, PPC only.
@@ -1259,49 +1261,56 @@ EOF
 	echo x86_64-unknown-haiku
 	exit ;;
     SX-4:SUPER-UX:*:*)
-	echo sx4-nec-superux${UNAME_RELEASE}
+	echo sx4-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-5:SUPER-UX:*:*)
-	echo sx5-nec-superux${UNAME_RELEASE}
+	echo sx5-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-6:SUPER-UX:*:*)
-	echo sx6-nec-superux${UNAME_RELEASE}
+	echo sx6-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-7:SUPER-UX:*:*)
-	echo sx7-nec-superux${UNAME_RELEASE}
+	echo sx7-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-8:SUPER-UX:*:*)
-	echo sx8-nec-superux${UNAME_RELEASE}
+	echo sx8-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-8R:SUPER-UX:*:*)
-	echo sx8r-nec-superux${UNAME_RELEASE}
+	echo sx8r-nec-superux"$UNAME_RELEASE"
 	exit ;;
     SX-ACE:SUPER-UX:*:*)
-	echo sxace-nec-superux${UNAME_RELEASE}
+	echo sxace-nec-superux"$UNAME_RELEASE"
 	exit ;;
     Power*:Rhapsody:*:*)
-	echo powerpc-apple-rhapsody${UNAME_RELEASE}
+	echo powerpc-apple-rhapsody"$UNAME_RELEASE"
 	exit ;;
     *:Rhapsody:*:*)
-	echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-apple-rhapsody"$UNAME_RELEASE"
 	exit ;;
     *:Darwin:*:*)
 	UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown
-	eval $set_cc_for_build
+	eval "$set_cc_for_build"
 	if test "$UNAME_PROCESSOR" = unknown ; then
 	    UNAME_PROCESSOR=powerpc
 	fi
-	if test `echo "$UNAME_RELEASE" | sed -e 's/\..*//'` -le 10 ; then
+	if test "`echo "$UNAME_RELEASE" | sed -e 's/\..*//'`" -le 10 ; then
 	    if [ "$CC_FOR_BUILD" != no_compiler_found ]; then
 		if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \
-		    (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | \
-		    grep IS_64BIT_ARCH >/dev/null
+		       (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | \
+		       grep IS_64BIT_ARCH >/dev/null
 		then
 		    case $UNAME_PROCESSOR in
 			i386) UNAME_PROCESSOR=x86_64 ;;
 			powerpc) UNAME_PROCESSOR=powerpc64 ;;
 		    esac
 		fi
+		# On 10.4-10.6 one might compile for PowerPC via gcc -arch ppc
+		if (echo '#ifdef __POWERPC__'; echo IS_PPC; echo '#endif') | \
+		       (CCOPTS="" $CC_FOR_BUILD -E - 2>/dev/null) | \
+		       grep IS_PPC >/dev/null
+		then
+		    UNAME_PROCESSOR=powerpc
+		fi
 	    fi
 	elif test "$UNAME_PROCESSOR" = i386 ; then
 	    # Avoid executing cc on OS X 10.9, as it ships with a stub
@@ -1312,7 +1321,7 @@ EOF
 	    # that Apple uses in portable devices.
 	    UNAME_PROCESSOR=x86_64
 	fi
-	echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
+	echo "$UNAME_PROCESSOR"-apple-darwin"$UNAME_RELEASE"
 	exit ;;
     *:procnto*:*:* | *:QNX:[0123456789]*:*)
 	UNAME_PROCESSOR=`uname -p`
@@ -1320,19 +1329,25 @@ EOF
 		UNAME_PROCESSOR=i386
 		UNAME_MACHINE=pc
 	fi
-	echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}
+	echo "$UNAME_PROCESSOR"-"$UNAME_MACHINE"-nto-qnx"$UNAME_RELEASE"
 	exit ;;
     *:QNX:*:4*)
 	echo i386-pc-qnx
 	exit ;;
-    NEO-?:NONSTOP_KERNEL:*:*)
-	echo neo-tandem-nsk${UNAME_RELEASE}
+    NEO-*:NONSTOP_KERNEL:*:*)
+	echo neo-tandem-nsk"$UNAME_RELEASE"
 	exit ;;
     NSE-*:NONSTOP_KERNEL:*:*)
-	echo nse-tandem-nsk${UNAME_RELEASE}
+	echo nse-tandem-nsk"$UNAME_RELEASE"
+	exit ;;
+    NSR-*:NONSTOP_KERNEL:*:*)
+	echo nsr-tandem-nsk"$UNAME_RELEASE"
 	exit ;;
-    NSR-?:NONSTOP_KERNEL:*:*)
-	echo nsr-tandem-nsk${UNAME_RELEASE}
+    NSV-*:NONSTOP_KERNEL:*:*)
+	echo nsv-tandem-nsk"$UNAME_RELEASE"
+	exit ;;
+    NSX-*:NONSTOP_KERNEL:*:*)
+	echo nsx-tandem-nsk"$UNAME_RELEASE"
 	exit ;;
     *:NonStop-UX:*:*)
 	echo mips-compaq-nonstopux
@@ -1341,7 +1356,7 @@ EOF
 	echo bs2000-siemens-sysv
 	exit ;;
     DS/*:UNIX_System_V:*:*)
-	echo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE}
+	echo "$UNAME_MACHINE"-"$UNAME_SYSTEM"-"$UNAME_RELEASE"
 	exit ;;
     *:Plan9:*:*)
 	# "uname -m" is not consistent, so use $cputype instead. 386
@@ -1352,7 +1367,7 @@ EOF
 	else
 	    UNAME_MACHINE="$cputype"
 	fi
-	echo ${UNAME_MACHINE}-unknown-plan9
+	echo "$UNAME_MACHINE"-unknown-plan9
 	exit ;;
     *:TOPS-10:*:*)
 	echo pdp10-unknown-tops10
@@ -1373,14 +1388,14 @@ EOF
 	echo pdp10-unknown-its
 	exit ;;
     SEI:*:*:SEIUX)
-	echo mips-sei-seiux${UNAME_RELEASE}
+	echo mips-sei-seiux"$UNAME_RELEASE"
 	exit ;;
     *:DragonFly:*:*)
-	echo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`
+	echo "$UNAME_MACHINE"-unknown-dragonfly"`echo "$UNAME_RELEASE"|sed -e 's/[-(].*//'`"
 	exit ;;
     *:*VMS:*:*)
 	UNAME_MACHINE=`(uname -p) 2>/dev/null`
-	case "${UNAME_MACHINE}" in
+	case "$UNAME_MACHINE" in
 	    A*) echo alpha-dec-vms ; exit ;;
 	    I*) echo ia64-dec-vms ; exit ;;
 	    V*) echo vax-dec-vms ; exit ;;
@@ -1389,37 +1404,48 @@ EOF
 	echo i386-pc-xenix
 	exit ;;
     i*86:skyos:*:*)
-	echo ${UNAME_MACHINE}-pc-skyos`echo ${UNAME_RELEASE} | sed -e 's/ .*$//'`
+	echo "$UNAME_MACHINE"-pc-skyos"`echo "$UNAME_RELEASE" | sed -e 's/ .*$//'`"
 	exit ;;
     i*86:rdos:*:*)
-	echo ${UNAME_MACHINE}-pc-rdos
+	echo "$UNAME_MACHINE"-pc-rdos
 	exit ;;
     i*86:AROS:*:*)
-	echo ${UNAME_MACHINE}-pc-aros
+	echo "$UNAME_MACHINE"-pc-aros
 	exit ;;
     x86_64:VMkernel:*:*)
-	echo ${UNAME_MACHINE}-unknown-esx
+	echo "$UNAME_MACHINE"-unknown-esx
 	exit ;;
     amd64:Isilon\ OneFS:*:*)
 	echo x86_64-unknown-onefs
 	exit ;;
 esac
 
+echo "$0: unable to guess system type" >&2
+
+case "$UNAME_MACHINE:$UNAME_SYSTEM" in
+    mips:Linux | mips64:Linux)
+	# If we got here on MIPS GNU/Linux, output extra information.
+	cat >&2 <<EOF
+
+NOTE: MIPS GNU/Linux systems require a C compiler to fully recognize
+the system type. Please install a C compiler and try again.
+EOF
+	;;
+esac
+
 cat >&2 <<EOF
-$0: unable to guess system type
 
-This script, last modified $timestamp, has failed to recognize
-the operating system you are using. It is advised that you
-download the most up to date version of the config scripts from
+This script (version $timestamp), has failed to recognize the
+operating system you are using. If your script is old, overwrite *all*
+copies of config.guess and config.sub with the latest versions from:
 
-  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess
+  https://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess
 and
-  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub
+  https://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub
 
-If the version you run ($0) is already up to date, please
-send the following data and any information you think might be
-pertinent to <config-patches at gnu.org> in order to provide the needed
-information to handle your system.
+If $0 has already been updated, send the following data and any
+information you think might be pertinent to config-patches at gnu.org to
+provide the necessary information to handle your system.
 
 config.guess timestamp = $timestamp
 
@@ -1438,16 +1464,16 @@ hostinfo               = `(hostinfo) 2>/
 /usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null`
 /usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null`
 
-UNAME_MACHINE = ${UNAME_MACHINE}
-UNAME_RELEASE = ${UNAME_RELEASE}
-UNAME_SYSTEM  = ${UNAME_SYSTEM}
-UNAME_VERSION = ${UNAME_VERSION}
+UNAME_MACHINE = "$UNAME_MACHINE"
+UNAME_RELEASE = "$UNAME_RELEASE"
+UNAME_SYSTEM  = "$UNAME_SYSTEM"
+UNAME_VERSION = "$UNAME_VERSION"
 EOF
 
 exit 1
 
 # Local variables:
-# eval: (add-hook 'write-file-hooks 'time-stamp)
+# eval: (add-hook 'write-file-functions 'time-stamp)
 # time-stamp-start: "timestamp='"
 # time-stamp-format: "%:y-%02m-%02d"
 # time-stamp-end: "'"

Modified: polly/trunk/lib/External/isl/config.sub
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/config.sub?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/config.sub (original)
+++ polly/trunk/lib/External/isl/config.sub Sat Apr 21 01:34:22 2018
@@ -1,8 +1,8 @@
 #! /bin/sh
 # Configuration validation subroutine script.
-#   Copyright 1992-2016 Free Software Foundation, Inc.
+#   Copyright 1992-2018 Free Software Foundation, Inc.
 
-timestamp='2016-03-30'
+timestamp='2018-02-22'
 
 # This file is free software; you can redistribute it and/or modify it
 # under the terms of the GNU General Public License as published by
@@ -15,7 +15,7 @@ timestamp='2016-03-30'
 # General Public License for more details.
 #
 # You should have received a copy of the GNU General Public License
-# along with this program; if not, see <http://www.gnu.org/licenses/>.
+# along with this program; if not, see <https://www.gnu.org/licenses/>.
 #
 # As a special exception to the GNU General Public License, if you
 # distribute this file as part of a program that contains a
@@ -33,7 +33,7 @@ timestamp='2016-03-30'
 # Otherwise, we print the canonical config type on stdout and succeed.
 
 # You can get the latest version of this script from:
-# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub
+# https://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub
 
 # This file is supposed to be the same for all GNU packages
 # and recognize all the CPU types, system types and aliases
@@ -57,7 +57,7 @@ Usage: $0 [OPTION] CPU-MFR-OPSYS or ALIA
 
 Canonicalize a configuration name.
 
-Operation modes:
+Options:
   -h, --help         print this help, then exit
   -t, --time-stamp   print date of last modification, then exit
   -v, --version      print version number, then exit
@@ -67,7 +67,7 @@ Report bugs and patches to <config-patch
 version="\
 GNU config.sub ($timestamp)
 
-Copyright 1992-2016 Free Software Foundation, Inc.
+Copyright 1992-2018 Free Software Foundation, Inc.
 
 This is free software; see the source for copying conditions.  There is NO
 warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -94,7 +94,7 @@ while test $# -gt 0 ; do
 
     *local*)
        # First pass through any local machine types.
-       echo $1
+       echo "$1"
        exit ;;
 
     * )
@@ -112,24 +112,24 @@ esac
 
 # Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any).
 # Here we must recognize all the valid KERNEL-OS combinations.
-maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
+maybe_os=`echo "$1" | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
 case $maybe_os in
   nto-qnx* | linux-gnu* | linux-android* | linux-dietlibc | linux-newlib* | \
   linux-musl* | linux-uclibc* | uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | \
   knetbsd*-gnu* | netbsd*-gnu* | netbsd*-eabi* | \
-  kopensolaris*-gnu* | \
+  kopensolaris*-gnu* | cloudabi*-eabi* | \
   storm-chaos* | os2-emx* | rtmk-nova*)
     os=-$maybe_os
-    basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
+    basic_machine=`echo "$1" | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
     ;;
   android-linux)
     os=-linux-android
-    basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`-unknown
+    basic_machine=`echo "$1" | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`-unknown
     ;;
   *)
-    basic_machine=`echo $1 | sed 's/-[^-]*$//'`
-    if [ $basic_machine != $1 ]
-    then os=`echo $1 | sed 's/.*-/-/'`
+    basic_machine=`echo "$1" | sed 's/-[^-]*$//'`
+    if [ "$basic_machine" != "$1" ]
+    then os=`echo "$1" | sed 's/.*-/-/'`
     else os=; fi
     ;;
 esac
@@ -178,44 +178,44 @@ case $os in
 		;;
 	-sco6)
 		os=-sco5v6
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco5)
 		os=-sco3.2v5
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco4)
 		os=-sco3.2v4
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco3.2.[4-9]*)
 		os=`echo $os | sed -e 's/sco3.2./sco3.2v/'`
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco3.2v[4-9]*)
 		# Don't forget version if it is 3.2v4 or newer.
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco5v6*)
 		# Don't forget version if it is 3.2v4 or newer.
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-sco*)
 		os=-sco3.2v2
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-udk*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-isc)
 		os=-isc2.2
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-clix*)
 		basic_machine=clipper-intergraph
 		;;
 	-isc*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-pc/'`
 		;;
 	-lynx*178)
 		os=-lynxos178
@@ -227,10 +227,7 @@ case $os in
 		os=-lynxos
 		;;
 	-ptx*)
-		basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'`
-		;;
-	-windowsnt*)
-		os=`echo $os | sed -e 's/windowsnt/winnt/'`
+		basic_machine=`echo "$1" | sed -e 's/86-.*/86-sequent/'`
 		;;
 	-psos*)
 		os=-psos
@@ -263,7 +260,7 @@ case $basic_machine in
 	| fido | fr30 | frv | ft32 \
 	| h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
 	| hexagon \
-	| i370 | i860 | i960 | ia64 \
+	| i370 | i860 | i960 | ia16 | ia64 \
 	| ip2k | iq2000 \
 	| k1om \
 	| le32 | le64 \
@@ -299,8 +296,9 @@ case $basic_machine in
 	| nios | nios2 | nios2eb | nios2el \
 	| ns16k | ns32k \
 	| open8 | or1k | or1knd | or32 \
-	| pdp10 | pdp11 | pj | pjl \
+	| pdp10 | pj | pjl \
 	| powerpc | powerpc64 | powerpc64le | powerpcle \
+	| pru \
 	| pyramid \
 	| riscv32 | riscv64 \
 	| rl78 | rx \
@@ -314,7 +312,7 @@ case $basic_machine in
 	| ubicom32 \
 	| v850 | v850e | v850e1 | v850e2 | v850es | v850e2v3 \
 	| visium \
-	| we32k \
+	| wasm32 \
 	| x86 | xc16x | xstormy16 | xtensa \
 	| z8k | z80)
 		basic_machine=$basic_machine-unknown
@@ -335,7 +333,7 @@ case $basic_machine in
 		basic_machine=$basic_machine-unknown
 		os=-none
 		;;
-	m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k)
+	m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65)
 		;;
 	ms1)
 		basic_machine=mt-unknown
@@ -364,7 +362,7 @@ case $basic_machine in
 	  ;;
 	# Object if more than one company name word.
 	*-*-*)
-		echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+		echo Invalid configuration \`"$1"\': machine \`"$basic_machine"\' not recognized 1>&2
 		exit 1
 		;;
 	# Recognize the basic CPU types with company name.
@@ -387,7 +385,7 @@ case $basic_machine in
 	| h8300-* | h8500-* \
 	| hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
 	| hexagon-* \
-	| i*86-* | i860-* | i960-* | ia64-* \
+	| i*86-* | i860-* | i960-* | ia16-* | ia64-* \
 	| ip2k-* | iq2000-* \
 	| k1om-* \
 	| le32-* | le64-* \
@@ -428,6 +426,7 @@ case $basic_machine in
 	| orion-* \
 	| pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
 	| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* \
+	| pru-* \
 	| pyramid-* \
 	| riscv32-* | riscv64-* \
 	| rl78-* | romp-* | rs6000-* | rx-* \
@@ -444,6 +443,7 @@ case $basic_machine in
 	| v850-* | v850e-* | v850e1-* | v850es-* | v850e2-* | v850e2v3-* \
 	| vax-* \
 	| visium-* \
+	| wasm32-* \
 	| we32k-* \
 	| x86-* | x86_64-* | xc16x-* | xps100-* \
 	| xstormy16-* | xtensa*-* \
@@ -457,7 +457,7 @@ case $basic_machine in
 	# Recognize the various machine names and aliases which stand
 	# for a CPU type and a company and sometimes even an OS.
 	386bsd)
-		basic_machine=i386-unknown
+		basic_machine=i386-pc
 		os=-bsd
 		;;
 	3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc)
@@ -491,7 +491,7 @@ case $basic_machine in
 		basic_machine=x86_64-pc
 		;;
 	amd64-*)
-		basic_machine=x86_64-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=x86_64-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	amdahl)
 		basic_machine=580-amdahl
@@ -536,7 +536,7 @@ case $basic_machine in
 		os=-linux
 		;;
 	blackfin-*)
-		basic_machine=bfin-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=bfin-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		os=-linux
 		;;
 	bluegene*)
@@ -544,13 +544,13 @@ case $basic_machine in
 		os=-cnk
 		;;
 	c54x-*)
-		basic_machine=tic54x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=tic54x-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	c55x-*)
-		basic_machine=tic55x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=tic55x-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	c6x-*)
-		basic_machine=tic6x-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=tic6x-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	c90)
 		basic_machine=c90-cray
@@ -639,10 +639,18 @@ case $basic_machine in
 		basic_machine=rs6000-bull
 		os=-bosx
 		;;
-	dpx2* | dpx2*-bull)
+	dpx2*)
 		basic_machine=m68k-bull
 		os=-sysv3
 		;;
+	e500v[12])
+		basic_machine=powerpc-unknown
+		os=$os"spe"
+		;;
+	e500v[12]-*)
+		basic_machine=powerpc-`echo "$basic_machine" | sed 's/^[^-]*-//'`
+		os=$os"spe"
+		;;
 	ebmon29k)
 		basic_machine=a29k-amd
 		os=-ebmon
@@ -732,9 +740,6 @@ case $basic_machine in
 	hp9k8[0-9][0-9] | hp8[0-9][0-9])
 		basic_machine=hppa1.0-hp
 		;;
-	hppa-next)
-		os=-nextstep3
-		;;
 	hppaosf)
 		basic_machine=hppa1.1-hp
 		os=-osf
@@ -747,26 +752,26 @@ case $basic_machine in
 		basic_machine=i370-ibm
 		;;
 	i*86v32)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86.*/86-pc/'`
 		os=-sysv32
 		;;
 	i*86v4*)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86.*/86-pc/'`
 		os=-sysv4
 		;;
 	i*86v)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86.*/86-pc/'`
 		os=-sysv
 		;;
 	i*86sol2)
-		basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
+		basic_machine=`echo "$1" | sed -e 's/86.*/86-pc/'`
 		os=-solaris2
 		;;
 	i386mach)
 		basic_machine=i386-mach
 		os=-mach
 		;;
-	i386-vsta | vsta)
+	vsta)
 		basic_machine=i386-unknown
 		os=-vsta
 		;;
@@ -785,19 +790,16 @@ case $basic_machine in
 		os=-sysv
 		;;
 	leon-*|leon[3-9]-*)
-		basic_machine=sparc-`echo $basic_machine | sed 's/-.*//'`
+		basic_machine=sparc-`echo "$basic_machine" | sed 's/-.*//'`
 		;;
 	m68knommu)
 		basic_machine=m68k-unknown
 		os=-linux
 		;;
 	m68knommu-*)
-		basic_machine=m68k-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=m68k-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		os=-linux
 		;;
-	m88k-omron*)
-		basic_machine=m88k-omron
-		;;
 	magnum | m3230)
 		basic_machine=mips-mips
 		os=-sysv
@@ -829,10 +831,10 @@ case $basic_machine in
 		os=-mint
 		;;
 	mips3*-*)
-		basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`
+		basic_machine=`echo "$basic_machine" | sed -e 's/mips3/mips64/'`
 		;;
 	mips3*)
-		basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown
+		basic_machine=`echo "$basic_machine" | sed -e 's/mips3/mips64/'`-unknown
 		;;
 	monitor)
 		basic_machine=m68k-rom68k
@@ -851,7 +853,7 @@ case $basic_machine in
 		os=-msdos
 		;;
 	ms1-*)
-		basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`
+		basic_machine=`echo "$basic_machine" | sed -e 's/ms1-/mt-/'`
 		;;
 	msys)
 		basic_machine=i686-pc
@@ -893,7 +895,7 @@ case $basic_machine in
 		basic_machine=v70-nec
 		os=-sysv
 		;;
-	next | m*-next )
+	next | m*-next)
 		basic_machine=m68k-next
 		case $os in
 		    -nextstep* )
@@ -938,6 +940,12 @@ case $basic_machine in
 	nsr-tandem)
 		basic_machine=nsr-tandem
 		;;
+	nsv-tandem)
+		basic_machine=nsv-tandem
+		;;
+	nsx-tandem)
+		basic_machine=nsx-tandem
+		;;
 	op50n-* | op60c-*)
 		basic_machine=hppa1.1-oki
 		os=-proelf
@@ -970,7 +978,7 @@ case $basic_machine in
 		os=-linux
 		;;
 	parisc-*)
-		basic_machine=hppa-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=hppa-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		os=-linux
 		;;
 	pbd)
@@ -986,7 +994,7 @@ case $basic_machine in
 		basic_machine=i386-pc
 		;;
 	pc98-*)
-		basic_machine=i386-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=i386-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	pentium | p5 | k5 | k6 | nexgen | viac3)
 		basic_machine=i586-pc
@@ -1001,16 +1009,16 @@ case $basic_machine in
 		basic_machine=i786-pc
 		;;
 	pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)
-		basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=i586-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	pentiumpro-* | p6-* | 6x86-* | athlon-*)
-		basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=i686-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)
-		basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=i686-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	pentium4-*)
-		basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=i786-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	pn)
 		basic_machine=pn-gould
@@ -1020,23 +1028,23 @@ case $basic_machine in
 	ppc | ppcbe)	basic_machine=powerpc-unknown
 		;;
 	ppc-* | ppcbe-*)
-		basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=powerpc-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
-	ppcle | powerpclittle | ppc-le | powerpc-little)
+	ppcle | powerpclittle)
 		basic_machine=powerpcle-unknown
 		;;
 	ppcle-* | powerpclittle-*)
-		basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=powerpcle-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	ppc64)	basic_machine=powerpc64-unknown
 		;;
-	ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`
+	ppc64-*) basic_machine=powerpc64-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
-	ppc64le | powerpc64little | ppc64-le | powerpc64-little)
+	ppc64le | powerpc64little)
 		basic_machine=powerpc64le-unknown
 		;;
 	ppc64le-* | powerpc64little-*)
-		basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=powerpc64le-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	ps2)
 		basic_machine=i386-ibm
@@ -1090,17 +1098,10 @@ case $basic_machine in
 	sequent)
 		basic_machine=i386-sequent
 		;;
-	sh)
-		basic_machine=sh-hitachi
-		os=-hms
-		;;
 	sh5el)
 		basic_machine=sh5le-unknown
 		;;
-	sh64)
-		basic_machine=sh64-unknown
-		;;
-	sparclite-wrs | simso-wrs)
+	simso-wrs)
 		basic_machine=sparclite-wrs
 		os=-vxworks
 		;;
@@ -1119,7 +1120,7 @@ case $basic_machine in
 		os=-sysv4
 		;;
 	strongarm-* | thumb-*)
-		basic_machine=arm-`echo $basic_machine | sed 's/^[^-]*-//'`
+		basic_machine=arm-`echo "$basic_machine" | sed 's/^[^-]*-//'`
 		;;
 	sun2)
 		basic_machine=m68000-sun
@@ -1241,6 +1242,9 @@ case $basic_machine in
 		basic_machine=hppa1.1-winbond
 		os=-proelf
 		;;
+	x64)
+		basic_machine=x86_64-pc
+		;;
 	xbox)
 		basic_machine=i686-pc
 		os=-mingw32
@@ -1249,20 +1253,12 @@ case $basic_machine in
 		basic_machine=xps100-honeywell
 		;;
 	xscale-* | xscalee[bl]-*)
-		basic_machine=`echo $basic_machine | sed 's/^xscale/arm/'`
+		basic_machine=`echo "$basic_machine" | sed 's/^xscale/arm/'`
 		;;
 	ymp)
 		basic_machine=ymp-cray
 		os=-unicos
 		;;
-	z8k-*-coff)
-		basic_machine=z8k-unknown
-		os=-sim
-		;;
-	z80-*-coff)
-		basic_machine=z80-unknown
-		os=-sim
-		;;
 	none)
 		basic_machine=none-none
 		os=-none
@@ -1291,10 +1287,6 @@ case $basic_machine in
 	vax)
 		basic_machine=vax-dec
 		;;
-	pdp10)
-		# there are many clones, so DEC is not a safe bet
-		basic_machine=pdp10-unknown
-		;;
 	pdp11)
 		basic_machine=pdp11-dec
 		;;
@@ -1304,9 +1296,6 @@ case $basic_machine in
 	sh[1234] | sh[24]a | sh[24]aeb | sh[34]eb | sh[1234]le | sh[23]ele)
 		basic_machine=sh-unknown
 		;;
-	sparc | sparcv8 | sparcv9 | sparcv9b | sparcv9v)
-		basic_machine=sparc-sun
-		;;
 	cydra)
 		basic_machine=cydra-cydrome
 		;;
@@ -1326,7 +1315,7 @@ case $basic_machine in
 		# Make sure to match an already-canonicalized machine name.
 		;;
 	*)
-		echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
+		echo Invalid configuration \`"$1"\': machine \`"$basic_machine"\' not recognized 1>&2
 		exit 1
 		;;
 esac
@@ -1334,10 +1323,10 @@ esac
 # Here we canonicalize certain aliases for manufacturers.
 case $basic_machine in
 	*-digital*)
-		basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'`
+		basic_machine=`echo "$basic_machine" | sed 's/digital.*/dec/'`
 		;;
 	*-commodore*)
-		basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'`
+		basic_machine=`echo "$basic_machine" | sed 's/commodore.*/cbm/'`
 		;;
 	*)
 		;;
@@ -1348,8 +1337,8 @@ esac
 if [ x"$os" != x"" ]
 then
 case $os in
-	# First match some system type aliases
-	# that might get confused with valid system types.
+	# First match some system type aliases that might get confused
+	# with valid system types.
 	# -solaris* is a basic system type, with this one exception.
 	-auroraux)
 		os=-auroraux
@@ -1360,18 +1349,19 @@ case $os in
 	-solaris)
 		os=-solaris2
 		;;
-	-svr4*)
-		os=-sysv4
-		;;
 	-unixware*)
 		os=-sysv4.2uw
 		;;
 	-gnu/linux*)
 		os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'`
 		;;
-	# First accept the basic system types.
+	# es1800 is here to avoid being matched by es* (a different OS)
+	-es1800*)
+		os=-ose
+		;;
+	# Now accept the basic system types.
 	# The portable systems comes first.
-	# Each alternative MUST END IN A *, to match a version number.
+	# Each alternative MUST end in a * to match a version number.
 	# -sysv* is not here because it comes later, after sysvr4.
 	-gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \
 	      | -*vms* | -sco* | -esix* | -isc* | -aix* | -cnk* | -sunos | -sunos[34]*\
@@ -1381,25 +1371,26 @@ case $os in
 	      | -aos* | -aros* | -cloudabi* | -sortix* \
 	      | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \
 	      | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \
-	      | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \
+	      | -hiux* | -knetbsd* | -mirbsd* | -netbsd* \
 	      | -bitrig* | -openbsd* | -solidbsd* | -libertybsd* \
 	      | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \
 	      | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \
 	      | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \
 	      | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \
-	      | -chorusos* | -chorusrdb* | -cegcc* \
+	      | -chorusos* | -chorusrdb* | -cegcc* | -glidix* \
 	      | -cygwin* | -msys* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
-	      | -mingw32* | -mingw64* | -linux-gnu* | -linux-android* \
+	      | -midipix* | -mingw32* | -mingw64* | -linux-gnu* | -linux-android* \
 	      | -linux-newlib* | -linux-musl* | -linux-uclibc* \
 	      | -uxpv* | -beos* | -mpeix* | -udk* | -moxiebox* \
-	      | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
+	      | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* \
 	      | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
 	      | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \
 	      | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
-	      | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
+	      | -morphos* | -superux* | -rtmk* | -windiss* \
 	      | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \
 	      | -skyos* | -haiku* | -rdos* | -toppers* | -drops* | -es* \
-	      | -onefs* | -tirtos*)
+	      | -onefs* | -tirtos* | -phoenix* | -fuchsia* | -redox* | -bme* \
+	      | -midnightbsd*)
 	# Remember, each alternative MUST END IN *, to match a version number.
 		;;
 	-qnx*)
@@ -1416,12 +1407,12 @@ case $os in
 	-nto*)
 		os=`echo $os | sed -e 's|nto|nto-qnx|'`
 		;;
-	-sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \
-	      | -windows* | -osx | -abug | -netware* | -os9* | -beos* | -haiku* \
+	-sim | -xray | -os68k* | -v88r* \
+	      | -windows* | -osx | -abug | -netware* | -os9* \
 	      | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*)
 		;;
 	-mac*)
-		os=`echo $os | sed -e 's|mac|macos|'`
+		os=`echo "$os" | sed -e 's|mac|macos|'`
 		;;
 	-linux-dietlibc)
 		os=-linux-dietlibc
@@ -1430,10 +1421,10 @@ case $os in
 		os=`echo $os | sed -e 's|linux|linux-gnu|'`
 		;;
 	-sunos5*)
-		os=`echo $os | sed -e 's|sunos5|solaris2|'`
+		os=`echo "$os" | sed -e 's|sunos5|solaris2|'`
 		;;
 	-sunos6*)
-		os=`echo $os | sed -e 's|sunos6|solaris3|'`
+		os=`echo "$os" | sed -e 's|sunos6|solaris3|'`
 		;;
 	-opened*)
 		os=-openedition
@@ -1444,12 +1435,6 @@ case $os in
 	-wince*)
 		os=-wince
 		;;
-	-osfrose*)
-		os=-osfrose
-		;;
-	-osf*)
-		os=-osf
-		;;
 	-utek*)
 		os=-bsd
 		;;
@@ -1474,7 +1459,7 @@ case $os in
 	-nova*)
 		os=-rtmk-nova
 		;;
-	-ns2 )
+	-ns2)
 		os=-nextstep2
 		;;
 	-nsk*)
@@ -1496,7 +1481,7 @@ case $os in
 	-oss*)
 		os=-sysv3
 		;;
-	-svr4)
+	-svr4*)
 		os=-sysv4
 		;;
 	-svr3)
@@ -1511,24 +1496,28 @@ case $os in
 	-ose*)
 		os=-ose
 		;;
-	-es1800*)
-		os=-ose
-		;;
-	-xenix)
-		os=-xenix
-		;;
 	-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
 		os=-mint
 		;;
-	-aros*)
-		os=-aros
-		;;
 	-zvmoe)
 		os=-zvmoe
 		;;
 	-dicos*)
 		os=-dicos
 		;;
+	-pikeos*)
+		# Until real need of OS specific support for
+		# particular features comes up, bare metal
+		# configurations are quite functional.
+		case $basic_machine in
+		    arm*)
+			os=-eabi
+			;;
+		    *)
+			os=-elf
+			;;
+		esac
+		;;
 	-nacl*)
 		;;
 	-ios)
@@ -1538,7 +1527,7 @@ case $os in
 	*)
 		# Get rid of the `-' at the beginning of $os.
 		os=`echo $os | sed 's/[^-]*-//'`
-		echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2
+		echo Invalid configuration \`"$1"\': system \`"$os"\' not recognized 1>&2
 		exit 1
 		;;
 esac
@@ -1628,12 +1617,12 @@ case $basic_machine in
 	sparc-* | *-sun)
 		os=-sunos4.1.1
 		;;
+	pru-*)
+		os=-elf
+		;;
 	*-be)
 		os=-beos
 		;;
-	*-haiku)
-		os=-haiku
-		;;
 	*-ibm)
 		os=-aix
 		;;
@@ -1673,7 +1662,7 @@ case $basic_machine in
 	m88k-omron*)
 		os=-luna
 		;;
-	*-next )
+	*-next)
 		os=-nextstep
 		;;
 	*-sequent)
@@ -1688,9 +1677,6 @@ case $basic_machine in
 	i370-*)
 		os=-mvs
 		;;
-	*-next)
-		os=-nextstep3
-		;;
 	*-gould)
 		os=-sysv
 		;;
@@ -1800,15 +1786,15 @@ case $basic_machine in
 				vendor=stratus
 				;;
 		esac
-		basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"`
+		basic_machine=`echo "$basic_machine" | sed "s/unknown/$vendor/"`
 		;;
 esac
 
-echo $basic_machine$os
+echo "$basic_machine$os"
 exit
 
 # Local variables:
-# eval: (add-hook 'write-file-hooks 'time-stamp)
+# eval: (add-hook 'write-file-functions 'time-stamp)
 # time-stamp-start: "timestamp='"
 # time-stamp-format: "%:y-%02m-%02d"
 # time-stamp-end: "'"

Modified: polly/trunk/lib/External/isl/configure
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/configure?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/configure (original)
+++ polly/trunk/lib/External/isl/configure Sat Apr 21 01:34:22 2018
@@ -1,6 +1,6 @@
 #! /bin/sh
 # Guess values for system-dependent variables and create Makefiles.
-# Generated by GNU Autoconf 2.69 for isl 0.18.
+# Generated by GNU Autoconf 2.69 for isl 0.19.
 #
 # Report bugs to <isl-development at googlegroups.com>.
 #
@@ -590,8 +590,8 @@ MAKEFLAGS=
 # Identity of this package.
 PACKAGE_NAME='isl'
 PACKAGE_TARNAME='isl'
-PACKAGE_VERSION='0.18'
-PACKAGE_STRING='isl 0.18'
+PACKAGE_VERSION='0.19'
+PACKAGE_STRING='isl 0.19'
 PACKAGE_BUGREPORT='isl-development at googlegroups.com'
 PACKAGE_URL=''
 
@@ -1387,7 +1387,7 @@ if test "$ac_init_help" = "long"; then
   # Omit some internal or obsolete options to make the list less imposing.
   # This message is too long to be a string in the A/UX 3.1 sh.
   cat <<_ACEOF
-\`configure' configures isl 0.18 to adapt to many kinds of systems.
+\`configure' configures isl 0.19 to adapt to many kinds of systems.
 
 Usage: $0 [OPTION]... [VAR=VALUE]...
 
@@ -1458,7 +1458,7 @@ fi
 
 if test -n "$ac_init_help"; then
   case $ac_init_help in
-     short | recursive ) echo "Configuration of isl 0.18:";;
+     short | recursive ) echo "Configuration of isl 0.19:";;
    esac
   cat <<\_ACEOF
 
@@ -1589,7 +1589,7 @@ fi
 test -n "$ac_init_help" && exit $ac_status
 if $ac_init_version; then
   cat <<\_ACEOF
-isl configure 0.18
+isl configure 0.19
 generated by GNU Autoconf 2.69
 
 Copyright (C) 2012 Free Software Foundation, Inc.
@@ -2484,7 +2484,7 @@ cat >config.log <<_ACEOF
 This file contains any messages produced by compilers while
 running configure, to aid debugging if configure makes a mistake.
 
-It was created by isl $as_me 0.18, which was
+It was created by isl $as_me 0.19, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   $ $0 $@
@@ -3348,7 +3348,7 @@ fi
 
 # Define the identity of the package.
  PACKAGE='isl'
- VERSION='0.18'
+ VERSION='0.19'
 
 
 cat >>confdefs.h <<_ACEOF
@@ -3481,7 +3481,7 @@ fi
 AM_BACKSLASH='\'
 
 
-versioninfo=18:0:3
+versioninfo=19:0:0
 
 if test "x$prefix" != "xNONE"; then
 	prefix_wd=`cd $prefix && pwd`
@@ -17387,7 +17387,7 @@ if ${am_cv_pathless_PYTHON+:} false; the
   $as_echo_n "(cached) " >&6
 else
 
-	for am_cv_pathless_PYTHON in python python2 python3 python3.3 python3.2 python3.1 python3.0 python2.7  python2.6 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0 none; do
+	for am_cv_pathless_PYTHON in python python2 python3 python3.8 python3.7 python3.6 python3.5 python3.4 python3.3 python3.2 python3.1 python3.0 python2.7  python2.6 python2.5 python2.4 python2.3 python2.2 python2.1 python2.0 none; do
 	  test "$am_cv_pathless_PYTHON" = none && break
 	  prog="import sys
 # split strings by '.' and convert to numeric.  Append some zeros
@@ -20256,7 +20256,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_wri
 # report actual input values of CONFIG_FILES etc. instead of their
 # values after options handling.
 ac_log="
-This file was extended by isl $as_me 0.18, which was
+This file was extended by isl $as_me 0.19, which was
 generated by GNU Autoconf 2.69.  Invocation command line was
 
   CONFIG_FILES    = $CONFIG_FILES
@@ -20322,7 +20322,7 @@ _ACEOF
 cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
 ac_cs_version="\\
-isl config.status 0.18
+isl config.status 0.19
 configured by $0, generated by GNU Autoconf 2.69,
   with options \\"\$ac_cs_config\\"
 

Modified: polly/trunk/lib/External/isl/configure.ac
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/configure.ac?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/configure.ac (original)
+++ polly/trunk/lib/External/isl/configure.ac Sat Apr 21 01:34:22 2018
@@ -1,10 +1,10 @@
-AC_INIT([isl], [0.18], [isl-development at googlegroups.com])
+AC_INIT([isl], [0.19], [isl-development at googlegroups.com])
 AC_CONFIG_AUX_DIR([.])
 AC_CONFIG_MACRO_DIR([m4])
 AM_INIT_AUTOMAKE([foreign])
 m4_ifdef([AM_SILENT_RULES],[AM_SILENT_RULES([yes])])
 AC_SUBST(versioninfo)
-versioninfo=18:0:3
+versioninfo=19:0:0
 
 if test "x$prefix" != "xNONE"; then
 	prefix_wd=`cd $prefix && pwd`

Modified: polly/trunk/lib/External/isl/depcomp
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/depcomp?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/depcomp (original)
+++ polly/trunk/lib/External/isl/depcomp Sat Apr 21 01:34:22 2018
@@ -1,9 +1,9 @@
 #! /bin/sh
 # depcomp - compile a program generating dependencies as side-effects
 
-scriptversion=2013-05-30.07; # UTC
+scriptversion=2016-01-11.22; # UTC
 
-# Copyright (C) 1999-2014 Free Software Foundation, Inc.
+# Copyright (C) 1999-2017 Free Software Foundation, Inc.
 
 # This program is free software; you can redistribute it and/or modify
 # it under the terms of the GNU General Public License as published by
@@ -786,6 +786,6 @@ exit 0
 # eval: (add-hook 'write-file-hooks 'time-stamp)
 # time-stamp-start: "scriptversion="
 # time-stamp-format: "%:y-%02m-%02d.%02H"
-# time-stamp-time-zone: "UTC"
+# time-stamp-time-zone: "UTC0"
 # time-stamp-end: "; # UTC"
 # End:

Modified: polly/trunk/lib/External/isl/doc/Makefile.in
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/doc/Makefile.in?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/doc/Makefile.in (original)
+++ polly/trunk/lib/External/isl/doc/Makefile.in Sat Apr 21 01:34:22 2018
@@ -1,7 +1,7 @@
-# Makefile.in generated by automake 1.15 from Makefile.am.
+# Makefile.in generated by automake 1.15.1 from Makefile.am.
 # @configure_input@
 
-# Copyright (C) 1994-2014 Free Software Foundation, Inc.
+# Copyright (C) 1994-2017 Free Software Foundation, Inc.
 
 # This Makefile.in is free software; the Free Software Foundation
 # gives unlimited permission to copy and/or distribute it,

Modified: polly/trunk/lib/External/isl/doc/user.pod
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/doc/user.pod?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/doc/user.pod (original)
+++ polly/trunk/lib/External/isl/doc/user.pod Sat Apr 21 01:34:22 2018
@@ -270,6 +270,17 @@ be used as an alternative.
 
 =back
 
+=head3 Changes since isl-0.19
+
+=over
+
+=item * Zero-dimensional objects of type C<isl_multi_pw_aff> or
+C<isl_multi_union_pw_aff> can now keep track of an explicit domain.
+This explicit domain, if present, is taken into account
+by various operations that take such objects as input.
+
+=back
+
 =head1 License
 
 C<isl> is released under the MIT license.
@@ -733,9 +744,10 @@ For integer C<isl_val>s we additionally
 		__isl_keep isl_val *v2);
 
 An C<isl_val> can also be compared to an integer using the following
-function.  The result is undefined for NaN.
+functions.  The result of C<isl_val_cmp_si> undefined for NaN.
 
 	#include <isl/val.h>
+	isl_bool isl_val_gt_si(__isl_keep isl_val *v, long i);
 	int isl_val_cmp_si(__isl_keep isl_val *v, long i);
 
 The following unary operations are available on C<isl_val>s.
@@ -2749,6 +2761,10 @@ Objects of the value type do not have an
 The space of a multiple value is therefore always a set space.
 Similarly, the space of a multiple union piecewise
 affine expression is always a set space.
+If the base expressions are not total, then
+a corresponding zero-dimensional multiple expression may
+have an explicit domain that keeps track of the domain
+outside of any base expressions.
 
 The multiple expression types defined by C<isl>
 are C<isl_multi_val>, C<isl_multi_aff>, C<isl_multi_pw_aff>,
@@ -2969,10 +2985,7 @@ while there is only a single multiple ex
 an C<isl_multi_union_pw_aff>, which can therefore only live
 in a single space.  This means that not every
 C<isl_union_pw_multi_aff> can be converted to
-an C<isl_multi_union_pw_aff>.  Conversely, a zero-dimensional
-C<isl_multi_union_pw_aff> carries no information
-about any possible domain and therefore cannot be converted
-to an C<isl_union_pw_multi_aff>.  Moreover, the elements
+an C<isl_multi_union_pw_aff>.  Conversely, the elements
 of an C<isl_multi_union_pw_aff> may be defined over different domains,
 while each multiple expression inside an C<isl_union_pw_multi_aff>
 has a single domain.  The conversion of an C<isl_union_pw_multi_aff>
@@ -3973,18 +3986,26 @@ can be found then assign C<1> to C<*modu
 	__isl_give isl_val *isl_set_get_stride(
 		__isl_keep isl_set *set, int pos);
 
+	#include <isl/map.h>
+	__isl_give isl_stride_info *
+	isl_map_get_range_stride_info(
+		__isl_keep isl_map *map, int pos);
+
 Check if the values of the given set dimension are equal to
 some affine expression of the other dimensions (the offset)
+modulo some integer stride or
+check if the values of the given output dimensions are equal to
+some affine expression of the input dimensions (the offset)
 modulo some integer stride.
 If no more specific information can be found, then the stride
 is taken to be one and the offset is taken to be the zero expression.
-The function C<isl_set_get_stride_info> performs the same
-computation but only returns the stride.
-Otherwise,
+The function C<isl_set_get_stride> performs the same
+computation as C<isl_set_get_stride_info> but only returns the stride.
+For the other functions,
 the stride and offset can be extracted from the returned object
 using the following functions.
 
-	#include <isl/set.h>
+	#include <isl/stride_info.h>
 	__isl_give isl_val *isl_stride_info_get_stride(
 		__isl_keep isl_stride_info *si);
 	__isl_give isl_aff *isl_stride_info_get_offset(
@@ -3992,7 +4013,7 @@ using the following functions.
 
 The stride info object can be released using the following function.
 
-	#include <isl/set.h>
+	#include <isl/stride_info.h>
 	__isl_null isl_stride_info *isl_stride_info_free(
 		__isl_take isl_stride_info *si);
 
@@ -4569,8 +4590,9 @@ parameters.
 	__isl_give isl_set *isl_pw_aff_params(
 		__isl_take isl_pw_aff *pwa);
 
-The function C<isl_multi_union_pw_aff_domain> requires its
-input to have at least one set dimension.
+If no explicit domain was set on a zero-dimensional input to
+C<isl_multi_union_pw_aff_domain>, then this function will
+return a parameter set.
 
 	#include <isl/polynomial.h>
 	__isl_give isl_qpolynomial *
@@ -5738,6 +5760,14 @@ elements in the argument.
 
 The following functions evaluate a function in a point.
 
+	#include <isl/aff.h>
+	__isl_give isl_val *isl_aff_eval(
+		__isl_take isl_aff *aff,
+		__isl_take isl_point *pnt);
+	__isl_give isl_val *isl_pw_aff_eval(
+		__isl_take isl_pw_aff *pa,
+		__isl_take isl_point *pnt);
+
 	#include <isl/polynomial.h>
 	__isl_give isl_val *isl_pw_qpolynomial_eval(
 		__isl_take isl_pw_qpolynomial *pwqp,
@@ -5752,6 +5782,11 @@ The following functions evaluate a funct
 		__isl_take isl_union_pw_qpolynomial_fold *upwf,
 		__isl_take isl_point *pnt);
 
+These functions return NaN when evaluated at a void point.
+Note that C<isl_pw_aff_eval> returns NaN when the function is evaluated outside
+its definition domain, while C<isl_pw_qpolynomial_eval> returns zero
+when the function is evaluated outside its explicit domain.
+
 =item * Dimension manipulation
 
 It is usually not advisable to directly change the (input or output)
@@ -10649,7 +10684,8 @@ range of the schedule.
 The range of the options can consist of elements in one or more spaces,
 the names of which determine the effect of the option.
 The values of the range typically also refer to the schedule dimension
-to which the option applies.  In case of nested AST generation
+to which the option applies, with value C<0> representing
+the outermost schedule dimension.  In case of nested AST generation
 (see L</"Nested AST Generation">), these values refer to the position
 of the schedule dimension within the innermost AST generation.
 The constraints on the domain elements of

Modified: polly/trunk/lib/External/isl/include/isl/aff.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/aff.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/aff.h (original)
+++ polly/trunk/lib/External/isl/include/isl/aff.h Sat Apr 21 01:34:22 2018
@@ -9,6 +9,7 @@
 #include <isl/multi.h>
 #include <isl/union_set_type.h>
 #include <isl/val.h>
+#include <isl/point.h>
 
 #if defined(__cplusplus)
 extern "C" {
@@ -134,6 +135,9 @@ __isl_give isl_aff *isl_aff_gist(__isl_t
 __isl_give isl_aff *isl_aff_gist_params(__isl_take isl_aff *aff,
 	__isl_take isl_set *context);
 
+__isl_give isl_val *isl_aff_eval(__isl_take isl_aff *aff,
+	__isl_take isl_point *pnt);
+
 __isl_give isl_aff *isl_aff_pullback_aff(__isl_take isl_aff *aff1,
 	__isl_take isl_aff *aff2);
 __isl_overload
@@ -325,6 +329,9 @@ __isl_give isl_pw_aff *isl_pw_aff_gist(_
 __isl_give isl_pw_aff *isl_pw_aff_gist_params(__isl_take isl_pw_aff *pwaff,
 	__isl_take isl_set *context);
 
+__isl_give isl_val *isl_pw_aff_eval(__isl_take isl_pw_aff *pa,
+	__isl_take isl_point *pnt);
+
 __isl_overload
 __isl_give isl_pw_aff *isl_pw_aff_pullback_multi_aff(
 	__isl_take isl_pw_aff *pa, __isl_take isl_multi_aff *ma);

Modified: polly/trunk/lib/External/isl/include/isl/map.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/map.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/map.h (original)
+++ polly/trunk/lib/External/isl/include/isl/map.h Sat Apr 21 01:34:22 2018
@@ -23,6 +23,7 @@
 #include <isl/map_type.h>
 #include <isl/val.h>
 #include <isl/stdint.h>
+#include <isl/stride_info.h>
 
 #if defined(__cplusplus)
 extern "C" {
@@ -604,6 +605,9 @@ __isl_give isl_map *isl_map_gist_params(
 __isl_give isl_map *isl_map_gist_basic_map(__isl_take isl_map *map,
 	__isl_take isl_basic_map *context);
 
+__isl_give isl_stride_info *isl_map_get_range_stride_info(
+	__isl_keep isl_map *map, int pos);
+
 __isl_export
 __isl_give isl_map *isl_map_coalesce(__isl_take isl_map *map);
 

Modified: polly/trunk/lib/External/isl/include/isl/set.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/set.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/set.h (original)
+++ polly/trunk/lib/External/isl/include/isl/set.h Sat Apr 21 01:34:22 2018
@@ -18,6 +18,7 @@
 #include <isl/local_space.h>
 #include <isl/val.h>
 #include <isl/stdint.h>
+#include <isl/stride_info.h>
 
 #if defined(__cplusplus)
 extern "C" {
@@ -427,12 +428,6 @@ __isl_give isl_set *isl_set_gist_params(
 isl_stat isl_set_dim_residue_class_val(__isl_keep isl_set *set,
 	int pos, __isl_give isl_val **modulo, __isl_give isl_val **residue);
 
-struct isl_stride_info;
-typedef struct isl_stride_info isl_stride_info;
-__isl_give isl_val *isl_stride_info_get_stride(__isl_keep isl_stride_info *si);
-__isl_give isl_aff *isl_stride_info_get_offset(__isl_keep isl_stride_info *si);
-__isl_null isl_stride_info *isl_stride_info_free(
-	__isl_take isl_stride_info *si);
 __isl_give isl_stride_info *isl_set_get_stride_info(__isl_keep isl_set *set,
 	int pos);
 __isl_export

Added: polly/trunk/lib/External/isl/include/isl/stride_info.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/stride_info.h?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/stride_info.h (added)
+++ polly/trunk/lib/External/isl/include/isl/stride_info.h Sat Apr 21 01:34:22 2018
@@ -0,0 +1,27 @@
+/*
+ * Use of this software is governed by the MIT license
+ */
+
+#ifndef ISL_STRIDE_INFO_H
+#define ISL_STRIDE_INFO_H
+
+#include <isl/val.h>
+#include <isl/aff_type.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+struct isl_stride_info;
+typedef struct isl_stride_info isl_stride_info;
+
+__isl_give isl_val *isl_stride_info_get_stride(__isl_keep isl_stride_info *si);
+__isl_give isl_aff *isl_stride_info_get_offset(__isl_keep isl_stride_info *si);
+__isl_null isl_stride_info *isl_stride_info_free(
+	__isl_take isl_stride_info *si);
+
+#if defined(__cplusplus)
+}
+#endif
+
+#endif

Modified: polly/trunk/lib/External/isl/include/isl/val.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/val.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/val.h (original)
+++ polly/trunk/lib/External/isl/include/isl/val.h Sat Apr 21 01:34:22 2018
@@ -128,6 +128,7 @@ __isl_export
 isl_bool isl_val_le(__isl_keep isl_val *v1, __isl_keep isl_val *v2);
 __isl_export
 isl_bool isl_val_gt(__isl_keep isl_val *v1, __isl_keep isl_val *v2);
+isl_bool isl_val_gt_si(__isl_keep isl_val *v, long i);
 __isl_export
 isl_bool isl_val_ge(__isl_keep isl_val *v1, __isl_keep isl_val *v2);
 __isl_export

Modified: polly/trunk/lib/External/isl/include/isl/vec.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/include/isl/vec.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/include/isl/vec.h (original)
+++ polly/trunk/lib/External/isl/include/isl/vec.h Sat Apr 21 01:34:22 2018
@@ -65,6 +65,7 @@ __isl_give isl_vec *isl_vec_read_from_fi
 
 __isl_give isl_vec *isl_vec_drop_els(__isl_take isl_vec *vec,
 	unsigned pos, unsigned n);
+__isl_give isl_vec *isl_vec_add_els(__isl_take isl_vec *vec, unsigned n);
 __isl_give isl_vec *isl_vec_insert_els(__isl_take isl_vec *vec,
 	unsigned pos, unsigned n);
 __isl_give isl_vec *isl_vec_insert_zero_els(__isl_take isl_vec *vec,

Modified: polly/trunk/lib/External/isl/isl_aff.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_aff.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_aff.c (original)
+++ polly/trunk/lib/External/isl/isl_aff.c Sat Apr 21 01:34:22 2018
@@ -15,7 +15,6 @@
  */
 
 #include <isl_ctx_private.h>
-#define ISL_DIM_H
 #include <isl_map_private.h>
 #include <isl_union_map_private.h>
 #include <isl_aff_private.h>
@@ -23,10 +22,12 @@
 #include <isl_local_space_private.h>
 #include <isl_vec_private.h>
 #include <isl_mat_private.h>
+#include <isl/id.h>
 #include <isl/constraint.h>
 #include <isl_seq.h>
 #include <isl/set.h>
 #include <isl_val_private.h>
+#include <isl_point_private.h>
 #include <isl_config.h>
 
 #undef BASE
@@ -346,9 +347,16 @@ int isl_aff_find_dim_by_name(__isl_keep
 	return isl_local_space_find_dim_by_name(aff->ls, type, name);
 }
 
+/* Return the domain space of "aff".
+ */
+static __isl_keep isl_space *isl_aff_peek_domain_space(__isl_keep isl_aff *aff)
+{
+	return aff ? isl_local_space_peek_space(aff->ls) : NULL;
+}
+
 __isl_give isl_space *isl_aff_get_domain_space(__isl_keep isl_aff *aff)
 {
-	return aff ? isl_local_space_get_space(aff->ls) : NULL;
+	return isl_space_copy(isl_aff_peek_domain_space(aff));
 }
 
 __isl_give isl_space *isl_aff_get_space(__isl_keep isl_aff *aff)
@@ -2454,30 +2462,74 @@ __isl_give isl_aff *isl_aff_drop_dims(__
 	return aff;
 }
 
-/* Project the domain of the affine expression onto its parameter space.
- * The affine expression may not involve any of the domain dimensions.
+/* Drop the "n" domain dimensions starting at "first" from "aff",
+ * after checking that they do not appear in the affine expression.
  */
-__isl_give isl_aff *isl_aff_project_domain_on_params(__isl_take isl_aff *aff)
+static __isl_give isl_aff *drop_domain(__isl_take isl_aff *aff, unsigned first,
+	unsigned n)
 {
-	isl_space *space;
-	unsigned n;
-	int involves;
+	isl_bool involves;
 
-	n = isl_aff_dim(aff, isl_dim_in);
-	involves = isl_aff_involves_dims(aff, isl_dim_in, 0, n);
+	involves = isl_aff_involves_dims(aff, isl_dim_in, first, n);
 	if (involves < 0)
 		return isl_aff_free(aff);
 	if (involves)
 		isl_die(isl_aff_get_ctx(aff), isl_error_invalid,
 		    "affine expression involves some of the domain dimensions",
 		    return isl_aff_free(aff));
-	aff = isl_aff_drop_dims(aff, isl_dim_in, 0, n);
+	return isl_aff_drop_dims(aff, isl_dim_in, first, n);
+}
+
+/* Project the domain of the affine expression onto its parameter space.
+ * The affine expression may not involve any of the domain dimensions.
+ */
+__isl_give isl_aff *isl_aff_project_domain_on_params(__isl_take isl_aff *aff)
+{
+	isl_space *space;
+	unsigned n;
+
+	n = isl_aff_dim(aff, isl_dim_in);
+	aff = drop_domain(aff, 0, n);
 	space = isl_aff_get_domain_space(aff);
 	space = isl_space_params(space);
 	aff = isl_aff_reset_domain_space(aff, space);
 	return aff;
 }
 
+/* Check that the domain of "aff" is a product.
+ */
+static isl_stat check_domain_product(__isl_keep isl_aff *aff)
+{
+	isl_bool is_product;
+
+	is_product = isl_space_is_product(isl_aff_peek_domain_space(aff));
+	if (is_product < 0)
+		return isl_stat_error;
+	if (!is_product)
+		isl_die(isl_aff_get_ctx(aff), isl_error_invalid,
+			"domain is not a product", return isl_stat_error);
+	return isl_stat_ok;
+}
+
+/* Given an affine function with a domain of the form [A -> B] that
+ * does not depend on B, return the same function on domain A.
+ */
+__isl_give isl_aff *isl_aff_domain_factor_domain(__isl_take isl_aff *aff)
+{
+	isl_space *space;
+	int n, n_in;
+
+	if (check_domain_product(aff) < 0)
+		return isl_aff_free(aff);
+	space = isl_aff_get_domain_space(aff);
+	n = isl_space_dim(space, isl_dim_set);
+	space = isl_space_factor_domain(space);
+	n_in = isl_space_dim(space, isl_dim_set);
+	aff = drop_domain(aff, n_in, n - n_in);
+	aff = isl_aff_reset_domain_space(aff, space);
+	return aff;
+}
+
 /* Convert an affine expression defined over a parameter domain
  * into one that is defined over a zero-dimensional set.
  */
@@ -2631,12 +2683,12 @@ __isl_give isl_pw_aff *isl_pw_aff_from_a
 #undef DEFAULT_IS_ZERO
 #define DEFAULT_IS_ZERO 0
 
-#define NO_EVAL
 #define NO_OPT
 #define NO_LIFT
 #define NO_MORPH
 
 #include <isl_pw_templ.c>
+#include <isl_pw_eval.c>
 #include <isl_pw_hash.c>
 #include <isl_pw_union_opt.c>
 
@@ -3350,7 +3402,7 @@ isl_bool isl_multi_pw_aff_is_cst(__isl_k
 		return isl_bool_error;
 
 	for (i = 0; i < mpa->n; ++i) {
-		isl_bool is_cst = isl_pw_aff_is_cst(mpa->p[i]);
+		isl_bool is_cst = isl_pw_aff_is_cst(mpa->u.p[i]);
 		if (is_cst < 0 || !is_cst)
 			return is_cst;
 	}
@@ -3830,6 +3882,7 @@ error:
 #define DOMBASE set
 #define NO_DOMAIN
 
+#include <isl_multi_no_explicit_domain.c>
 #include <isl_multi_templ.c>
 #include <isl_multi_apply_set.c>
 #include <isl_multi_cmp.c>
@@ -4111,9 +4164,9 @@ static __isl_give isl_multi_aff *isl_mul
 		goto error;
 
 	for (i = 0; i < maff->n; ++i) {
-		maff->p[i] = isl_aff_substitute_equalities(maff->p[i],
+		maff->u.p[i] = isl_aff_substitute_equalities(maff->u.p[i],
 						    isl_basic_set_copy(eq));
-		if (!maff->p[i])
+		if (!maff->u.p[i])
 			goto error;
 	}
 
@@ -4135,8 +4188,8 @@ __isl_give isl_multi_aff *isl_multi_aff_
 		return NULL;
 
 	for (i = 0; i < maff->n; ++i) {
-		maff->p[i] = isl_aff_scale(maff->p[i], f);
-		if (!maff->p[i])
+		maff->u.p[i] = isl_aff_scale(maff->u.p[i], f);
+		if (!maff->u.p[i])
 			return isl_multi_aff_free(maff);
 	}
 
@@ -4233,7 +4286,6 @@ __isl_give isl_set *isl_multi_aff_lex_gt
 #define DEFAULT_IS_ZERO 0
 
 #define NO_SUB
-#define NO_EVAL
 #define NO_OPT
 #define NO_INVOLVES_DIMS
 #define NO_INSERT_DIMS
@@ -5396,8 +5448,9 @@ __isl_give isl_multi_aff *isl_multi_aff_
 		type = isl_dim_set;
 
 	for (i = 0; i < maff->n; ++i) {
-		maff->p[i] = isl_aff_substitute(maff->p[i], type, pos, subs);
-		if (!maff->p[i])
+		maff->u.p[i] = isl_aff_substitute(maff->u.p[i],
+						type, pos, subs);
+		if (!maff->u.p[i])
 			return isl_multi_aff_free(maff);
 	}
 
@@ -5538,7 +5591,7 @@ void isl_seq_preimage(isl_int *dst, isl_
 
 		if (isl_int_is_zero(src[offset]))
 			continue;
-		isl_int_set(c1, ma->p[i]->v->el[0]);
+		isl_int_set(c1, ma->u.p[i]->v->el[0]);
 		isl_int_mul(c2, f, src[offset]);
 		isl_int_gcd(g, c1, c2);
 		isl_int_divexact(c1, c1, g);
@@ -5548,19 +5601,19 @@ void isl_seq_preimage(isl_int *dst, isl_
 		o_dst = has_denom;
 		o_src = 1;
 		isl_seq_combine(dst + o_dst, c1, dst + o_dst,
-				c2, ma->p[i]->v->el + o_src, 1 + n_param);
+				c2, ma->u.p[i]->v->el + o_src, 1 + n_param);
 		o_dst += 1 + n_param;
 		o_src += 1 + n_param;
 		isl_seq_scale(dst + o_dst, dst + o_dst, c1, n_before);
 		o_dst += n_before;
 		isl_seq_combine(dst + o_dst, c1, dst + o_dst,
-				c2, ma->p[i]->v->el + o_src, n_in);
+				c2, ma->u.p[i]->v->el + o_src, n_in);
 		o_dst += n_in;
 		o_src += n_in;
 		isl_seq_scale(dst + o_dst, dst + o_dst, c1, n_after);
 		o_dst += n_after;
 		isl_seq_combine(dst + o_dst, c1, dst + o_dst,
-				c2, ma->p[i]->v->el + o_src, n_div_ma);
+				c2, ma->u.p[i]->v->el + o_src, n_div_ma);
 		o_dst += n_div_ma;
 		o_src += n_div_ma;
 		isl_seq_scale(dst + o_dst, dst + o_dst, c1, n_div_bmap);
@@ -5601,7 +5654,7 @@ __isl_give isl_aff *isl_aff_pullback_mul
 		goto error;
 
 	n_div_aff = isl_aff_dim(aff, isl_dim_div);
-	n_div_ma = ma->n ? isl_aff_dim(ma->p[0], isl_dim_div) : 0;
+	n_div_ma = ma->n ? isl_aff_dim(ma->u.p[0], isl_dim_div) : 0;
 
 	ls = isl_aff_get_domain_local_space(aff);
 	ls = isl_local_space_preimage_multi_aff(ls, isl_multi_aff_copy(ma));
@@ -5669,9 +5722,9 @@ static __isl_give isl_multi_aff *isl_mul
 				isl_multi_aff_get_space(ma1));
 
 	for (i = 0; i < ma1->n; ++i) {
-		ma1->p[i] = isl_aff_pullback_multi_aff(ma1->p[i],
+		ma1->u.p[i] = isl_aff_pullback_multi_aff(ma1->u.p[i],
 						    isl_multi_aff_copy(ma2));
-		if (!ma1->p[i])
+		if (!ma1->u.p[i])
 			goto error;
 	}
 
@@ -5766,10 +5819,10 @@ __isl_give isl_multi_aff *isl_multi_aff_
 		return NULL;
 
 	for (i = 1; i < maff->n; ++i)
-		maff->p[0] = isl_aff_align_divs(maff->p[0], maff->p[i]);
+		maff->u.p[0] = isl_aff_align_divs(maff->u.p[0], maff->u.p[i]);
 	for (i = 1; i < maff->n; ++i) {
-		maff->p[i] = isl_aff_align_divs(maff->p[i], maff->p[0]);
-		if (!maff->p[i])
+		maff->u.p[i] = isl_aff_align_divs(maff->u.p[i], maff->u.p[0]);
+		if (!maff->u.p[i])
 			return isl_multi_aff_free(maff);
 	}
 
@@ -5822,7 +5875,7 @@ __isl_give isl_multi_aff *isl_multi_aff_
 	if (!maff)
 		return NULL;
 
-	n_div = isl_aff_dim(maff->p[0], isl_dim_div);
+	n_div = isl_aff_dim(maff->u.p[0], isl_dim_div);
 	space = isl_multi_aff_get_space(maff);
 	space = isl_space_lift(isl_space_domain(space), n_div);
 	space = isl_space_extend_domain_with_range(space,
@@ -5833,14 +5886,14 @@ __isl_give isl_multi_aff *isl_multi_aff_
 	maff->space = space;
 
 	if (ls) {
-		*ls = isl_aff_get_domain_local_space(maff->p[0]);
+		*ls = isl_aff_get_domain_local_space(maff->u.p[0]);
 		if (!*ls)
 			return isl_multi_aff_free(maff);
 	}
 
 	for (i = 0; i < maff->n; ++i) {
-		maff->p[i] = isl_aff_lift(maff->p[i]);
-		if (!maff->p[i])
+		maff->u.p[i] = isl_aff_lift(maff->u.p[i]);
+		if (!maff->u.p[i])
 			goto error;
 	}
 
@@ -6274,14 +6327,32 @@ error:
 #undef DOMBASE
 #define DOMBASE set
 
+#include <isl_multi_explicit_domain.c>
+#include <isl_multi_pw_aff_explicit_domain.c>
 #include <isl_multi_templ.c>
 #include <isl_multi_apply_set.c>
 #include <isl_multi_coalesce.c>
 #include <isl_multi_dims.c>
 #include <isl_multi_gist.c>
 #include <isl_multi_hash.c>
+#include <isl_multi_align_set.c>
 #include <isl_multi_intersect.c>
 
+/* Does "mpa" have a non-trivial explicit domain?
+ *
+ * The explicit domain, if present, is trivial if it represents
+ * an (obviously) universe set.
+ */
+isl_bool isl_multi_pw_aff_has_non_trivial_domain(
+	__isl_keep isl_multi_pw_aff *mpa)
+{
+	if (!mpa)
+		return isl_bool_error;
+	if (!isl_multi_pw_aff_has_explicit_domain(mpa))
+		return isl_bool_false;
+	return isl_bool_not(isl_set_plain_is_universe(mpa->u.dom));
+}
+
 /* Scale the elements of "pma" by the corresponding elements of "mv".
  */
 __isl_give isl_pw_multi_aff *isl_pw_multi_aff_scale_multi_val(
@@ -6434,7 +6505,7 @@ static __isl_give isl_map *map_from_mult
 		isl_pw_aff *pa;
 		isl_map *map_i;
 
-		pa = isl_pw_aff_copy(mpa->p[i]);
+		pa = isl_pw_aff_copy(mpa->u.p[i]);
 		map_i = map_from_pw_aff(pa);
 
 		map = isl_map_flat_range_product(map, map_i);
@@ -6489,6 +6560,29 @@ error:
 
 /* Construct and return a piecewise multi affine expression
  * that is equal to the given multi piecewise affine expression
+ * on the shared domain of the piecewise affine expressions,
+ * in the special case of a 0D multi piecewise affine expression.
+ *
+ * Create a piecewise multi affine expression with the explicit domain of
+ * the 0D multi piecewise affine expression as domain.
+ */
+static __isl_give isl_pw_multi_aff *isl_pw_multi_aff_from_multi_pw_aff_0D(
+	__isl_take isl_multi_pw_aff *mpa)
+{
+	isl_space *space;
+	isl_set *dom;
+	isl_multi_aff *ma;
+
+	space = isl_multi_pw_aff_get_space(mpa);
+	dom = isl_multi_pw_aff_get_explicit_domain(mpa);
+	isl_multi_pw_aff_free(mpa);
+
+	ma = isl_multi_aff_zero(space);
+	return isl_pw_multi_aff_alloc(dom, ma);
+}
+
+/* Construct and return a piecewise multi affine expression
+ * that is equal to the given multi piecewise affine expression
  * on the shared domain of the piecewise affine expressions.
  */
 __isl_give isl_pw_multi_aff *isl_pw_multi_aff_from_multi_pw_aff(
@@ -6502,13 +6596,10 @@ __isl_give isl_pw_multi_aff *isl_pw_mult
 	if (!mpa)
 		return NULL;
 
-	space = isl_multi_pw_aff_get_space(mpa);
-
-	if (mpa->n == 0) {
-		isl_multi_pw_aff_free(mpa);
-		return isl_pw_multi_aff_zero(space);
-	}
+	if (mpa->n == 0)
+		return isl_pw_multi_aff_from_multi_pw_aff_0D(mpa);
 
+	space = isl_multi_pw_aff_get_space(mpa);
 	pa = isl_multi_pw_aff_get_pw_aff(mpa, 0);
 	pma = isl_pw_multi_aff_from_pw_aff(pa);
 
@@ -6554,6 +6645,10 @@ __isl_give isl_multi_pw_aff *isl_multi_p
 
 /* Construct and return a multi piecewise affine expression
  * that is equal to the given piecewise multi affine expression.
+ *
+ * If the resulting multi piecewise affine expression has
+ * an explicit domain, then assign it the domain of the input.
+ * In other cases, the domain is stored in the individual elements.
  */
 __isl_give isl_multi_pw_aff *isl_multi_pw_aff_from_pw_multi_aff(
 	__isl_take isl_pw_multi_aff *pma)
@@ -6575,6 +6670,12 @@ __isl_give isl_multi_pw_aff *isl_multi_p
 		pa = isl_pw_multi_aff_get_pw_aff(pma, i);
 		mpa = isl_multi_pw_aff_set_pw_aff(mpa, i, pa);
 	}
+	if (isl_multi_pw_aff_has_explicit_domain(mpa)) {
+		isl_set *dom;
+
+		dom = isl_pw_multi_aff_domain(isl_pw_multi_aff_copy(pma));
+		mpa = isl_multi_pw_aff_intersect_domain(mpa, dom);
+	}
 
 	isl_pw_multi_aff_free(pma);
 	return mpa;
@@ -6657,7 +6758,7 @@ isl_bool isl_multi_pw_aff_is_equal(__isl
 		return equal;
 
 	for (i = 0; i < mpa1->n; ++i) {
-		equal = isl_pw_aff_is_equal(mpa1->p[i], mpa2->p[i]);
+		equal = isl_pw_aff_is_equal(mpa1->u.p[i], mpa2->u.p[i]);
 		if (equal < 0 || !equal)
 			return equal;
 	}
@@ -6706,6 +6807,9 @@ isl_bool isl_pw_multi_aff_is_equal(__isl
  * In other words, plug in "ma" in "mpa".
  *
  * The parameters of "mpa" and "ma" are assumed to have been aligned.
+ *
+ * If "mpa" has an explicit domain, then it is this domain
+ * that needs to undergo a pullback, i.e., a preimage.
  */
 static __isl_give isl_multi_pw_aff *isl_multi_pw_aff_pullback_multi_aff_aligned(
 	__isl_take isl_multi_pw_aff *mpa, __isl_take isl_multi_aff *ma)
@@ -6723,9 +6827,15 @@ static __isl_give isl_multi_pw_aff *isl_
 		goto error;
 
 	for (i = 0; i < mpa->n; ++i) {
-		mpa->p[i] = isl_pw_aff_pullback_multi_aff(mpa->p[i],
+		mpa->u.p[i] = isl_pw_aff_pullback_multi_aff(mpa->u.p[i],
 						    isl_multi_aff_copy(ma));
-		if (!mpa->p[i])
+		if (!mpa->u.p[i])
+			goto error;
+	}
+	if (isl_multi_pw_aff_has_explicit_domain(mpa)) {
+		mpa->u.dom = isl_set_preimage_multi_aff(mpa->u.dom,
+							isl_multi_aff_copy(ma));
+		if (!mpa->u.dom)
 			goto error;
 	}
 
@@ -6768,6 +6878,9 @@ error:
  * In other words, plug in "pma" in "mpa".
  *
  * The parameters of "mpa" and "mpa" are assumed to have been aligned.
+ *
+ * If "mpa" has an explicit domain, then it is this domain
+ * that needs to undergo a pullback, i.e., a preimage.
  */
 static __isl_give isl_multi_pw_aff *
 isl_multi_pw_aff_pullback_pw_multi_aff_aligned(
@@ -6784,9 +6897,15 @@ isl_multi_pw_aff_pullback_pw_multi_aff_a
 				isl_multi_pw_aff_get_space(mpa));
 
 	for (i = 0; i < mpa->n; ++i) {
-		mpa->p[i] = isl_pw_aff_pullback_pw_multi_aff_aligned(mpa->p[i],
+		mpa->u.p[i] = isl_pw_aff_pullback_pw_multi_aff_aligned(
+				    mpa->u.p[i], isl_pw_multi_aff_copy(pma));
+		if (!mpa->u.p[i])
+			goto error;
+	}
+	if (isl_multi_pw_aff_has_explicit_domain(mpa)) {
+		mpa->u.dom = isl_set_preimage_pw_multi_aff(mpa->u.dom,
 						    isl_pw_multi_aff_copy(pma));
-		if (!mpa->p[i])
+		if (!mpa->u.dom)
 			goto error;
 	}
 
@@ -7019,6 +7138,9 @@ __isl_give isl_pw_aff *isl_pw_aff_pullba
  * The parameters of "mpa1" and "mpa2" are assumed to have been aligned.
  *
  * We pullback each member of "mpa1" in turn.
+ *
+ * If "mpa1" has an explicit domain, then it is this domain
+ * that needs to undergo a pullback instead, i.e., a preimage.
  */
 static __isl_give isl_multi_pw_aff *
 isl_multi_pw_aff_pullback_multi_pw_aff_aligned(
@@ -7035,12 +7157,18 @@ isl_multi_pw_aff_pullback_multi_pw_aff_a
 				isl_multi_pw_aff_get_space(mpa1));
 
 	for (i = 0; i < mpa1->n; ++i) {
-		mpa1->p[i] = isl_pw_aff_pullback_multi_pw_aff_aligned(
-				mpa1->p[i], isl_multi_pw_aff_copy(mpa2));
-		if (!mpa1->p[i])
+		mpa1->u.p[i] = isl_pw_aff_pullback_multi_pw_aff_aligned(
+				mpa1->u.p[i], isl_multi_pw_aff_copy(mpa2));
+		if (!mpa1->u.p[i])
 			goto error;
 	}
 
+	if (isl_multi_pw_aff_has_explicit_domain(mpa1)) {
+		mpa1->u.dom = isl_set_preimage_multi_pw_aff(mpa1->u.dom,
+						isl_multi_pw_aff_copy(mpa2));
+		if (!mpa1->u.dom)
+			goto error;
+	}
 	mpa1 = isl_multi_pw_aff_reset_space(mpa1, space);
 
 	isl_multi_pw_aff_free(mpa2);
@@ -8072,14 +8200,42 @@ error:
 #define NO_IDENTITY
 #define NO_GIST
 
+#include <isl_multi_explicit_domain.c>
+#include <isl_multi_union_pw_aff_explicit_domain.c>
 #include <isl_multi_templ.c>
 #include <isl_multi_apply_set.c>
 #include <isl_multi_apply_union_set.c>
 #include <isl_multi_coalesce.c>
 #include <isl_multi_floor.c>
 #include <isl_multi_gist.c>
+#include <isl_multi_align_set.c>
+#include <isl_multi_align_union_set.c>
 #include <isl_multi_intersect.c>
 
+/* Does "mupa" have a non-trivial explicit domain?
+ *
+ * The explicit domain, if present, is trivial if it represents
+ * an (obviously) universe parameter set.
+ */
+isl_bool isl_multi_union_pw_aff_has_non_trivial_domain(
+	__isl_keep isl_multi_union_pw_aff *mupa)
+{
+	isl_bool is_params, trivial;
+	isl_set *set;
+
+	if (!mupa)
+		return isl_bool_error;
+	if (!isl_multi_union_pw_aff_has_explicit_domain(mupa))
+		return isl_bool_false;
+	is_params = isl_union_set_is_params(mupa->u.dom);
+	if (is_params < 0 || !is_params)
+		return isl_bool_not(is_params);
+	set = isl_set_from_union_set(isl_union_set_copy(mupa->u.dom));
+	trivial = isl_set_plain_is_universe(set);
+	isl_set_free(set);
+	return isl_bool_not(trivial);
+}
+
 /* Construct a multiple union piecewise affine expression
  * in the given space with value zero in each of the output dimensions.
  *
@@ -8119,15 +8275,70 @@ error:
  * the defined expression on the symmetric difference of the domains.
  *
  * We simply iterate over the elements in both arguments and
- * call isl_union_pw_aff_union_add on each of them.
+ * call isl_union_pw_aff_union_add on each of them, if there is
+ * at least one element.
+ *
+ * Otherwise, the two expressions have an explicit domain and
+ * the union of these explicit domains is computed.
+ * This assumes that the explicit domains are either both in terms
+ * of specific domains elements or both in terms of parameters.
+ * However, if one of the expressions does not have any constraints
+ * on its explicit domain, then this is allowed as well and the result
+ * is the expression with no constraints on its explicit domain.
  */
 static __isl_give isl_multi_union_pw_aff *
 isl_multi_union_pw_aff_union_add_aligned(
 	__isl_take isl_multi_union_pw_aff *mupa1,
 	__isl_take isl_multi_union_pw_aff *mupa2)
 {
-	return isl_multi_union_pw_aff_bin_op(mupa1, mupa2,
+	isl_bool has_domain, is_params1, is_params2;
+
+	if (isl_multi_union_pw_aff_check_equal_space(mupa1, mupa2) < 0)
+		goto error;
+	if (mupa1->n > 0)
+		return isl_multi_union_pw_aff_bin_op(mupa1, mupa2,
 					    &isl_union_pw_aff_union_add);
+	if (isl_multi_union_pw_aff_check_has_explicit_domain(mupa1) < 0 ||
+	    isl_multi_union_pw_aff_check_has_explicit_domain(mupa2) < 0)
+		goto error;
+
+	has_domain = isl_multi_union_pw_aff_has_non_trivial_domain(mupa1);
+	if (has_domain < 0)
+		goto error;
+	if (!has_domain) {
+		isl_multi_union_pw_aff_free(mupa2);
+		return mupa1;
+	}
+	has_domain = isl_multi_union_pw_aff_has_non_trivial_domain(mupa2);
+	if (has_domain < 0)
+		goto error;
+	if (!has_domain) {
+		isl_multi_union_pw_aff_free(mupa1);
+		return mupa2;
+	}
+
+	is_params1 = isl_union_set_is_params(mupa1->u.dom);
+	is_params2 = isl_union_set_is_params(mupa2->u.dom);
+	if (is_params1 < 0 || is_params2 < 0)
+		goto error;
+	if (is_params1 != is_params2)
+		isl_die(isl_multi_union_pw_aff_get_ctx(mupa1),
+			isl_error_invalid,
+			"cannot compute union of concrete domain and "
+			"parameter constraints", goto error);
+	mupa1 = isl_multi_union_pw_aff_cow(mupa1);
+	if (!mupa1)
+		goto error;
+	mupa1->u.dom = isl_union_set_union(mupa1->u.dom,
+					    isl_union_set_copy(mupa2->u.dom));
+	if (!mupa1->u.dom)
+		goto error;
+	isl_multi_union_pw_aff_free(mupa2);
+	return mupa1;
+error:
+	isl_multi_union_pw_aff_free(mupa1);
+	isl_multi_union_pw_aff_free(mupa2);
+	return NULL;
 }
 
 /* Compute the sum of "mupa1" and "mupa2" on the union of their domains,
@@ -8222,6 +8433,10 @@ static isl_stat extract_space(__isl_take
  *
  * In order to be able to perform the conversion, the input
  * needs to be non-empty and may only involve a single range space.
+ *
+ * If the resulting multi union piecewise affine expression has
+ * an explicit domain, then assign it the domain of the input.
+ * In other cases, the domain is stored in the individual elements.
  */
 __isl_give isl_multi_union_pw_aff *
 isl_multi_union_pw_aff_from_union_pw_multi_aff(
@@ -8253,6 +8468,14 @@ isl_multi_union_pw_aff_from_union_pw_mul
 		upa = isl_union_pw_multi_aff_get_union_pw_aff(upma, i);
 		mupa = isl_multi_union_pw_aff_set_union_pw_aff(mupa, i, upa);
 	}
+	if (isl_multi_union_pw_aff_has_explicit_domain(mupa)) {
+		isl_union_set *dom;
+		isl_union_pw_multi_aff *copy;
+
+		copy = isl_union_pw_multi_aff_copy(upma);
+		dom = isl_union_pw_multi_aff_domain(copy);
+		mupa = isl_multi_union_pw_aff_intersect_domain(mupa, dom);
+	}
 
 	isl_union_pw_multi_aff_free(upma);
 	return mupa;
@@ -8355,6 +8578,10 @@ __isl_give isl_multi_union_pw_aff *isl_m
 /* Return a multiple union piecewise affine expression
  * that is equal to "pma" on "domain", assuming "domain" and "pma"
  * have been aligned.
+ *
+ * If the resulting multi union piecewise affine expression has
+ * an explicit domain, then assign it the input domain.
+ * In other cases, the domain is stored in the individual elements.
  */
 static __isl_give isl_multi_union_pw_aff *
 isl_multi_union_pw_aff_pw_multi_aff_on_domain_aligned(
@@ -8379,6 +8606,9 @@ isl_multi_union_pw_aff_pw_multi_aff_on_d
 					    isl_union_set_copy(domain), pa);
 		mupa = isl_multi_union_pw_aff_set_union_pw_aff(mupa, i, upa);
 	}
+	if (isl_multi_union_pw_aff_has_explicit_domain(mupa))
+		mupa = isl_multi_union_pw_aff_intersect_domain(mupa,
+						    isl_union_set_copy(domain));
 
 	isl_union_set_free(domain);
 	isl_pw_multi_aff_free(pma);
@@ -8420,6 +8650,8 @@ error:
 
 /* Return a union set containing those elements in the domains
  * of the elements of "mupa" where they are all zero.
+ *
+ * If there are no elements, then simply return the entire domain.
  */
 __isl_give isl_union_set *isl_multi_union_pw_aff_zero_union_set(
 	__isl_take isl_multi_union_pw_aff *mupa)
@@ -8433,9 +8665,7 @@ __isl_give isl_union_set *isl_multi_unio
 
 	n = isl_multi_union_pw_aff_dim(mupa, isl_dim_set);
 	if (n == 0)
-		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
-			"cannot determine zero set "
-			"of zero-dimensional function", goto error);
+		return isl_multi_union_pw_aff_domain(mupa);
 
 	upa = isl_multi_union_pw_aff_get_union_pw_aff(mupa, 0);
 	zero = isl_union_pw_aff_zero_union_set(upa);
@@ -8451,9 +8681,37 @@ __isl_give isl_union_set *isl_multi_unio
 
 	isl_multi_union_pw_aff_free(mupa);
 	return zero;
-error:
-	isl_multi_union_pw_aff_free(mupa);
-	return NULL;
+}
+
+/* Construct a union map mapping the shared domain
+ * of the union piecewise affine expressions to the range of "mupa"
+ * in the special case of a 0D multi union piecewise affine expression.
+ *
+ * Construct a map between the explicit domain of "mupa" and
+ * the range space.
+ * Note that this assumes that the domain consists of explicit elements.
+ */
+static __isl_give isl_union_map *isl_union_map_from_multi_union_pw_aff_0D(
+	__isl_take isl_multi_union_pw_aff *mupa)
+{
+	isl_bool is_params;
+	isl_space *space;
+	isl_union_set *dom, *ran;
+
+	space = isl_multi_union_pw_aff_get_space(mupa);
+	dom = isl_multi_union_pw_aff_domain(mupa);
+	ran = isl_union_set_from_set(isl_set_universe(space));
+
+	is_params = isl_union_set_is_params(dom);
+	if (is_params < 0)
+		dom = isl_union_set_free(dom);
+	else if (is_params)
+		isl_die(isl_union_set_get_ctx(dom), isl_error_invalid,
+			"cannot create union map from expression without "
+			"explicit domain elements",
+			dom = isl_union_set_free(dom));
+
+	return isl_union_map_from_domain_and_range(dom, ran);
 }
 
 /* Construct a union map mapping the shared domain
@@ -8461,8 +8719,8 @@ error:
  * with each dimension in the range equated to the
  * corresponding union piecewise affine expression.
  *
- * The input cannot be zero-dimensional as there is
- * no way to extract a domain from a zero-dimensional isl_multi_union_pw_aff.
+ * If the input is zero-dimensional, then construct a mapping
+ * from its explicit domain.
  */
 __isl_give isl_union_map *isl_union_map_from_multi_union_pw_aff(
 	__isl_take isl_multi_union_pw_aff *mupa)
@@ -8477,9 +8735,7 @@ __isl_give isl_union_map *isl_union_map_
 
 	n = isl_multi_union_pw_aff_dim(mupa, isl_dim_set);
 	if (n == 0)
-		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
-			"cannot determine domain of zero-dimensional "
-			"isl_multi_union_pw_aff", goto error);
+		return isl_union_map_from_multi_union_pw_aff_0D(mupa);
 
 	upa = isl_multi_union_pw_aff_get_union_pw_aff(mupa, 0);
 	umap = isl_union_map_from_union_pw_aff(upa);
@@ -8497,9 +8753,6 @@ __isl_give isl_union_map *isl_union_map_
 
 	isl_multi_union_pw_aff_free(mupa);
 	return umap;
-error:
-	isl_multi_union_pw_aff_free(mupa);
-	return NULL;
 }
 
 /* Internal data structure for isl_union_pw_multi_aff_reset_range_space.
@@ -8559,10 +8812,32 @@ isl_union_pw_multi_aff_reset_range_space
 }
 
 /* Construct and return a union piecewise multi affine expression
+ * that is equal to the given multi union piecewise affine expression,
+ * in the special case of a 0D multi union piecewise affine expression.
+ *
+ * Construct a union piecewise multi affine expression
+ * on top of the explicit domain of the input.
+ */
+__isl_give isl_union_pw_multi_aff *
+isl_union_pw_multi_aff_from_multi_union_pw_aff_0D(
+	__isl_take isl_multi_union_pw_aff *mupa)
+{
+	isl_space *space;
+	isl_multi_val *mv;
+	isl_union_set *domain;
+
+	space = isl_multi_union_pw_aff_get_space(mupa);
+	mv = isl_multi_val_zero(space);
+	domain = isl_multi_union_pw_aff_domain(mupa);
+	return isl_union_pw_multi_aff_multi_val_on_domain(domain, mv);
+}
+
+/* Construct and return a union piecewise multi affine expression
  * that is equal to the given multi union piecewise affine expression.
  *
- * In order to be able to perform the conversion, the input
- * needs to have a least one output dimension.
+ * If the input is zero-dimensional, then
+ * construct a union piecewise multi affine expression
+ * on top of the explicit domain of the input.
  */
 __isl_give isl_union_pw_multi_aff *
 isl_union_pw_multi_aff_from_multi_union_pw_aff(
@@ -8578,9 +8853,7 @@ isl_union_pw_multi_aff_from_multi_union_
 
 	n = isl_multi_union_pw_aff_dim(mupa, isl_dim_set);
 	if (n == 0)
-		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
-			"cannot determine domain of zero-dimensional "
-			"isl_multi_union_pw_aff", goto error);
+		return isl_union_pw_multi_aff_from_multi_union_pw_aff_0D(mupa);
 
 	space = isl_multi_union_pw_aff_get_space(mupa);
 	upa = isl_multi_union_pw_aff_get_union_pw_aff(mupa, 0);
@@ -8598,9 +8871,20 @@ isl_union_pw_multi_aff_from_multi_union_
 
 	isl_multi_union_pw_aff_free(mupa);
 	return upma;
-error:
-	isl_multi_union_pw_aff_free(mupa);
-	return NULL;
+}
+
+/* Intersect the range of "mupa" with "range",
+ * in the special case where "mupa" is 0D.
+ *
+ * Intersect the domain of "mupa" with the constraints on the parameters
+ * of "range".
+ */
+static __isl_give isl_multi_union_pw_aff *mupa_intersect_range_0D(
+	__isl_take isl_multi_union_pw_aff *mupa, __isl_take isl_set *range)
+{
+	range = isl_set_params(range);
+	mupa = isl_multi_union_pw_aff_intersect_params(mupa, range);
+	return mupa;
 }
 
 /* Intersect the range of "mupa" with "range".
@@ -8630,9 +8914,7 @@ __isl_give isl_multi_union_pw_aff *isl_m
 			"space don't match", goto error);
 	n = isl_multi_union_pw_aff_dim(mupa, isl_dim_set);
 	if (n == 0)
-		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
-			"cannot intersect range of zero-dimensional "
-			"isl_multi_union_pw_aff", goto error);
+		return mupa_intersect_range_0D(mupa, range);
 
 	upma = isl_union_pw_multi_aff_from_multi_union_pw_aff(
 					isl_multi_union_pw_aff_copy(mupa));
@@ -8647,7 +8929,28 @@ error:
 	return NULL;
 }
 
+/* Return the shared domain of the elements of "mupa",
+ * in the special case where "mupa" is zero-dimensional.
+ *
+ * Return the explicit domain of "mupa".
+ * Note that this domain may be a parameter set, either
+ * because "mupa" is meant to live in a set space or
+ * because no explicit domain has been set.
+ */
+__isl_give isl_union_set *isl_multi_union_pw_aff_domain_0D(
+	__isl_take isl_multi_union_pw_aff *mupa)
+{
+	isl_union_set *dom;
+
+	dom = isl_multi_union_pw_aff_get_explicit_domain(mupa);
+	isl_multi_union_pw_aff_free(mupa);
+
+	return dom;
+}
+
 /* Return the shared domain of the elements of "mupa".
+ *
+ * If "mupa" is zero-dimensional, then return its explicit domain.
  */
 __isl_give isl_union_set *isl_multi_union_pw_aff_domain(
 	__isl_take isl_multi_union_pw_aff *mupa)
@@ -8661,8 +8964,7 @@ __isl_give isl_union_set *isl_multi_unio
 
 	n = isl_multi_union_pw_aff_dim(mupa, isl_dim_set);
 	if (n == 0)
-		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
-			"cannot determine domain", goto error);
+		return isl_multi_union_pw_aff_domain_0D(mupa);
 
 	upa = isl_multi_union_pw_aff_get_union_pw_aff(mupa, 0);
 	dom = isl_union_pw_aff_domain(upa);
@@ -8676,9 +8978,6 @@ __isl_give isl_union_set *isl_multi_unio
 
 	isl_multi_union_pw_aff_free(mupa);
 	return dom;
-error:
-	isl_multi_union_pw_aff_free(mupa);
-	return NULL;
 }
 
 /* Apply "aff" to "mupa".  The space of "mupa" is equal to the domain of "aff".
@@ -8785,10 +9084,25 @@ error:
 	return NULL;
 }
 
+/* Apply "ma" to "mupa", in the special case where "mupa" is 0D.
+ * The space of "mupa" is known to be compatible with the domain of "ma".
+ *
+ * Construct an isl_multi_union_pw_aff that is equal to "ma"
+ * on the domain of "mupa".
+ */
+static __isl_give isl_multi_union_pw_aff *mupa_apply_multi_aff_0D(
+	__isl_take isl_multi_union_pw_aff *mupa, __isl_take isl_multi_aff *ma)
+{
+	isl_union_set *dom;
+
+	dom = isl_multi_union_pw_aff_domain(mupa);
+	ma = isl_multi_aff_project_domain_on_params(ma);
+
+	return isl_multi_union_pw_aff_multi_aff_on_domain(dom, ma);
+}
+
 /* Apply "ma" to "mupa".  The space of "mupa" needs to be compatible
  * with the domain of "ma".
- * Furthermore, the dimension of this space needs to be greater than zero,
- * unless the dimension of the target space of "ma" is also zero.
  * The result is defined over the shared domain of the elements of "mupa"
  */
 __isl_give isl_multi_union_pw_aff *isl_multi_union_pw_aff_apply_multi_aff(
@@ -8817,9 +9131,8 @@ __isl_give isl_multi_union_pw_aff *isl_m
 		isl_die(isl_multi_aff_get_ctx(ma), isl_error_invalid,
 			"spaces don't match", goto error);
 	n_out = isl_multi_aff_dim(ma, isl_dim_out);
-	if (isl_multi_aff_dim(ma, isl_dim_in) == 0 && n_out != 0)
-		isl_die(isl_multi_aff_get_ctx(ma), isl_error_invalid,
-			"cannot determine domains", goto error);
+	if (isl_multi_aff_dim(ma, isl_dim_in) == 0)
+		return mupa_apply_multi_aff_0D(mupa, ma);
 
 	space1 = isl_space_range(isl_multi_aff_get_space(ma));
 	res = isl_multi_union_pw_aff_alloc(space1);
@@ -8843,6 +9156,23 @@ error:
 	return NULL;
 }
 
+/* Apply "pa" to "mupa", in the special case where "mupa" is 0D.
+ * The space of "mupa" is known to be compatible with the domain of "pa".
+ *
+ * Construct an isl_multi_union_pw_aff that is equal to "pa"
+ * on the domain of "mupa".
+ */
+static __isl_give isl_union_pw_aff *isl_multi_union_pw_aff_apply_pw_aff_0D(
+	__isl_take isl_multi_union_pw_aff *mupa, __isl_take isl_pw_aff *pa)
+{
+	isl_union_set *dom;
+
+	dom = isl_multi_union_pw_aff_domain(mupa);
+	pa = isl_pw_aff_project_domain_on_params(pa);
+
+	return isl_union_pw_aff_pw_aff_on_domain(dom, pa);
+}
+
 /* Apply "pa" to "mupa".  The space of "mupa" needs to be compatible
  * with the domain of "pa".
  * Furthermore, the dimension of this space needs to be greater than zero.
@@ -8874,8 +9204,7 @@ __isl_give isl_union_pw_aff *isl_multi_u
 		isl_die(isl_pw_aff_get_ctx(pa), isl_error_invalid,
 			"spaces don't match", goto error);
 	if (isl_pw_aff_dim(pa, isl_dim_in) == 0)
-		isl_die(isl_pw_aff_get_ctx(pa), isl_error_invalid,
-			"cannot determine domains", goto error);
+		return isl_multi_union_pw_aff_apply_pw_aff_0D(mupa, pa);
 
 	space = isl_space_params(isl_multi_union_pw_aff_get_space(mupa));
 	upa = isl_union_pw_aff_empty(space);
@@ -8903,10 +9232,26 @@ error:
 	return NULL;
 }
 
+/* Apply "pma" to "mupa", in the special case where "mupa" is 0D.
+ * The space of "mupa" is known to be compatible with the domain of "pma".
+ *
+ * Construct an isl_multi_union_pw_aff that is equal to "pma"
+ * on the domain of "mupa".
+ */
+static __isl_give isl_multi_union_pw_aff *mupa_apply_pw_multi_aff_0D(
+	__isl_take isl_multi_union_pw_aff *mupa,
+	__isl_take isl_pw_multi_aff *pma)
+{
+	isl_union_set *dom;
+
+	dom = isl_multi_union_pw_aff_domain(mupa);
+	pma = isl_pw_multi_aff_project_domain_on_params(pma);
+
+	return isl_multi_union_pw_aff_pw_multi_aff_on_domain(dom, pma);
+}
+
 /* Apply "pma" to "mupa".  The space of "mupa" needs to be compatible
  * with the domain of "pma".
- * Furthermore, the dimension of this space needs to be greater than zero,
- * unless the dimension of the target space of "pma" is also zero.
  * The result is defined over the shared domain of the elements of "mupa"
  */
 __isl_give isl_multi_union_pw_aff *isl_multi_union_pw_aff_apply_pw_multi_aff(
@@ -8936,9 +9281,8 @@ __isl_give isl_multi_union_pw_aff *isl_m
 		isl_die(isl_pw_multi_aff_get_ctx(pma), isl_error_invalid,
 			"spaces don't match", goto error);
 	n_out = isl_pw_multi_aff_dim(pma, isl_dim_out);
-	if (isl_pw_multi_aff_dim(pma, isl_dim_in) == 0 && n_out != 0)
-		isl_die(isl_pw_multi_aff_get_ctx(pma), isl_error_invalid,
-			"cannot determine domains", goto error);
+	if (isl_pw_multi_aff_dim(pma, isl_dim_in) == 0)
+		return mupa_apply_pw_multi_aff_0D(mupa, pma);
 
 	space1 = isl_space_range(isl_pw_multi_aff_get_space(pma));
 	res = isl_multi_union_pw_aff_alloc(space1);
@@ -8962,11 +9306,47 @@ error:
 	return NULL;
 }
 
+/* Replace the explicit domain of "mupa" by its preimage under "upma".
+ * If the explicit domain only keeps track of constraints on the parameters,
+ * then only update those constraints.
+ */
+static __isl_give isl_multi_union_pw_aff *preimage_explicit_domain(
+	__isl_take isl_multi_union_pw_aff *mupa,
+	__isl_keep isl_union_pw_multi_aff *upma)
+{
+	isl_bool is_params;
+
+	if (isl_multi_union_pw_aff_check_has_explicit_domain(mupa) < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+
+	mupa = isl_multi_union_pw_aff_cow(mupa);
+	if (!mupa)
+		return NULL;
+
+	is_params = isl_union_set_is_params(mupa->u.dom);
+	if (is_params < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+
+	upma = isl_union_pw_multi_aff_copy(upma);
+	if (is_params)
+		mupa->u.dom = isl_union_set_intersect_params(mupa->u.dom,
+		    isl_union_set_params(isl_union_pw_multi_aff_domain(upma)));
+	else
+		mupa->u.dom = isl_union_set_preimage_union_pw_multi_aff(
+							    mupa->u.dom, upma);
+	if (!mupa->u.dom)
+		return isl_multi_union_pw_aff_free(mupa);
+	return mupa;
+}
+
 /* Compute the pullback of "mupa" by the function represented by "upma".
  * In other words, plug in "upma" in "mupa".  The result contains
  * expressions defined over the domain space of "upma".
  *
  * Run over all elements of "mupa" and plug in "upma" in each of them.
+ *
+ * If "mupa" has an explicit domain, then it is this domain
+ * that needs to undergo a pullback instead, i.e., a preimage.
  */
 __isl_give isl_multi_union_pw_aff *
 isl_multi_union_pw_aff_pullback_union_pw_multi_aff(
@@ -8979,6 +9359,7 @@ isl_multi_union_pw_aff_pullback_union_pw
 				    isl_union_pw_multi_aff_get_space(upma));
 	upma = isl_union_pw_multi_aff_align_params(upma,
 				    isl_multi_union_pw_aff_get_space(mupa));
+	mupa = isl_multi_union_pw_aff_cow(mupa);
 	if (!mupa || !upma)
 		goto error;
 
@@ -8992,6 +9373,9 @@ isl_multi_union_pw_aff_pullback_union_pw
 		mupa = isl_multi_union_pw_aff_set_union_pw_aff(mupa, i, upa);
 	}
 
+	if (isl_multi_union_pw_aff_has_explicit_domain(mupa))
+		mupa = preimage_explicit_domain(mupa, upma);
+
 	isl_union_pw_multi_aff_free(upma);
 	return mupa;
 error:
@@ -9010,25 +9394,14 @@ __isl_give isl_multi_pw_aff *isl_multi_u
 	__isl_keep isl_multi_union_pw_aff *mupa, __isl_take isl_space *space)
 {
 	int i, n;
-	isl_bool equal_params;
-	isl_space *space_mpa = NULL;
+	isl_space *space_mpa;
 	isl_multi_pw_aff *mpa;
 
 	if (!mupa || !space)
 		goto error;
 
 	space_mpa = isl_multi_union_pw_aff_get_space(mupa);
-	equal_params = isl_space_has_equal_params(space_mpa, space);
-	if (equal_params < 0)
-		goto error;
-	if (!equal_params) {
-		space = isl_space_drop_dims(space, isl_dim_param,
-					0, isl_space_dim(space, isl_dim_param));
-		space = isl_space_align_params(space,
-					isl_space_copy(space_mpa));
-		if (!space)
-			goto error;
-	}
+	space = isl_space_replace_params(space, space_mpa);
 	space_mpa = isl_space_map_from_domain_and_range(isl_space_copy(space),
 							space_mpa);
 	mpa = isl_multi_pw_aff_alloc(space_mpa);
@@ -9050,7 +9423,94 @@ __isl_give isl_multi_pw_aff *isl_multi_u
 	isl_space_free(space);
 	return mpa;
 error:
-	isl_space_free(space_mpa);
 	isl_space_free(space);
 	return NULL;
 }
+
+/* Evaluate the affine function "aff" in the void point "pnt".
+ * In particular, return the value NaN.
+ */
+static __isl_give isl_val *eval_void(__isl_take isl_aff *aff,
+	__isl_take isl_point *pnt)
+{
+	isl_ctx *ctx;
+
+	ctx = isl_point_get_ctx(pnt);
+	isl_aff_free(aff);
+	isl_point_free(pnt);
+	return isl_val_nan(ctx);
+}
+
+/* Evaluate the affine expression "aff"
+ * in the coordinates (with denominator) "pnt".
+ */
+static __isl_give isl_val *eval(__isl_keep isl_vec *aff,
+	__isl_keep isl_vec *pnt)
+{
+	isl_int n, d;
+	isl_ctx *ctx;
+	isl_val *v;
+
+	if (!aff || !pnt)
+		return NULL;
+
+	ctx = isl_vec_get_ctx(aff);
+	isl_int_init(n);
+	isl_int_init(d);
+	isl_seq_inner_product(aff->el + 1, pnt->el, pnt->size, &n);
+	isl_int_mul(d, aff->el[0], pnt->el[0]);
+	v = isl_val_rat_from_isl_int(ctx, n, d);
+	v = isl_val_normalize(v);
+	isl_int_clear(n);
+	isl_int_clear(d);
+
+	return v;
+}
+
+/* Check that the domain space of "aff" is equal to "space".
+ */
+static isl_stat isl_aff_check_has_domain_space(__isl_keep isl_aff *aff,
+	__isl_keep isl_space *space)
+{
+	isl_bool ok;
+
+	ok = isl_space_is_equal(isl_aff_peek_domain_space(aff), space);
+	if (ok < 0)
+		return isl_stat_error;
+	if (!ok)
+		isl_die(isl_aff_get_ctx(aff), isl_error_invalid,
+			"incompatible spaces", return isl_stat_error);
+	return isl_stat_ok;
+}
+
+/* Evaluate the affine function "aff" in "pnt".
+ */
+__isl_give isl_val *isl_aff_eval(__isl_take isl_aff *aff,
+	__isl_take isl_point *pnt)
+{
+	isl_bool is_void;
+	isl_val *v;
+	isl_local_space *ls;
+
+	if (isl_aff_check_has_domain_space(aff, isl_point_peek_space(pnt)) < 0)
+		goto error;
+	is_void = isl_point_is_void(pnt);
+	if (is_void < 0)
+		goto error;
+	if (is_void)
+		return eval_void(aff, pnt);
+
+	ls = isl_aff_get_domain_local_space(aff);
+	pnt = isl_local_space_lift_point(ls, pnt);
+
+	v = eval(aff->v, isl_point_peek_vec(pnt));
+
+	isl_aff_free(aff);
+	isl_point_free(pnt);
+
+	return v;
+error:
+	isl_aff_free(aff);
+	isl_point_free(pnt);
+	return NULL;
+}

Modified: polly/trunk/lib/External/isl/isl_aff_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_aff_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_aff_private.h (original)
+++ polly/trunk/lib/External/isl/isl_aff_private.h Sat Apr 21 01:34:22 2018
@@ -41,6 +41,11 @@ struct isl_pw_aff {
 	struct isl_pw_aff_piece p[1];
 };
 
+#undef PW
+#define PW isl_pw_aff
+
+#include <isl_pw_templ.h>
+
 #undef EL
 #define EL isl_pw_aff
 
@@ -62,6 +67,11 @@ struct isl_pw_multi_aff {
 	struct isl_pw_multi_aff_piece p[1];
 };
 
+#undef PW
+#define PW isl_pw_multi_aff
+
+#include <isl_pw_templ.h>
+
 __isl_give isl_aff *isl_aff_alloc_vec(__isl_take isl_local_space *ls,
 	__isl_take isl_vec *v);
 __isl_give isl_aff *isl_aff_alloc(__isl_take isl_local_space *ls);
@@ -78,6 +88,8 @@ __isl_give isl_aff *isl_aff_set_coeffici
 	enum isl_dim_type type, int pos, isl_int v);
 __isl_give isl_aff *isl_aff_add_constant(__isl_take isl_aff *aff, isl_int v);
 
+__isl_give isl_aff *isl_aff_domain_factor_domain(__isl_take isl_aff *aff);
+
 int isl_aff_plain_cmp(__isl_keep isl_aff *aff1, __isl_keep isl_aff *aff2);
 
 __isl_give isl_aff *isl_aff_normalize(__isl_take isl_aff *aff);
@@ -159,9 +171,14 @@ __isl_give isl_basic_set *isl_aff_pos_ba
 
 #undef BASE
 #define BASE pw_aff
+#undef DOMBASE
+#define DOMBASE set
+#define EXPLICIT_DOMAIN
 
 #include <isl_multi_templ.h>
 
+#undef EXPLICIT_DOMAIN
+
 #undef EL
 #define EL isl_union_pw_aff
 
@@ -169,9 +186,14 @@ __isl_give isl_basic_set *isl_aff_pos_ba
 
 #undef BASE
 #define BASE union_pw_aff
+#undef DOMBASE
+#define DOMBASE union_set
+#define EXPLICIT_DOMAIN
 
 #include <isl_multi_templ.h>
 
+#undef EXPLICIT_DOMAIN
+
 #undef EL
 #define EL isl_union_pw_multi_aff
 

Modified: polly/trunk/lib/External/isl/isl_ast.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast.c (original)
+++ polly/trunk/lib/External/isl/isl_ast.c Sat Apr 21 01:34:22 2018
@@ -9,6 +9,7 @@
 
 #include <string.h>
 
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl_ast_private.h>
 

Modified: polly/trunk/lib/External/isl/isl_ast_build.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast_build.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast_build.c (original)
+++ polly/trunk/lib/External/isl/isl_ast_build.c Sat Apr 21 01:34:22 2018
@@ -10,6 +10,7 @@
  * B.P. 105 - 78153 Le Chesnay, France
  */
 
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl/space.h>
 #include <isl/map.h>

Modified: polly/trunk/lib/External/isl/isl_ast_build_expr.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast_build_expr.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast_build_expr.c (original)
+++ polly/trunk/lib/External/isl/isl_ast_build_expr.c Sat Apr 21 01:34:22 2018
@@ -10,6 +10,7 @@
  * B.P. 105 - 78153 Le Chesnay, France
  */
 
+#include <isl/id.h>
 #include <isl/space.h>
 #include <isl/constraint.h>
 #include <isl/ilp.h>
@@ -1423,7 +1424,7 @@ static int cmp_constraint(__isl_keep isl
 /* Construct an isl_ast_expr that evaluates the conditions defining "bset".
  * The result is simplified in terms of build->domain.
  *
- * If "bset" is not bounded by any constraint, then we contruct
+ * If "bset" is not bounded by any constraint, then we construct
  * the expression "1", i.e., "true".
  *
  * Otherwise, we sort the constraints, putting constraints that involve

Modified: polly/trunk/lib/External/isl/isl_ast_build_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast_build_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast_build_private.h (original)
+++ polly/trunk/lib/External/isl/isl_ast_build_private.h Sat Apr 21 01:34:22 2018
@@ -50,7 +50,7 @@
  *
  * "strides" contains the stride of each loop.  The number of elements
  * is equal to the number of dimensions in "domain".
- * "offsets" constains the offsets of strided loops.  If s is the stride
+ * "offsets" contains the offsets of strided loops.  If s is the stride
  * for a given dimension and f is the corresponding offset, then the
  * dimension takes on values
  *
@@ -133,7 +133,7 @@
  * an AST from a schedule tree.  It may be NULL if we are not generating
  * an AST from a schedule tree or if we are not inside a band node.
  *
- * "loop_type" originally constains loop AST generation types for
+ * "loop_type" originally contains loop AST generation types for
  * the "n" members of "node" and it is updated (along with "n") when
  * a schedule dimension is inserted.
  * It is NULL if "node" is NULL.

Modified: polly/trunk/lib/External/isl/isl_ast_codegen.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast_codegen.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast_codegen.c (original)
+++ polly/trunk/lib/External/isl/isl_ast_codegen.c Sat Apr 21 01:34:22 2018
@@ -11,6 +11,7 @@
  */
 
 #include <limits.h>
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl/space.h>
 #include <isl/aff.h>
@@ -2651,7 +2652,7 @@ static int foreach_iteration(__isl_take
  * "executed" and "build" are inputs to compute_domains.
  * "schedule_domain" is the domain of "executed".
  *
- * "option" constains the domains at the current depth that should by
+ * "option" contains the domains at the current depth that should by
  * atomic, separated or unrolled.  These domains are as specified by
  * the user, except that inner dimensions have been eliminated and
  * that they have been made pair-wise disjoint.
@@ -3880,7 +3881,7 @@ static int first_offset(struct isl_set_m
  * with "<<" the lexicographic order, proving that the order is preserved
  * in all cases.
  */
-static __isl_give isl_union_map *contruct_shifted_executed(
+static __isl_give isl_union_map *construct_shifted_executed(
 	struct isl_set_map_pair *domain, int *order, int n,
 	__isl_keep isl_val *stride, __isl_keep isl_multi_val *offset,
 	__isl_take isl_ast_build *build)
@@ -3951,9 +3952,9 @@ static __isl_give isl_union_map *contruc
  * domain is equal to zero.  The other offsets are reduced modulo stride.
  *
  * Based on this information, we construct a new inverse schedule in
- * contruct_shifted_executed that exposes the stride.
+ * construct_shifted_executed that exposes the stride.
  * Since this involves the introduction of a new schedule dimension,
- * the build needs to be changed accodingly.
+ * the build needs to be changed accordingly.
  * After computing the AST, the newly introduced dimension needs
  * to be removed again from the list of grafts.  We do this by plugging
  * in a mapping that represents the new schedule domain in terms of the
@@ -3985,7 +3986,7 @@ static __isl_give isl_ast_graft_list *ge
 	mv = isl_multi_val_add_val(mv, val);
 	mv = isl_multi_val_mod_val(mv, isl_val_copy(stride));
 
-	executed = contruct_shifted_executed(domain, order, n, stride, mv,
+	executed = construct_shifted_executed(domain, order, n, stride, mv,
 						build);
 	space = isl_ast_build_get_space(build, 1);
 	space = isl_space_map_from_set(space);

Modified: polly/trunk/lib/External/isl/isl_ast_graft.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_ast_graft.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_ast_graft.c (original)
+++ polly/trunk/lib/External/isl/isl_ast_graft.c Sat Apr 21 01:34:22 2018
@@ -10,6 +10,7 @@
  * B.P. 105 - 78153 Le Chesnay, France
  */
 
+#include <isl/id.h>
 #include <isl/space.h>
 #include <isl_ast_private.h>
 #include <isl_ast_build_expr.h>

Modified: polly/trunk/lib/External/isl/isl_convex_hull.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_convex_hull.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_convex_hull.c (original)
+++ polly/trunk/lib/External/isl/isl_convex_hull.c Sat Apr 21 01:34:22 2018
@@ -1557,7 +1557,7 @@ static void update_constraint(struct isl
 	c->ineq = ineq;
 }
 
-/* Check whether the constraint hash table "table" constains the constraint
+/* Check whether the constraint hash table "table" contains the constraint
  * "con".
  */
 static int has_constraint(struct isl_ctx *ctx, struct isl_hash_table *table,

Modified: polly/trunk/lib/External/isl/isl_fold.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_fold.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_fold.c (original)
+++ polly/trunk/lib/External/isl/isl_fold.c Sat Apr 21 01:34:22 2018
@@ -8,7 +8,6 @@
  * 91893 Orsay, France 
  */
 
-#define ISL_DIM_H
 #include <isl_map_private.h>
 #include <isl_union_map_private.h>
 #include <isl_polynomial_private.h>
@@ -685,6 +684,7 @@ __isl_give isl_qpolynomial_fold *isl_qpo
 #define NO_PULLBACK
 
 #include <isl_pw_templ.c>
+#include <isl_pw_eval.c>
 
 #undef UNION
 #define UNION isl_union_pw_qpolynomial_fold

Modified: polly/trunk/lib/External/isl/isl_id_to_ast_expr.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_id_to_ast_expr.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_id_to_ast_expr.c (original)
+++ polly/trunk/lib/External/isl/isl_id_to_ast_expr.c Sat Apr 21 01:34:22 2018
@@ -1,4 +1,5 @@
 #include <isl/id_to_ast_expr.h>
+#include <isl/id.h>
 #include <isl/ast.h>
 
 #define isl_id_is_equal(id1,id2)	id1 == id2

Modified: polly/trunk/lib/External/isl/isl_id_to_id.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_id_to_id.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_id_to_id.c (original)
+++ polly/trunk/lib/External/isl/isl_id_to_id.c Sat Apr 21 01:34:22 2018
@@ -1,4 +1,5 @@
 #include <isl/id_to_id.h>
+#include <isl/id.h>
 
 #define isl_id_is_equal(id1,id2)	id1 == id2
 

Modified: polly/trunk/lib/External/isl/isl_id_to_pw_aff.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_id_to_pw_aff.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_id_to_pw_aff.c (original)
+++ polly/trunk/lib/External/isl/isl_id_to_pw_aff.c Sat Apr 21 01:34:22 2018
@@ -1,4 +1,5 @@
 #include <isl/id_to_pw_aff.h>
+#include <isl/id.h>
 #include <isl/aff.h>
 
 #define isl_id_is_equal(id1,id2)	id1 == id2

Modified: polly/trunk/lib/External/isl/isl_input.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_input.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_input.c (original)
+++ polly/trunk/lib/External/isl/isl_input.c Sat Apr 21 01:34:22 2018
@@ -2581,6 +2581,43 @@ static struct isl_obj schedule_read(__is
 	return obj;
 }
 
+/* Read a disjunction of object bodies from "s".
+ * That is, read the inside of the braces, but not the braces themselves.
+ * "v" contains a description of the identifiers parsed so far.
+ * "map" contains information about the parameters.
+ */
+static struct isl_obj obj_read_disjuncts(__isl_keep isl_stream *s,
+	struct vars *v, __isl_keep isl_map *map)
+{
+	struct isl_obj obj = { isl_obj_set, NULL };
+
+	if (isl_stream_next_token_is(s, '}')) {
+		obj.type = isl_obj_union_set;
+		obj.v = isl_union_set_empty(isl_map_get_space(map));
+		return obj;
+	}
+
+	for (;;) {
+		struct isl_obj o;
+		o = obj_read_body(s, isl_map_copy(map), v);
+		if (o.type == isl_obj_none || !o.v)
+			return o;
+		if (!obj.v)
+			obj = o;
+		else {
+			obj = obj_add(s, obj, o);
+			if (obj.type == isl_obj_none || !obj.v)
+				return obj;
+		}
+		if (!isl_stream_eat_if_available(s, ';'))
+			break;
+		if (isl_stream_next_token_is(s, '}'))
+			break;
+	}
+
+	return obj;
+}
+
 static struct isl_obj obj_read(__isl_keep isl_stream *s)
 {
 	isl_map *map = NULL;
@@ -2662,37 +2699,14 @@ static struct isl_obj obj_read(__isl_kee
 		map = read_map_tuple(s, map, isl_dim_param, v, 0, 1);
 		if (!map)
 			goto error;
-	} else if (tok->type == '}') {
-		obj.type = isl_obj_union_set;
-		obj.v = isl_union_set_empty(isl_map_get_space(map));
-		isl_token_free(tok);
-		goto done;
 	} else
 		isl_stream_push_token(s, tok);
 
-	for (;;) {
-		struct isl_obj o;
-		tok = NULL;
-		o = obj_read_body(s, isl_map_copy(map), v);
-		if (o.type == isl_obj_none || !o.v)
-			goto error;
-		if (!obj.v)
-			obj = o;
-		else {
-			obj = obj_add(s, obj, o);
-			if (obj.type == isl_obj_none || !obj.v)
-				goto error;
-		}
-		tok = isl_stream_next_token(s);
-		if (!tok || tok->type != ';')
-			break;
-		isl_token_free(tok);
-		if (isl_stream_next_token_is(s, '}')) {
-			tok = isl_stream_next_token(s);
-			break;
-		}
-	}
+	obj = obj_read_disjuncts(s, v, map);
+	if (obj.type == isl_obj_none || !obj.v)
+		goto error;
 
+	tok = isl_stream_next_token(s);
 	if (tok && tok->type == '}') {
 		isl_token_free(tok);
 	} else {
@@ -2701,7 +2715,7 @@ static struct isl_obj obj_read(__isl_kee
 			isl_token_free(tok);
 		goto error;
 	}
-done:
+
 	vars_free(v);
 	isl_map_free(map);
 
@@ -2782,17 +2796,19 @@ error:
 	return NULL;
 }
 
-__isl_give isl_union_set *isl_stream_read_union_set(__isl_keep isl_stream *s)
+/* Extract an isl_union_set from "obj".
+ * This only works if the object was detected as either a set
+ * (in which case it is converted to a union set) or a union set.
+ */
+static __isl_give isl_union_set *extract_union_set(isl_ctx *ctx,
+	struct isl_obj obj)
 {
-	struct isl_obj obj;
-
-	obj = obj_read(s);
 	if (obj.type == isl_obj_set) {
 		obj.type = isl_obj_union_set;
 		obj.v = isl_union_set_from_set(obj.v);
 	}
 	if (obj.v)
-		isl_assert(s->ctx, obj.type == isl_obj_union_set, goto error);
+		isl_assert(ctx, obj.type == isl_obj_union_set, goto error);
 
 	return obj.v;
 error:
@@ -2800,6 +2816,18 @@ error:
 	return NULL;
 }
 
+/* Read an isl_union_set from "s".
+ * First read a generic object and then try and extract
+ * an isl_union_set from that.
+ */
+__isl_give isl_union_set *isl_stream_read_union_set(__isl_keep isl_stream *s)
+{
+	struct isl_obj obj;
+
+	obj = obj_read(s);
+	return extract_union_set(s->ctx, obj);
+}
+
 static __isl_give isl_basic_map *basic_map_read(__isl_keep isl_stream *s)
 {
 	struct isl_obj obj;
@@ -3695,6 +3723,9 @@ __isl_give isl_multi_aff *isl_multi_aff_
  * The input format is similar to that of map, except that any conditions
  * on the domains should be specified inside the tuple since each
  * piecewise affine expression may have a different domain.
+ * However, additional, shared conditions can also be specified.
+ * This is especially useful for setting the explicit domain
+ * of a zero-dimensional isl_multi_pw_aff.
  *
  * Since we do not know in advance if the isl_multi_pw_aff lives
  * in a set or a map space, we first read the first tuple and check
@@ -3737,6 +3768,9 @@ __isl_give isl_multi_pw_aff *isl_stream_
 			goto error;
 	}
 
+	if (isl_stream_eat_if_available(s, ':'))
+		dom = read_formula(s, v, dom, 0);
+
 	if (isl_stream_eat(s, '}'))
 		goto error;
 
@@ -3942,6 +3976,106 @@ static int next_is_param_tuple(__isl_kee
 	return is_tuple;
 }
 
+/* Read the core of a body of an isl_multi_union_pw_aff from "s",
+ * i.e., everything except the parameter specification and
+ * without shared domain constraints.
+ * "v" contains a description of the identifiers parsed so far.
+ * The parameters, if any, are specified by "space".
+ *
+ * The body is of the form
+ *
+ *	[{ [..] : ... ; [..] : ... }, { [..] : ... ; [..] : ... }]
+ *
+ * Read the tuple, collecting the individual isl_union_pw_aff
+ * elements in a list and construct the result from the tuple space and
+ * the list.
+ */
+static __isl_give isl_multi_union_pw_aff *read_multi_union_pw_aff_body_core(
+	__isl_keep isl_stream *s, struct vars *v, __isl_take isl_space *space)
+{
+	isl_union_pw_aff_list *list;
+	isl_multi_union_pw_aff *mupa;
+
+	list = isl_union_pw_aff_list_alloc(s->ctx, 0);
+	space = read_tuple_space(s, v, space, 1, 0,
+				&read_union_pw_aff_el, &list);
+	mupa = isl_multi_union_pw_aff_from_union_pw_aff_list(space, list);
+
+	return mupa;
+}
+
+/* Read the body of an isl_union_set from "s",
+ * i.e., everything except the parameter specification.
+ * "v" contains a description of the identifiers parsed so far.
+ * The parameters, if any, are specified by "space".
+ *
+ * First read a generic disjunction of object bodies and then try and extract
+ * an isl_union_set from that.
+ */
+static __isl_give isl_union_set *read_union_set_body(__isl_keep isl_stream *s,
+	struct vars *v, __isl_take isl_space *space)
+{
+	struct isl_obj obj = { isl_obj_set, NULL };
+	isl_map *map;
+
+	map = isl_set_universe(space);
+	if (isl_stream_eat(s, '{') < 0)
+		goto error;
+	obj = obj_read_disjuncts(s, v, map);
+	if (isl_stream_eat(s, '}') < 0)
+		goto error;
+	isl_map_free(map);
+
+	return extract_union_set(s->ctx, obj);
+error:
+	obj.type->free(obj.v);
+	isl_map_free(map);
+	return NULL;
+}
+
+/* Read the body of an isl_multi_union_pw_aff from "s",
+ * i.e., everything except the parameter specification.
+ * "v" contains a description of the identifiers parsed so far.
+ * The parameters, if any, are specified by "space".
+ *
+ * In particular, handle the special case with shared domain constraints.
+ * These are specified as
+ *
+ *	([...] : ...)
+ *
+ * and are especially useful for setting the explicit domain
+ * of a zero-dimensional isl_multi_union_pw_aff.
+ * The core isl_multi_union_pw_aff body ([...]) is read by
+ * read_multi_union_pw_aff_body_core.
+ */
+static __isl_give isl_multi_union_pw_aff *read_multi_union_pw_aff_body(
+	__isl_keep isl_stream *s, struct vars *v, __isl_take isl_space *space)
+{
+	isl_multi_union_pw_aff *mupa;
+
+	if (!isl_stream_next_token_is(s, '('))
+		return read_multi_union_pw_aff_body_core(s, v, space);
+
+	if (isl_stream_eat(s, '(') < 0)
+		goto error;
+	mupa = read_multi_union_pw_aff_body_core(s, v, isl_space_copy(space));
+	if (isl_stream_eat_if_available(s, ':')) {
+		isl_union_set *dom;
+
+		dom = read_union_set_body(s, v, space);
+		mupa = isl_multi_union_pw_aff_intersect_domain(mupa, dom);
+	} else {
+		isl_space_free(space);
+	}
+	if (isl_stream_eat(s, ')') < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+
+	return mupa;
+error:
+	isl_space_free(space);
+	return NULL;
+}
+
 /* Read an isl_multi_union_pw_aff from "s".
  *
  * The input has the form
@@ -3952,20 +4086,28 @@ static int next_is_param_tuple(__isl_kee
  *
  *	[..] -> [{ [..] : ... ; [..] : ... }, { [..] : ... ; [..] : ... }]
  *
+ * Additionally, a shared domain may be specified as
+ *
+ *	([..] : ...)
+ *
+ * or
+ *
+ *	[..] -> ([..] : ...)
+ *
+ * The first case is handled by the caller, the second case
+ * is handled by read_multi_union_pw_aff_body.
+ *
  * We first check for the special case of an empty tuple "[]".
  * Then we check if there are any parameters.
- * Finally, we read the tuple, collecting the individual isl_union_pw_aff
- * elements in a list and construct the result from the tuple space and
- * the list.
+ * Finally, read the tuple and construct the result.
  */
-__isl_give isl_multi_union_pw_aff *isl_stream_read_multi_union_pw_aff(
+static __isl_give isl_multi_union_pw_aff *read_multi_union_pw_aff_core(
 	__isl_keep isl_stream *s)
 {
 	struct vars *v;
 	isl_set *dom = NULL;
 	isl_space *space;
 	isl_multi_union_pw_aff *mupa = NULL;
-	isl_union_pw_aff_list *list;
 
 	if (next_is_empty_tuple(s)) {
 		if (isl_stream_eat(s, '['))
@@ -3988,10 +4130,7 @@ __isl_give isl_multi_union_pw_aff *isl_s
 	}
 	space = isl_set_get_space(dom);
 	isl_set_free(dom);
-	list = isl_union_pw_aff_list_alloc(s->ctx, 0);
-	space = read_tuple_space(s, v, space, 1, 0,
-				&read_union_pw_aff_el, &list);
-	mupa = isl_multi_union_pw_aff_from_union_pw_aff_list(space, list);
+	mupa = read_multi_union_pw_aff_body(s, v, space);
 
 	vars_free(v);
 
@@ -4003,6 +4142,40 @@ error:
 	return NULL;
 }
 
+/* Read an isl_multi_union_pw_aff from "s".
+ *
+ * In particular, handle the special case with shared domain constraints.
+ * These are specified as
+ *
+ *	([...] : ...)
+ *
+ * and are especially useful for setting the explicit domain
+ * of a zero-dimensional isl_multi_union_pw_aff.
+ * The core isl_multi_union_pw_aff ([...]) is read by
+ * read_multi_union_pw_aff_core.
+ */
+__isl_give isl_multi_union_pw_aff *isl_stream_read_multi_union_pw_aff(
+	__isl_keep isl_stream *s)
+{
+	isl_multi_union_pw_aff *mupa;
+
+	if (!isl_stream_next_token_is(s, '('))
+		return read_multi_union_pw_aff_core(s);
+
+	if (isl_stream_eat(s, '(') < 0)
+		return NULL;
+	mupa = read_multi_union_pw_aff_core(s);
+	if (isl_stream_eat_if_available(s, ':')) {
+		isl_union_set *dom;
+
+		dom = isl_stream_read_union_set(s);
+		mupa = isl_multi_union_pw_aff_intersect_domain(mupa, dom);
+	}
+	if (isl_stream_eat(s, ')') < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+	return mupa;
+}
+
 /* Read an isl_multi_union_pw_aff from "str".
  */
 __isl_give isl_multi_union_pw_aff *isl_multi_union_pw_aff_read_from_str(

Modified: polly/trunk/lib/External/isl/isl_local.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_local.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_local.c (original)
+++ polly/trunk/lib/External/isl/isl_local.c Sat Apr 21 01:34:22 2018
@@ -1,16 +1,67 @@
 /*
+ * Copyright 2011      INRIA Saclay
  * Copyright 2014      Ecole Normale Superieure
  *
  * Use of this software is governed by the MIT license
  *
- * Written by Sven Verdoolaege,
- * Ecole Normale Superieure, 45 rue d'Ulm, 75230 Paris, France
+ * Written by Sven Verdoolaege, INRIA Saclay - Ile-de-France,
+ * Parc Club Orsay Universite, ZAC des vignes, 4 rue Jacques Monod,
+ * 91893 Orsay, France
+ * and Ecole Normale Superieure, 45 rue d'Ulm, 75230 Paris, France
  */
 
+#include <isl/space.h>
+#include <isl_vec_private.h>
 #include <isl_mat_private.h>
 #include <isl_seq.h>
+#include <isl_local.h>
 
-/* Given a matrix "div" representing local variables,
+/* Return the isl_ctx to which "local" belongs.
+ */
+isl_ctx *isl_local_get_ctx(__isl_keep isl_local *local)
+{
+	if (!local)
+		return NULL;
+
+	return isl_mat_get_ctx(local);
+}
+
+/* Return the number of local variables (isl_dim_div),
+ * the number of other variables (isl_dim_set) or
+ * the total number of variables (isl_dim_all) in "local".
+ *
+ * Other types do not have any meaning for an isl_local object.
+ */
+int isl_local_dim(__isl_keep isl_local *local, enum isl_dim_type type)
+{
+	isl_mat *mat = local;
+
+	if (!local)
+		return 0;
+	if (type == isl_dim_div)
+		return isl_mat_rows(mat);
+	if (type == isl_dim_all)
+		return isl_mat_cols(mat) - 2;
+	if (type == isl_dim_set)
+		return isl_local_dim(local, isl_dim_all) -
+			isl_local_dim(local, isl_dim_div);
+	isl_die(isl_local_get_ctx(local), isl_error_unsupported,
+		"unsupported dimension type", return 0);
+}
+
+/* Check that "pos" is a valid position for a variable in "local".
+ */
+static isl_stat isl_local_check_pos(__isl_keep isl_local *local, int pos)
+{
+	if (!local)
+		return isl_stat_error;
+	if (pos < 0 || pos >= isl_local_dim(local, isl_dim_div))
+		isl_die(isl_local_get_ctx(local), isl_error_invalid,
+			"position out of bounds", return isl_stat_error);
+	return isl_stat_ok;
+}
+
+/* Given local variables "local",
  * is the variable at position "pos" marked as not having
  * an explicit representation?
  * Note that even if this variable is not marked in this way and therefore
@@ -18,47 +69,44 @@
  * depend (indirectly) on other local variables that do not
  * have an explicit representation.
  */
-isl_bool isl_local_div_is_marked_unknown(__isl_keep isl_mat *div, int pos)
+isl_bool isl_local_div_is_marked_unknown(__isl_keep isl_local *local, int pos)
 {
-	if (!div)
+	isl_mat *mat = local;
+
+	if (isl_local_check_pos(local, pos) < 0)
 		return isl_bool_error;
-	if (pos < 0 || pos >= div->n_row)
-		isl_die(isl_mat_get_ctx(div), isl_error_invalid,
-			"position out of bounds", return isl_bool_error);
-	return isl_int_is_zero(div->row[pos][0]);
+	return isl_int_is_zero(mat->row[pos][0]);
 }
 
-/* Given a matrix "div" representing local variables,
+/* Given local variables "local",
  * does the variable at position "pos" have a complete explicit representation?
  * Having a complete explicit representation requires not only
  * an explicit representation, but also that all local variables
  * that appear in this explicit representation in turn have
  * a complete explicit representation.
  */
-isl_bool isl_local_div_is_known(__isl_keep isl_mat *div, int pos)
+isl_bool isl_local_div_is_known(__isl_keep isl_local *local, int pos)
 {
 	isl_bool marked;
 	int i, n, off;
+	isl_mat *mat = local;
 
-	if (!div)
+	if (isl_local_check_pos(local, pos) < 0)
 		return isl_bool_error;
-	if (pos < 0 || pos >= div->n_row)
-		isl_die(isl_mat_get_ctx(div), isl_error_invalid,
-			"position out of bounds", return isl_bool_error);
 
-	marked = isl_local_div_is_marked_unknown(div, pos);
+	marked = isl_local_div_is_marked_unknown(local, pos);
 	if (marked < 0 || marked)
 		return isl_bool_not(marked);
 
-	n = isl_mat_rows(div);
-	off = isl_mat_cols(div) - n;
+	n = isl_local_dim(local, isl_dim_div);
+	off = isl_mat_cols(mat) - n;
 
 	for (i = n - 1; i >= 0; --i) {
 		isl_bool known;
 
-		if (isl_int_is_zero(div->row[pos][off + i]))
+		if (isl_int_is_zero(mat->row[pos][off + i]))
 			continue;
-		known = isl_local_div_is_known(div, i);
+		known = isl_local_div_is_known(local, i);
 		if (known < 0 || !known)
 			return known;
 	}
@@ -66,52 +114,118 @@ isl_bool isl_local_div_is_known(__isl_ke
 	return isl_bool_true;
 }
 
-/* Compare two matrices representing local variables, defined over
+/* Does "local" have an explicit representation for all local variables?
+ */
+isl_bool isl_local_divs_known(__isl_keep isl_local *local)
+{
+	int i, n;
+
+	if (!local)
+		return isl_bool_error;
+
+	n = isl_local_dim(local, isl_dim_div);
+	for (i = 0; i < n; ++i) {
+		isl_bool unknown = isl_local_div_is_marked_unknown(local, i);
+		if (unknown < 0 || unknown)
+			return isl_bool_not(unknown);
+	}
+
+	return isl_bool_true;
+}
+
+/* Compare two sets of local variables, defined over
  * the same space.
  *
- * Return -1 if "div1" is "smaller" than "div2", 1 if "div1" is "greater"
- * than "div2" and 0 if they are equal.
+ * Return -1 if "local1" is "smaller" than "local2", 1 if "local1" is "greater"
+ * than "local2" and 0 if they are equal.
  *
  * The order is fairly arbitrary.  We do "prefer" divs that only involve
  * earlier dimensions in the sense that we consider matrices where
  * the first differing div involves earlier dimensions to be smaller.
  */
-int isl_local_cmp(__isl_keep isl_mat *div1, __isl_keep isl_mat *div2)
+int isl_local_cmp(__isl_keep isl_local *local1, __isl_keep isl_local *local2)
 {
 	int i;
 	int cmp;
 	isl_bool unknown1, unknown2;
 	int last1, last2;
 	int n_col;
+	isl_mat *mat1 = local1;
+	isl_mat *mat2 = local2;
 
-	if (div1 == div2)
+	if (local1 == local2)
 		return 0;
-	if (!div1)
+	if (!local1)
 		return -1;
-	if (!div2)
+	if (!local2)
 		return 1;
 
-	if (div1->n_row != div2->n_row)
-		return div1->n_row - div2->n_row;
+	if (mat1->n_row != mat2->n_row)
+		return mat1->n_row - mat2->n_row;
 
-	n_col = isl_mat_cols(div1);
-	for (i = 0; i < div1->n_row; ++i) {
-		unknown1 = isl_local_div_is_marked_unknown(div1, i);
-		unknown2 = isl_local_div_is_marked_unknown(div2, i);
+	n_col = isl_mat_cols(mat1);
+	for (i = 0; i < mat1->n_row; ++i) {
+		unknown1 = isl_local_div_is_marked_unknown(local1, i);
+		unknown2 = isl_local_div_is_marked_unknown(local2, i);
 		if (unknown1 && unknown2)
 			continue;
 		if (unknown1)
 			return 1;
 		if (unknown2)
 			return -1;
-		last1 = isl_seq_last_non_zero(div1->row[i] + 1, n_col - 1);
-		last2 = isl_seq_last_non_zero(div2->row[i] + 1, n_col - 1);
+		last1 = isl_seq_last_non_zero(mat1->row[i] + 1, n_col - 1);
+		last2 = isl_seq_last_non_zero(mat2->row[i] + 1, n_col - 1);
 		if (last1 != last2)
 			return last1 - last2;
-		cmp = isl_seq_cmp(div1->row[i], div2->row[i], n_col);
+		cmp = isl_seq_cmp(mat1->row[i], mat2->row[i], n_col);
 		if (cmp != 0)
 			return cmp;
 	}
 
 	return 0;
 }
+
+/* Extend a vector "v" representing an integer point
+ * in the domain space of "local"
+ * to one that also includes values for the local variables.
+ * All local variables are required to have an explicit representation.
+ */
+__isl_give isl_vec *isl_local_extend_point_vec(__isl_keep isl_local *local,
+	__isl_take isl_vec *v)
+{
+	unsigned n_div;
+	isl_bool known;
+	isl_mat *mat = local;
+
+	if (!local || !v)
+		return isl_vec_free(v);
+	known = isl_local_divs_known(local);
+	if (known < 0)
+		return isl_vec_free(v);
+	if (!known)
+		isl_die(isl_local_get_ctx(local), isl_error_invalid,
+			"unknown local variables", return isl_vec_free(v));
+	if (isl_vec_size(v) != 1 + isl_local_dim(local, isl_dim_set))
+		isl_die(isl_local_get_ctx(local), isl_error_invalid,
+			"incorrect size", return isl_vec_free(v));
+	if (!isl_int_is_one(v->el[0]))
+		isl_die(isl_local_get_ctx(local), isl_error_invalid,
+			"expecting integer point", return isl_vec_free(v));
+	n_div = isl_local_dim(local, isl_dim_div);
+	if (n_div != 0) {
+		int i;
+		unsigned dim = isl_local_dim(local, isl_dim_set);
+		v = isl_vec_add_els(v, n_div);
+		if (!v)
+			return NULL;
+
+		for (i = 0; i < n_div; ++i) {
+			isl_seq_inner_product(mat->row[i] + 1, v->el,
+						1 + dim + i, &v->el[1+dim+i]);
+			isl_int_fdiv_q(v->el[1+dim+i], v->el[1+dim+i],
+					mat->row[i][0]);
+		}
+	}
+
+	return v;
+}

Modified: polly/trunk/lib/External/isl/isl_local.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_local.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_local.h (original)
+++ polly/trunk/lib/External/isl/isl_local.h Sat Apr 21 01:34:22 2018
@@ -3,8 +3,15 @@
 
 #include <isl/mat.h>
 
-isl_bool isl_local_div_is_marked_unknown(__isl_keep isl_mat *div, int pos);
-isl_bool isl_local_div_is_known(__isl_keep isl_mat *div, int pos);
-int isl_local_cmp(__isl_keep isl_mat *div1, __isl_keep isl_mat *div2);
+typedef isl_mat isl_local;
+
+isl_bool isl_local_div_is_marked_unknown(__isl_keep isl_local *local, int pos);
+isl_bool isl_local_div_is_known(__isl_keep isl_local *local, int pos);
+isl_bool isl_local_divs_known(__isl_keep isl_local *local);
+
+int isl_local_cmp(__isl_keep isl_local *local1, __isl_keep isl_local *local2);
+
+__isl_give isl_vec *isl_local_extend_point_vec(__isl_keep isl_local *local,
+	__isl_take isl_vec *v);
 
 #endif

Modified: polly/trunk/lib/External/isl/isl_local_space.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_local_space.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_local_space.c (original)
+++ polly/trunk/lib/External/isl/isl_local_space.c Sat Apr 21 01:34:22 2018
@@ -11,12 +11,14 @@
  */
 
 #include <isl_ctx_private.h>
+#include <isl/id.h>
 #include <isl_map_private.h>
 #include <isl_local_space_private.h>
 #include <isl_space_private.h>
 #include <isl_mat_private.h>
 #include <isl_aff_private.h>
 #include <isl_vec_private.h>
+#include <isl_point_private.h>
 #include <isl_seq.h>
 #include <isl_local.h>
 
@@ -165,6 +167,30 @@ isl_bool isl_local_space_has_equal_space
 	return isl_space_is_equal(ls1->dim, ls2->dim);
 }
 
+/* Is the space of "ls" equal to "space"?
+ */
+isl_bool isl_local_space_has_space(__isl_keep isl_local_space *ls,
+	__isl_keep isl_space *space)
+{
+	return isl_space_is_equal(isl_local_space_peek_space(ls), space);
+}
+
+/* Check that the space of "ls" is equal to "space".
+ */
+static isl_stat isl_local_space_check_has_space(__isl_keep isl_local_space *ls,
+	__isl_keep isl_space *space)
+{
+	isl_bool ok;
+
+	ok = isl_local_space_has_space(ls, space);
+	if (ok < 0)
+		return isl_stat_error;
+	if (!ok)
+		isl_die(isl_local_space_get_ctx(ls), isl_error_invalid,
+			"spaces don't match", return isl_stat_error);
+	return isl_stat_ok;
+}
+
 /* Return true if the two local spaces are identical, with identical
  * expressions for the integer divisions.
  */
@@ -363,12 +389,19 @@ __isl_give isl_aff *isl_local_space_get_
 		return drop_unknown_divs_and_extract_div(ls, pos);
 }
 
-__isl_give isl_space *isl_local_space_get_space(__isl_keep isl_local_space *ls)
+/* Return the space of "ls".
+ */
+__isl_keep isl_space *isl_local_space_peek_space(__isl_keep isl_local_space *ls)
 {
 	if (!ls)
 		return NULL;
 
-	return isl_space_copy(ls->dim);
+	return ls->dim;
+}
+
+__isl_give isl_space *isl_local_space_get_space(__isl_keep isl_local_space *ls)
+{
+	return isl_space_copy(isl_local_space_peek_space(ls));
 }
 
 /* Return the space of "ls".
@@ -422,6 +455,13 @@ error:
 	return NULL;
 }
 
+/* Return the local variables of "ls".
+ */
+__isl_keep isl_local *isl_local_space_peek_local(__isl_keep isl_local_space *ls)
+{
+	return ls ? ls->div : NULL;
+}
+
 /* Replace the identifier of the tuple of type "type" by "id".
  */
 __isl_give isl_local_space *isl_local_space_set_tuple_id(
@@ -876,18 +916,9 @@ isl_bool isl_local_space_div_is_known(__
  */
 isl_bool isl_local_space_divs_known(__isl_keep isl_local_space *ls)
 {
-	int i;
-
 	if (!ls)
 		return isl_bool_error;
-
-	for (i = 0; i < ls->div->n_row; ++i) {
-		isl_bool unknown = isl_local_space_div_is_marked_unknown(ls, i);
-		if (unknown < 0 || unknown)
-			return isl_bool_not(unknown);
-	}
-
-	return isl_bool_true;
+	return isl_local_divs_known(ls->div);
 }
 
 __isl_give isl_local_space *isl_local_space_domain(
@@ -1344,7 +1375,7 @@ __isl_give isl_local_space *isl_local_sp
 			"spaces don't match", goto error);
 
 	n_div_ls = isl_local_space_dim(ls, isl_dim_div);
-	n_div_ma = ma->n ? isl_aff_dim(ma->p[0], isl_dim_div) : 0;
+	n_div_ma = ma->n ? isl_aff_dim(ma->u.p[0], isl_dim_div) : 0;
 
 	space = isl_space_domain(isl_multi_aff_get_space(ma));
 	res = isl_local_space_alloc(space, n_div_ma + n_div_ls);
@@ -1353,7 +1384,7 @@ __isl_give isl_local_space *isl_local_sp
 
 	if (n_div_ma) {
 		isl_mat_free(res->div);
-		res->div = isl_mat_copy(ma->p[0]->ls->div);
+		res->div = isl_mat_copy(ma->u.p[0]->ls->div);
 		res->div = isl_mat_add_zero_cols(res->div, n_div_ls);
 		res->div = isl_mat_add_rows(res->div, n_div_ls);
 		if (!res->div)
@@ -1514,3 +1545,39 @@ __isl_give isl_local_space *isl_local_sp
 
 	return ls;
 }
+
+/* Lift the point "pnt", living in the space of "ls"
+ * to live in a space with extra coordinates corresponding
+ * to the local variables of "ls".
+ */
+__isl_give isl_point *isl_local_space_lift_point(__isl_take isl_local_space *ls,
+	__isl_take isl_point *pnt)
+{
+	unsigned n_local;
+	isl_space *space;
+	isl_local *local;
+	isl_vec *vec;
+
+	if (isl_local_space_check_has_space(ls, isl_point_peek_space(pnt)) < 0)
+		goto error;
+
+	local = isl_local_space_peek_local(ls);
+	n_local = isl_local_space_dim(ls, isl_dim_div);
+
+	space = isl_point_take_space(pnt);
+	vec = isl_point_take_vec(pnt);
+
+	space = isl_space_lift(space, n_local);
+	vec = isl_local_extend_point_vec(local, vec);
+
+	pnt = isl_point_restore_vec(pnt, vec);
+	pnt = isl_point_restore_space(pnt, space);
+
+	isl_local_space_free(ls);
+
+	return pnt;
+error:
+	isl_local_space_free(ls);
+	isl_point_free(pnt);
+	return NULL;
+}

Modified: polly/trunk/lib/External/isl/isl_local_space_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_local_space_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_local_space_private.h (original)
+++ polly/trunk/lib/External/isl/isl_local_space_private.h Sat Apr 21 01:34:22 2018
@@ -19,6 +19,9 @@ __isl_give isl_local_space *isl_local_sp
 __isl_give isl_local_space *isl_local_space_alloc_div(__isl_take isl_space *dim,
 	__isl_take isl_mat *div);
 
+__isl_keep isl_space *isl_local_space_peek_space(
+	__isl_keep isl_local_space *ls);
+
 __isl_give isl_local_space *isl_local_space_swap_div(
 	__isl_take isl_local_space *ls, int a, int b);
 __isl_give isl_local_space *isl_local_space_add_div(
@@ -79,4 +82,10 @@ __isl_give isl_local_space *isl_local_sp
 int isl_local_space_cmp(__isl_keep isl_local_space *ls1,
 	__isl_keep isl_local_space *ls2);
 
+__isl_give isl_point *isl_local_space_lift_point(__isl_take isl_local_space *ls,
+	__isl_take isl_point *pnt);
+
+isl_bool isl_local_space_has_space(__isl_keep isl_local_space *ls,
+	__isl_keep isl_space *space);
+
 #endif

Modified: polly/trunk/lib/External/isl/isl_map.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_map.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_map.c (original)
+++ polly/trunk/lib/External/isl/isl_map.c Sat Apr 21 01:34:22 2018
@@ -23,6 +23,7 @@
 #include <isl_ctx_private.h>
 #include <isl_map_private.h>
 #include <isl_blk.h>
+#include <isl/id.h>
 #include <isl/constraint.h>
 #include "isl_space_private.h"
 #include "isl_equalities.h"
@@ -2204,6 +2205,21 @@ error:
 	return NULL;
 }
 
+/* Check that there are "n" dimensions of type "type" starting at "first"
+ * in "map".
+ */
+static isl_stat isl_map_check_range(__isl_keep isl_map *map,
+	enum isl_dim_type type, unsigned first, unsigned n)
+{
+	if (!map)
+		return isl_stat_error;
+	if (first + n > isl_map_dim(map, type) || first + n < first)
+		isl_die(isl_map_get_ctx(map), isl_error_invalid,
+			"position or range out of bounds",
+			return isl_stat_error);
+	return isl_stat_ok;
+}
+
 /* Drop "n" dimensions of type "type" starting at "first".
  *
  * In principle, this frees up some extra variables as the number
@@ -2274,10 +2290,8 @@ __isl_give isl_map *isl_map_drop(__isl_t
 {
 	int i;
 
-	if (!map)
-		goto error;
-
-	isl_assert(map->ctx, first + n <= isl_map_dim(map, type), goto error);
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
 
 	if (n == 0 && !isl_space_is_named_or_nested(map->dim, type))
 		return map;
@@ -2366,14 +2380,11 @@ __isl_give isl_map *isl_map_eliminate(__
 {
 	int i;
 
-	if (!map)
-		return NULL;
 	if (n == 0)
 		return map;
 
-	if (first + n > isl_map_dim(map, type) || first + n < first)
-		isl_die(map->ctx, isl_error_invalid,
-			"index out of bounds", goto error);
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
 
 	map = isl_map_cow(map);
 	if (!map)
@@ -2802,13 +2813,9 @@ isl_bool isl_map_involves_dims(__isl_kee
 {
 	int i;
 
-	if (!map)
+	if (isl_map_check_range(map, type, first, n) < 0)
 		return isl_bool_error;
 
-	if (first + n > isl_map_dim(map, type))
-		isl_die(map->ctx, isl_error_invalid,
-			"index out of bounds", return isl_bool_error);
-
 	for (i = 0; i < map->n; ++i) {
 		isl_bool involves = isl_basic_map_involves_dims(map->p[i],
 							    type, first, n);
@@ -2961,15 +2968,9 @@ static __isl_give isl_map *drop_constrai
 		enum isl_dim_type type, unsigned first, unsigned n))
 {
 	int i;
-	unsigned dim;
-
-	if (!map)
-		return NULL;
 
-	dim = isl_map_dim(map, type);
-	if (first + n > dim || first + n < first)
-		isl_die(isl_map_get_ctx(map), isl_error_invalid,
-			"index out of bounds", return isl_map_free(map));
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
 
 	map = isl_map_cow(map);
 	if (!map)
@@ -3142,9 +3143,8 @@ __isl_give isl_map *isl_map_remove_dims(
 		return map;
 
 	map = isl_map_cow(map);
-	if (!map)
-		return NULL;
-	isl_assert(map->ctx, first + n <= isl_map_dim(map, type), goto error);
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
 	
 	for (i = 0; i < map->n; ++i) {
 		map->p[i] = isl_basic_map_eliminate_vars(map->p[i],
@@ -4117,16 +4117,14 @@ __isl_give isl_map *isl_map_move_dims(__
 {
 	int i;
 
-	if (!map)
-		return NULL;
 	if (n == 0) {
 		map = isl_map_reset(map, src_type);
 		map = isl_map_reset(map, dst_type);
 		return map;
 	}
 
-	isl_assert(map->ctx, src_pos + n <= isl_map_dim(map, src_type),
-		goto error);
+	if (isl_map_check_range(map, src_type, src_pos, n))
+		return isl_map_free(map);
 
 	if (dst_type == src_type && dst_pos == src_pos)
 		return map;
@@ -4354,13 +4352,11 @@ __isl_give isl_map *isl_map_project_out(
 {
 	int i;
 
-	if (!map)
-		return NULL;
-
 	if (n == 0)
 		return map_space_reset(map, type);
 
-	isl_assert(map->ctx, first + n <= isl_map_dim(map, type), goto error);
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
 
 	map = isl_map_cow(map);
 	if (!map)
@@ -4382,6 +4378,22 @@ error:
 	return NULL;
 }
 
+/* Turn all the dimensions of type "type", except the "n" starting at "first"
+ * into existentially quantified variables.
+ */
+__isl_give isl_map *isl_map_project_onto(__isl_take isl_map *map,
+	enum isl_dim_type type, unsigned first, unsigned n)
+{
+	unsigned dim;
+
+	if (isl_map_check_range(map, type, first, n) < 0)
+		return isl_map_free(map);
+	dim = isl_map_dim(map, type);
+	map = isl_map_project_out(map, type, first + n, dim - (first + n));
+	map = isl_map_project_out(map, type, 0, first);
+	return map;
+}
+
 /* Turn the n dimensions of type type, starting at first
  * into existentially quantified variables.
  */
@@ -5503,6 +5515,23 @@ __isl_give isl_basic_set *isl_basic_set_
 							dim));
 }
 
+/* Check that the total dimensions of "map" and "space" are the same.
+ */
+static isl_stat check_map_space_equal_total_dim(__isl_keep isl_map *map,
+	__isl_keep isl_space *space)
+{
+	unsigned dim1, dim2;
+
+	if (!map || !space)
+		return isl_stat_error;
+	dim1 = isl_map_dim(map, isl_dim_all);
+	dim2 = isl_space_dim(space, isl_dim_all);
+	if (dim1 == dim2)
+		return isl_stat_ok;
+	isl_die(isl_map_get_ctx(map), isl_error_invalid,
+		"total dimensions do not match", return isl_stat_error);
+}
+
 __isl_give isl_map *isl_map_reset_space(__isl_take isl_map *map,
 	__isl_take isl_space *dim)
 {
@@ -5528,6 +5557,37 @@ error:
 	return NULL;
 }
 
+/* Replace the space of "map" by "space", without modifying
+ * the dimension of "map".
+ *
+ * If the space of "map" is identical to "space" (including the identifiers
+ * of the input and output dimensions), then simply return the original input.
+ */
+__isl_give isl_map *isl_map_reset_equal_dim_space(__isl_take isl_map *map,
+	__isl_take isl_space *space)
+{
+	isl_bool equal;
+	isl_space *map_space;
+
+	map_space = isl_map_peek_space(map);
+	equal = isl_space_is_equal(map_space, space);
+	if (equal >= 0 && equal)
+		equal = isl_space_has_equal_ids(map_space, space);
+	if (equal < 0)
+		goto error;
+	if (equal) {
+		isl_space_free(space);
+		return map;
+	}
+	if (check_map_space_equal_total_dim(map, space) < 0)
+		goto error;
+	return isl_map_reset_space(map, space);
+error:
+	isl_map_free(map);
+	isl_space_free(space);
+	return NULL;
+}
+
 __isl_give isl_set *isl_set_reset_space(__isl_take isl_set *set,
 	__isl_take isl_space *dim)
 {
@@ -9059,6 +9119,24 @@ struct isl_set *isl_set_remove_empty_par
 	return set_from_map(isl_map_remove_empty_parts(set_to_map(set)));
 }
 
+/* Create a binary relation that maps the shared initial "pos" dimensions
+ * of "bset1" and "bset2" to the remaining dimensions of "bset1" and "bset2".
+ */
+static __isl_give isl_basic_map *join_initial(__isl_keep isl_basic_set *bset1,
+	__isl_keep isl_basic_set *bset2, int pos)
+{
+	isl_basic_map *bmap1;
+	isl_basic_map *bmap2;
+
+	bmap1 = isl_basic_map_from_range(isl_basic_set_copy(bset1));
+	bmap2 = isl_basic_map_from_range(isl_basic_set_copy(bset2));
+	bmap1 = isl_basic_map_move_dims(bmap1, isl_dim_in, 0,
+					isl_dim_out, 0, pos);
+	bmap2 = isl_basic_map_move_dims(bmap2, isl_dim_in, 0,
+					isl_dim_out, 0, pos);
+	return isl_basic_map_range_product(bmap1, bmap2);
+}
+
 /* Given two basic sets bset1 and bset2, compute the maximal difference
  * between the values of dimension pos in bset1 and those in bset2
  * for any common value of the parameters and dimensions preceding pos.
@@ -9068,7 +9146,6 @@ static enum isl_lp_result basic_set_maxi
 	int pos, isl_int *opt)
 {
 	isl_basic_map *bmap1;
-	isl_basic_map *bmap2;
 	struct isl_ctx *ctx;
 	struct isl_vec *obj;
 	unsigned total;
@@ -9082,13 +9159,7 @@ static enum isl_lp_result basic_set_maxi
 	nparam = isl_basic_set_n_param(bset1);
 	dim1 = isl_basic_set_n_dim(bset1);
 
-	bmap1 = isl_basic_map_from_range(isl_basic_set_copy(bset1));
-	bmap2 = isl_basic_map_from_range(isl_basic_set_copy(bset2));
-	bmap1 = isl_basic_map_move_dims(bmap1, isl_dim_in, 0,
-					isl_dim_out, 0, pos);
-	bmap2 = isl_basic_map_move_dims(bmap2, isl_dim_in, 0,
-					isl_dim_out, 0, pos);
-	bmap1 = isl_basic_map_range_product(bmap1, bmap2);
+	bmap1 = join_initial(bset1, bset2, pos);
 	if (!bmap1)
 		return isl_lp_error;
 
@@ -9160,28 +9231,33 @@ int isl_basic_set_compare_at(struct isl_
 int isl_basic_set_follows_at(__isl_keep isl_basic_set *bset1,
 	__isl_keep isl_basic_set *bset2, int pos)
 {
-	isl_int opt;
-	enum isl_lp_result res;
-	int cmp;
-
-	isl_int_init(opt);
-
-	res = basic_set_maximal_difference_at(bset1, bset2, pos, &opt);
-
-	if (res == isl_lp_empty)
-		cmp = -1;
-	else if ((res == isl_lp_ok && isl_int_is_pos(opt)) ||
-		  res == isl_lp_unbounded)
-		cmp = 1;
-	else if (res == isl_lp_ok && isl_int_is_neg(opt))
-		cmp = -1;
-	else if (res == isl_lp_ok)
-		cmp = 0;
-	else
-		cmp = -2;
+	isl_bool empty;
+	isl_basic_map *bmap;
+	unsigned dim1;
 
-	isl_int_clear(opt);
-	return cmp;
+	dim1 = isl_basic_set_dim(bset1, isl_dim_set);
+	bmap = join_initial(bset1, bset2, pos);
+	bmap = isl_basic_map_order_ge(bmap, isl_dim_out, 0,
+					    isl_dim_out, dim1 - pos);
+	empty = isl_basic_map_is_empty(bmap);
+	if (empty < 0)
+		goto error;
+	if (empty) {
+		isl_basic_map_free(bmap);
+		return -1;
+	}
+	bmap = isl_basic_map_order_gt(bmap, isl_dim_out, 0,
+					    isl_dim_out, dim1 - pos);
+	empty = isl_basic_map_is_empty(bmap);
+	if (empty < 0)
+		goto error;
+	isl_basic_map_free(bmap);
+	if (empty)
+		return 0;
+	return 1;
+error:
+	isl_basic_map_free(bmap);
+	return -2;
 }
 
 /* Given two sets set1 and set2, check whether
@@ -12231,7 +12307,7 @@ __isl_give isl_basic_map *isl_basic_map_
 		isl_aff *aff;
 		isl_basic_map *bmap_i;
 
-		aff = isl_aff_copy(maff->p[i]);
+		aff = isl_aff_copy(maff->u.p[i]);
 		bmap_i = isl_basic_map_from_aff2(aff, rational);
 
 		bmap = isl_basic_map_flat_range_product(bmap, bmap_i);
@@ -12762,7 +12838,7 @@ static int set_ma_divs(__isl_keep isl_ba
 	if (n_div == 0)
 		return 0;
 
-	ls = isl_aff_get_domain_local_space(ma->p[0]);
+	ls = isl_aff_get_domain_local_space(ma->u.p[0]);
 	if (!ls)
 		return -1;
 
@@ -12808,7 +12884,7 @@ static int multi_aff_strides(__isl_keep
 	int strides = 0;
 
 	for (i = 0; i < ma->n; ++i)
-		if (!isl_int_is_one(ma->p[i]->v->el[0]))
+		if (!isl_int_is_one(ma->u.p[i]->v->el[0]))
 			strides++;
 
 	return strides;
@@ -12848,7 +12924,7 @@ static __isl_give isl_basic_map *add_ma_
 	for (i = 0; i < ma->n; ++i) {
 		int o_bmap = 0, o_ma = 1;
 
-		if (isl_int_is_one(ma->p[i]->v->el[0]))
+		if (isl_int_is_one(ma->u.p[i]->v->el[0]))
 			continue;
 		div = isl_basic_map_alloc_div(bmap);
 		k = isl_basic_map_alloc_equality(bmap);
@@ -12856,23 +12932,23 @@ static __isl_give isl_basic_map *add_ma_
 			goto error;
 		isl_int_set_si(bmap->div[div][0], 0);
 		isl_seq_cpy(bmap->eq[k] + o_bmap,
-			    ma->p[i]->v->el + o_ma, 1 + n_param);
+			    ma->u.p[i]->v->el + o_ma, 1 + n_param);
 		o_bmap += 1 + n_param;
 		o_ma += 1 + n_param;
 		isl_seq_clr(bmap->eq[k] + o_bmap, n_before);
 		o_bmap += n_before;
 		isl_seq_cpy(bmap->eq[k] + o_bmap,
-			    ma->p[i]->v->el + o_ma, n_in);
+			    ma->u.p[i]->v->el + o_ma, n_in);
 		o_bmap += n_in;
 		o_ma += n_in;
 		isl_seq_clr(bmap->eq[k] + o_bmap, n_after);
 		o_bmap += n_after;
 		isl_seq_cpy(bmap->eq[k] + o_bmap,
-			    ma->p[i]->v->el + o_ma, n_div_ma);
+			    ma->u.p[i]->v->el + o_ma, n_div_ma);
 		o_bmap += n_div_ma;
 		o_ma += n_div_ma;
 		isl_seq_clr(bmap->eq[k] + o_bmap, 1 + total - o_bmap);
-		isl_int_neg(bmap->eq[k][1 + total], ma->p[i]->v->el[0]);
+		isl_int_neg(bmap->eq[k][1 + total], ma->u.p[i]->v->el[0]);
 		total++;
 	}
 
@@ -12975,7 +13051,7 @@ __isl_give isl_basic_map *isl_basic_map_
 		n_after = 0;
 	}
 	n_div_bmap = isl_basic_map_dim(bmap, isl_dim_div);
-	n_div_ma = ma->n ? isl_aff_dim(ma->p[0], isl_dim_div) : 0;
+	n_div_ma = ma->n ? isl_aff_dim(ma->u.p[0], isl_dim_div) : 0;
 
 	space = isl_multi_aff_get_domain_space(ma);
 	space = isl_space_set(isl_basic_map_get_space(bmap), type, space);
@@ -13351,18 +13427,26 @@ __isl_give isl_map *isl_map_preimage_ran
  * We create a separate isl_multi_aff to effectuate this change
  * in order to avoid spurious splitting of the map along the pieces
  * of "mpa".
+ * If "mpa" has a non-trivial explicit domain, however,
+ * then the full substitution should be performed.
  */
 __isl_give isl_map *isl_map_preimage_multi_pw_aff(__isl_take isl_map *map,
 	enum isl_dim_type type, __isl_take isl_multi_pw_aff *mpa)
 {
 	int n;
+	isl_bool full;
 	isl_pw_multi_aff *pma;
 
 	if (!map || !mpa)
 		goto error;
 
 	n = isl_map_dim(map, type);
-	if (!isl_map_involves_dims(map, type, 0, n)) {
+	full = isl_map_involves_dims(map, type, 0, n);
+	if (full >= 0 && !full)
+		full = isl_multi_pw_aff_has_non_trivial_domain(mpa);
+	if (full < 0)
+		goto error;
+	if (!full) {
 		isl_space *space;
 		isl_multi_aff *ma;
 

Modified: polly/trunk/lib/External/isl/isl_map_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_map_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_map_private.h (original)
+++ polly/trunk/lib/External/isl/isl_map_private.h Sat Apr 21 01:34:22 2018
@@ -169,6 +169,7 @@ __isl_give isl_map *isl_map_reset(__isl_
 __isl_keep isl_space *isl_basic_map_peek_space(
 	__isl_keep const isl_basic_map *bmap);
 __isl_keep isl_space *isl_basic_set_peek_space(__isl_keep isl_basic_set *bset);
+__isl_keep isl_space *isl_map_peek_space(__isl_keep const isl_map *map);
 
 __isl_give isl_basic_set *isl_basic_set_reset_space(
 	__isl_take isl_basic_set *bset, __isl_take isl_space *dim);
@@ -176,6 +177,8 @@ __isl_give isl_basic_map *isl_basic_map_
 	__isl_take isl_basic_map *bmap, __isl_take isl_space *dim);
 __isl_give isl_map *isl_map_reset_space(__isl_take isl_map *map,
 	__isl_take isl_space *dim);
+__isl_give isl_map *isl_map_reset_equal_dim_space(__isl_take isl_map *map,
+	__isl_take isl_space *space);
 
 unsigned isl_basic_map_offset(struct isl_basic_map *bmap,
 					enum isl_dim_type type);
@@ -355,6 +358,8 @@ __isl_give isl_map *isl_map_eliminate(__
 	enum isl_dim_type type, unsigned first, unsigned n);
 __isl_give isl_set *isl_set_eliminate(__isl_take isl_set *set,
 	enum isl_dim_type type, unsigned first, unsigned n);
+__isl_give isl_map *isl_map_project_onto(__isl_take isl_map *map,
+	enum isl_dim_type type, unsigned first, unsigned n);
 
 int isl_basic_map_add_div_constraint(__isl_keep isl_basic_map *bmap,
 	unsigned div, int sign);
@@ -489,6 +494,7 @@ isl_bool isl_basic_map_plain_is_non_empt
 isl_bool isl_basic_map_plain_is_single_valued(__isl_keep isl_basic_map *bmap);
 
 isl_bool isl_map_is_set(__isl_keep isl_map *map);
+isl_bool isl_map_is_params(__isl_keep isl_map *map);
 
 isl_bool isl_basic_set_plain_dim_is_fixed(__isl_keep isl_basic_set *bset,
 	unsigned dim, isl_int *val);

Added: polly/trunk/lib/External/isl/isl_multi_align_set.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_align_set.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_align_set.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_align_set.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,7 @@
+#define ALIGN_DOMBASE set
+#define ALIGN_DOM isl_set
+
+#include <isl_multi_align_templ.c>
+
+#undef ALIGN_DOMBASE
+#undef ALIGN_DOM

Added: polly/trunk/lib/External/isl/isl_multi_align_templ.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_align_templ.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_align_templ.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_align_templ.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2017      Sven Verdoolaege
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege,
+ */
+
+/* Align the parameters of "multi" and "domain" (if needed) and
+ * call "fn".
+ */
+static __isl_give MULTI(BASE) *FN(FN(MULTI(BASE),align_params),ALIGN_DOMBASE)(
+	__isl_take MULTI(BASE) *multi, __isl_take ALIGN_DOM *domain,
+	__isl_give MULTI(BASE) *fn(__isl_take MULTI(BASE) *multi,
+		__isl_take ALIGN_DOM *domain))
+{
+	isl_bool aligned;
+	isl_bool named;
+	isl_space *dom_space;
+
+	aligned = FN(ALIGN_DOM,space_has_equal_params)(domain, multi->space);
+	if (aligned < 0)
+		goto error;
+	if (aligned)
+		return fn(multi, domain);
+
+	dom_space = FN(ALIGN_DOM,peek_space)(domain);
+	named = isl_space_has_named_params(multi->space);
+	if (named >= 0 && named)
+		named = isl_space_has_named_params(dom_space);
+	if (named < 0)
+		goto error;
+	if (!named)
+		isl_die(FN(MULTI(BASE),get_ctx)(multi), isl_error_invalid,
+			"unaligned unnamed parameters", goto error);
+	multi = FN(MULTI(BASE),align_params)(multi,
+					    FN(ALIGN_DOM,get_space)(domain));
+	domain = FN(ALIGN_DOM,align_params)(domain,
+					    FN(MULTI(BASE),get_space)(multi));
+	return fn(multi, domain);
+error:
+	FN(MULTI(BASE),free)(multi);
+	FN(ALIGN_DOM,free)(domain);
+	return NULL;
+}

Added: polly/trunk/lib/External/isl/isl_multi_align_union_set.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_align_union_set.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_align_union_set.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_align_union_set.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,7 @@
+#define ALIGN_DOMBASE union_set
+#define ALIGN_DOM isl_union_set
+
+#include <isl_multi_align_templ.c>
+
+#undef ALIGN_DOMBASE
+#undef ALIGN_DOM

Modified: polly/trunk/lib/External/isl/isl_multi_apply_templ.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_apply_templ.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_apply_templ.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_apply_templ.c Sat Apr 21 01:34:22 2018
@@ -34,8 +34,8 @@ __isl_give MULTI(BASE) *FN(FN(MULTI(BASE
 		goto error;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = fn(multi->p[i], FN(APPLY_DOM,copy)(set));
-		if (!multi->p[i])
+		multi->u.p[i] = fn(multi->u.p[i], FN(APPLY_DOM,copy)(set));
+		if (!multi->u.p[i])
 			goto error;
 	}
 

Modified: polly/trunk/lib/External/isl/isl_multi_cmp.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_cmp.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_cmp.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_cmp.c Sat Apr 21 01:34:22 2018
@@ -31,7 +31,7 @@ int FN(MULTI(BASE),plain_cmp)(__isl_keep
 		return cmp;
 
 	for (i = 0; i < multi1->n; ++i) {
-		cmp = FN(EL,plain_cmp)(multi1->p[i], multi2->p[i]);
+		cmp = FN(EL,plain_cmp)(multi1->u.p[i], multi2->u.p[i]);
 		if (cmp != 0)
 			return cmp;
 	}

Modified: polly/trunk/lib/External/isl/isl_multi_coalesce.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_coalesce.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_coalesce.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_coalesce.c Sat Apr 21 01:34:22 2018
@@ -23,12 +23,12 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),c
 		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		EL *el = FN(EL,copy)(multi->p[i]);
+		EL *el = FN(EL,copy)(multi->u.p[i]);
 		el = FN(EL,coalesce)(el);
 		if (!el)
 			return FN(MULTI(BASE),free)(multi);
-		FN(EL,free)(multi->p[i]);
-		multi->p[i] = el;
+		FN(EL,free)(multi->u.p[i]);
+		multi->u.p[i] = el;
 	}
 
 	return multi;

Modified: polly/trunk/lib/External/isl/isl_multi_dims.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_dims.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_dims.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_dims.c Sat Apr 21 01:34:22 2018
@@ -23,17 +23,21 @@ isl_bool FN(MULTI(BASE),involves_dims)(_
 
 	if (!multi)
 		return isl_bool_error;
-	if (multi->n == 0 || n == 0)
+	if (n == 0)
 		return isl_bool_false;
 
 	for (i = 0; i < multi->n; ++i) {
 		isl_bool involves;
 
-		involves = FN(EL,involves_dims)(multi->p[i], type, first, n);
+		involves = FN(EL,involves_dims)(multi->u.p[i], type, first, n);
 		if (involves < 0 || involves)
 			return involves;
 	}
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		return FN(MULTI(BASE),involves_explicit_domain_dims)(multi,
+								type, first, n);
+
 	return isl_bool_false;
 }
 
@@ -59,10 +63,16 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),i
 	multi->space = isl_space_insert_dims(multi->space, type, first, n);
 	if (!multi->space)
 		return FN(MULTI(BASE),free)(multi);
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		multi = FN(MULTI(BASE),insert_explicit_domain_dims)(multi,
+								type, first, n);
+	if (!multi)
+		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,insert_dims)(multi->p[i], type, first, n);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,insert_dims)(multi->u.p[i],
+							type, first, n);
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 

Added: polly/trunk/lib/External/isl/isl_multi_explicit_domain.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_explicit_domain.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_explicit_domain.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_explicit_domain.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,179 @@
+/*
+ * Copyright 2017      Sven Verdoolaege
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege.
+ */
+
+/* These versions of the explicit domain functions are used
+ * when the multi expression may have an explicit domain.
+ */
+
+#include <isl_multi_macro.h>
+
+__isl_give MULTI(BASE) *FN(MULTI(BASE),cow)(__isl_take MULTI(BASE) *multi);
+
+/* Does "multi" have an explicit domain?
+ *
+ * An explicit domain is only available if "multi" is zero-dimensional.
+ */
+static int FN(MULTI(BASE),has_explicit_domain)(__isl_keep MULTI(BASE) *multi)
+{
+	return multi && multi->n == 0;
+}
+
+/* Check that "multi" has an explicit domain.
+ */
+static isl_stat FN(MULTI(BASE),check_has_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi)
+{
+	if (!multi)
+		return isl_stat_error;
+	if (!FN(MULTI(BASE),has_explicit_domain)(multi))
+		isl_die(FN(MULTI(BASE),get_ctx)(multi), isl_error_internal,
+			"expression does not have an explicit domain",
+			return isl_stat_error);
+	return isl_stat_ok;
+}
+
+/* Return the explicit domain of "multi", assuming it has one.
+ */
+static __isl_give DOM *FN(MULTI(BASE),get_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi)
+{
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi) < 0)
+		return NULL;
+	return FN(DOM,copy)(multi->u.dom);
+}
+
+/* Replace the explicit domain of "multi" by "dom", assuming it has one.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),set_explicit_domain)(
+	__isl_take MULTI(BASE) *multi, __isl_take DOM *dom)
+{
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi) < 0)
+		goto error;
+	multi = FN(MULTI(BASE),cow)(multi);
+	if (!multi || !dom)
+		goto error;
+	FN(DOM,free)(multi->u.dom);
+	multi->u.dom = dom;
+	if (!multi->u.dom)
+		return FN(MULTI(BASE),free)(multi);
+	return multi;
+error:
+	FN(MULTI(BASE),free)(multi);
+	FN(DOM,free)(dom);
+	return NULL;
+}
+
+/* Intersect the domain of "dst" with the explicit domain of "src".
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),intersect_explicit_domain)(
+	__isl_take MULTI(BASE) *dst, __isl_keep MULTI(BASE) *src)
+{
+	DOM *dom;
+
+	dom = FN(MULTI(BASE),get_explicit_domain)(src);
+	dst = FN(MULTI(BASE),intersect_domain)(dst, dom);
+
+	return dst;
+}
+
+/* Set the explicit domain of "dst" to that of "src".
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),copy_explicit_domain)(
+	__isl_take MULTI(BASE) *dst, __isl_keep MULTI(BASE) *src)
+{
+	DOM *dom;
+
+	dom = FN(MULTI(BASE),get_explicit_domain)(src);
+	dst = FN(MULTI(BASE),set_explicit_domain)(dst, dom);
+
+	return dst;
+}
+
+/* Align the parameters of the explicit domain of "multi" to those of "space".
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),align_explicit_domain_params)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_space *space)
+{
+	DOM *dom;
+
+	dom = FN(MULTI(BASE),get_explicit_domain)(multi);
+	dom = FN(DOM,align_params)(dom, space);
+	multi = FN(MULTI(BASE),set_explicit_domain)(multi, dom);
+
+	return multi;
+}
+
+/* Replace the space of the explicit domain of "multi" by "space",
+ * without modifying its dimension.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),reset_explicit_domain_space)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_space *space)
+{
+	DOM *dom;
+
+	dom = FN(MULTI(BASE),get_explicit_domain)(multi);
+	dom = FN(DOM,reset_equal_dim_space)(dom, space);
+	multi = FN(MULTI(BASE),set_explicit_domain)(multi, dom);
+
+	return multi;
+}
+
+/* Free the explicit domain of "multi".
+ */
+static void FN(MULTI(BASE),free_explicit_domain)(__isl_keep MULTI(BASE) *multi)
+{
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi) < 0)
+		return;
+	FN(DOM,free)(multi->u.dom);
+}
+
+/* Do "multi1" and "multi2" have the same explicit domain?
+ */
+static isl_bool FN(MULTI(BASE),equal_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi1, __isl_keep MULTI(BASE) *multi2)
+{
+	DOM *dom1, *dom2;
+	isl_bool equal;
+
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi1) < 0 ||
+	    FN(MULTI(BASE),check_has_explicit_domain)(multi2) < 0)
+		return isl_bool_error;
+	dom1 = FN(MULTI(BASE),get_explicit_domain)(multi1);
+	dom2 = FN(MULTI(BASE),get_explicit_domain)(multi2);
+	equal = FN(DOM,is_equal)(dom1, dom2);
+	FN(DOM,free)(dom1);
+	FN(DOM,free)(dom2);
+
+	return equal;
+}
+
+static isl_stat FN(MULTI(BASE),check_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi) __attribute__ ((unused));
+
+/* Debugging function to check that the explicit domain of "multi"
+ * has the correct space.
+ */
+isl_stat FN(MULTI(BASE),check_explicit_domain)(__isl_keep MULTI(BASE) *multi)
+{
+	isl_space *space1, *space2;
+	isl_bool equal;
+
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi) < 0)
+		return isl_stat_error;
+	space1 = isl_space_domain(isl_space_copy(multi->space));
+	space2 = FN(DOM,get_space)(multi->u.dom);
+	equal = isl_space_is_equal(space1, space2);
+	isl_space_free(space1);
+	isl_space_free(space2);
+	if (equal < 0)
+		return isl_stat_error;
+	if (!equal)
+		isl_die(FN(MULTI(BASE),get_ctx)(multi), isl_error_internal,
+			"check failed", return isl_stat_error);
+	return isl_stat_ok;
+}

Modified: polly/trunk/lib/External/isl/isl_multi_floor.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_floor.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_floor.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_floor.c Sat Apr 21 01:34:22 2018
@@ -20,8 +20,8 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),f
 		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,floor)(multi->p[i]);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,floor)(multi->u.p[i]);
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 

Modified: polly/trunk/lib/External/isl/isl_multi_hash.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_hash.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_hash.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_hash.c Sat Apr 21 01:34:22 2018
@@ -22,7 +22,7 @@ uint32_t FN(MULTI(BASE),get_hash)(__isl_
 	hash = isl_hash_init();
 	for (i = 0; i < multi->n; ++i) {
 		uint32_t el_hash;
-		el_hash = FN(EL,get_hash)(multi->p[i]);
+		el_hash = FN(EL,get_hash)(multi->u.p[i]);
 		isl_hash_hash(hash, el_hash);
 	}
 

Modified: polly/trunk/lib/External/isl/isl_multi_intersect.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_intersect.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_intersect.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_intersect.c Sat Apr 21 01:34:22 2018
@@ -10,20 +10,142 @@
 
 #include <isl_multi_macro.h>
 
+/* Does the space of "domain" correspond to that of the domain of "multi"?
+ * The parameters do not need to be aligned.
+ */
+static isl_bool FN(MULTI(BASE),compatible_domain)(
+	__isl_keep MULTI(BASE) *multi, __isl_keep DOM *domain)
+{
+	isl_bool ok;
+	isl_space *space, *domain_space;
+
+	domain_space = FN(DOM,get_space)(domain);
+	space = FN(MULTI(BASE),get_space)(multi);
+	ok = isl_space_has_domain_tuples(domain_space, space);
+	isl_space_free(space);
+	isl_space_free(domain_space);
+
+	return ok;
+}
+
+/* Check that the space of "domain" corresponds to
+ * that of the domain of "multi", ignoring parameters.
+ */
+static isl_stat FN(MULTI(BASE),check_compatible_domain)(
+	__isl_keep MULTI(BASE) *multi, __isl_keep DOM *domain)
+{
+	isl_bool ok;
+
+	ok = FN(MULTI(BASE),compatible_domain)(multi, domain);
+	if (ok < 0)
+		return isl_stat_error;
+	if (!ok)
+		isl_die(FN(DOM,get_ctx)(domain), isl_error_invalid,
+			"incompatible spaces", return isl_stat_error);
+
+	return isl_stat_ok;
+}
+
+/* Intersect the explicit domain of "multi" with "domain".
+ *
+ * The parameters of "multi" and "domain" are assumed to have been aligned.
+ *
+ * In the case of an isl_multi_union_pw_aff object, the explicit domain
+ * is allowed to have only constraints on the parameters, while
+ * "domain" contains actual domain elements.  In this case,
+ * "domain" is intersected with those parameter constraints and
+ * then used as the explicit domain of "multi".
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),domain_intersect_aligned)(
+	__isl_take MULTI(BASE) *multi, __isl_take DOM *domain)
+{
+	isl_bool is_params;
+	DOM *multi_dom;
+
+	if (FN(MULTI(BASE),check_compatible_domain)(multi, domain) < 0)
+		goto error;
+	if (FN(MULTI(BASE),check_has_explicit_domain)(multi) < 0)
+		goto error;
+	is_params = FN(DOM,is_params)(multi->u.dom);
+	if (is_params < 0)
+		goto error;
+	multi_dom = FN(MULTI(BASE),get_explicit_domain)(multi);
+	if (!is_params) {
+		domain = FN(DOM,intersect)(multi_dom, domain);
+	} else {
+		isl_set *params;
+
+		params = FN(DOM,params)(multi_dom);
+		domain = FN(DOM,intersect_params)(domain, params);
+	}
+	multi = FN(MULTI(BASE),set_explicit_domain)(multi, domain);
+	return multi;
+error:
+	FN(MULTI(BASE),free)(multi);
+	FN(DOM,free)(domain);
+	return NULL;
+}
+
+/* Intersect the explicit domain of "multi" with "domain".
+ * First align the parameters, if needed.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),domain_intersect)(
+	__isl_take MULTI(BASE) *multi, __isl_take DOM *domain)
+{
+	return FN(FN(MULTI(BASE),align_params),DOMBASE)(multi, domain,
+				    FN(MULTI(BASE),domain_intersect_aligned));
+}
+
 /* Intersect the domain of "multi" with "domain".
+ *
+ * If "multi" has an explicit domain, then only this domain
+ * needs to be intersected.
  */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),intersect_domain)(
 	__isl_take MULTI(BASE) *multi, __isl_take DOM *domain)
 {
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		return FN(MULTI(BASE),domain_intersect)(multi, domain);
 	return FN(FN(MULTI(BASE),apply),DOMBASE)(multi, domain,
 					&FN(EL,intersect_domain));
 }
 
+/* Intersect the parameter domain of the explicit domain of "multi"
+ * with "domain".
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),domain_intersect_params_aligned)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_set *domain)
+{
+	DOM *multi_dom;
+
+	multi_dom = FN(MULTI(BASE),get_explicit_domain)(multi);
+	multi_dom = FN(DOM,intersect_params)(multi_dom, domain);
+	multi = FN(MULTI(BASE),set_explicit_domain)(multi, multi_dom);
+
+	return multi;
+}
+
+/* Intersect the parameter domain of the explicit domain of "multi"
+ * with "domain".
+ * First align the parameters, if needed.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),domain_intersect_params)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_set *domain)
+{
+	return FN(FN(MULTI(BASE),align_params),set)(multi, domain,
+			    FN(MULTI(BASE),domain_intersect_params_aligned));
+}
+
 /* Intersect the parameter domain of "multi" with "domain".
+ *
+ * If "multi" has an explicit domain, then only this domain
+ * needs to be intersected.
  */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),intersect_params)(
 	__isl_take MULTI(BASE) *multi, __isl_take isl_set *domain)
 {
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		return FN(MULTI(BASE),domain_intersect_params)(multi, domain);
 	return FN(MULTI(BASE),apply_set)(multi, domain,
 					&FN(EL,intersect_params));
 }

Added: polly/trunk/lib/External/isl/isl_multi_no_explicit_domain.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_no_explicit_domain.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_no_explicit_domain.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_no_explicit_domain.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,165 @@
+/*
+ * Copyright 2017      Sven Verdoolaege
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege.
+ */
+
+/* These versions of the explicit domain functions are used
+ * when the multi expression cannot have an explicit domain.
+ */
+
+#include <isl/space.h>
+
+#include <isl_multi_macro.h>
+
+/* Does "multi" have an explicit domain?
+ *
+ * No.
+ */
+static int FN(MULTI(BASE),has_explicit_domain)(__isl_keep MULTI(BASE) *multi)
+{
+	return 0;
+}
+
+/* Initialize the explicit domain of "multi".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),init_explicit_domain)(
+	__isl_take MULTI(BASE) *multi)
+{
+	return multi;
+}
+
+/* Intersect the domain of "dst" with the explicit domain of "src".
+ * "src" cannot have an explicit domain, so this function is never called.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),intersect_explicit_domain)(
+	__isl_take MULTI(BASE) *dst, __isl_keep MULTI(BASE) *src)
+{
+	return dst;
+}
+
+/* Set the explicit domain of "dst" to that of "src".
+ * "src" and "dst" cannot have an explicit domain,
+ * so this function is never called.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),copy_explicit_domain)(
+	__isl_take MULTI(BASE) *dst, __isl_keep MULTI(BASE) *src)
+{
+	return dst;
+}
+
+/* Intersect the domain of "dst" with the domain product
+ * of the explicit domains of "src1" and "src2".
+ * This function is only called if at least one of "src1" or "src2"
+ * has an explicit domain.
+ * "src1", "src2" and "dst" cannot have an explicit domain,
+ * so this function is never called.
+ */
+static __isl_give MULTI(BASE) *
+FN(MULTI(BASE),intersect_explicit_domain_product)(
+	__isl_take MULTI(BASE) *dst, __isl_keep MULTI(BASE) *src1,
+	__isl_keep MULTI(BASE) *src2)
+{
+	return dst;
+}
+
+/* Align the parameters of the explicit domain of "multi" to those of "space".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),align_explicit_domain_params)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_space *space)
+{
+	isl_space_free(space);
+	return multi;
+}
+
+/* Replace the space of the explicit domain of "multi" by "space",
+ * without modifying its dimension.
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+static __isl_give MULTI(BASE) *FN(MULTI(BASE),reset_explicit_domain_space)(
+	__isl_take MULTI(BASE) *multi, __isl_take isl_space *space)
+{
+	isl_space_free(space);
+	return multi;
+}
+
+/* Check whether the explicit domain of "multi" has non-zero coefficients
+ * for any dimension in the given range or if any of these dimensions appear
+ * with non-zero coefficients in any of the integer divisions involved.
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+isl_bool FN(MULTI(BASE),involves_explicit_domain_dims)(
+	__isl_keep MULTI(BASE) *multi,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	return isl_bool_false;
+}
+
+/* Insert "n" dimensions of type "type" at position "pos"
+ * of the explicit domain of "multi".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+__isl_give MULTI(BASE) *FN(MULTI(BASE),insert_explicit_domain_dims)(
+	__isl_take MULTI(BASE) *multi,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	return multi;
+}
+
+/* Drop the "n" dimensions of type "type" starting at position "pos"
+ * of the explicit domain of "multi".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+__isl_give MULTI(BASE) *FN(MULTI(BASE),drop_explicit_domain_dims)(
+	__isl_take MULTI(BASE) *multi,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	return multi;
+}
+
+/* Move the "n" dimensions of "src_type" starting at "src_pos" of
+ * of the explicit domain of "multi" to dimensions of "dst_type" at "dst_pos".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+__isl_give MULTI(BASE) *FN(MULTI(BASE),move_explicit_domain_dims)(
+	__isl_take MULTI(BASE) *multi,
+	enum isl_dim_type dst_type, unsigned dst_pos,
+	enum isl_dim_type src_type, unsigned src_pos, unsigned n)
+{
+	return multi;
+}
+
+/* Free the explicit domain of "multi".
+ * "multi" cannot have an explicit domain, so this function is never called.
+ */
+static void FN(MULTI(BASE),free_explicit_domain)(__isl_keep MULTI(BASE) *multi)
+{
+}
+
+/* Do "multi1" and "multi2" have the same explicit domain?
+ * "multi1" and "multi2" cannot have an explicit domain,
+ * so this function is never called.
+ */
+static isl_bool FN(MULTI(BASE),equal_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi1, __isl_keep MULTI(BASE) *multi2)
+{
+	return isl_bool_true;
+}
+
+static isl_stat FN(MULTI(BASE),check_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi) __attribute__ ((unused));
+
+/* Debugging function to check that the explicit domain of "multi"
+ * has the correct space.
+ * "multi" cannot have an explicit domain,
+ * so this function should never be called.
+ */
+static isl_stat FN(MULTI(BASE),check_explicit_domain)(
+	__isl_keep MULTI(BASE) *multi)
+{
+	return isl_stat_ok;
+}

Added: polly/trunk/lib/External/isl/isl_multi_pw_aff_explicit_domain.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_pw_aff_explicit_domain.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_pw_aff_explicit_domain.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_pw_aff_explicit_domain.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,134 @@
+/*
+ * Copyright 2017      Sven Verdoolaege
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege.
+ */
+
+/* Initialize the explicit domain of "mpa".
+ *
+ * The explicit domain is initialized to a universe set
+ * in the domain space.
+ */
+static __isl_give isl_multi_pw_aff *isl_multi_pw_aff_init_explicit_domain(
+	__isl_take isl_multi_pw_aff *mpa)
+{
+	if (isl_multi_pw_aff_check_has_explicit_domain(mpa) < 0)
+		return isl_multi_pw_aff_free(mpa);
+	mpa->u.dom = isl_set_universe(isl_multi_pw_aff_get_domain_space(mpa));
+	if (!mpa->u.dom)
+		return isl_multi_pw_aff_free(mpa);
+	return mpa;
+}
+
+/* Intersect the domain of "dst" with the domain product
+ * of the explicit domains of "src1" and "src2".
+ * This function is only called if at least one of "src1" or "src2"
+ * has an explicit domain.
+ */
+static __isl_give isl_multi_pw_aff *
+isl_multi_pw_aff_intersect_explicit_domain_product(
+	__isl_take isl_multi_pw_aff *dst, __isl_keep isl_multi_pw_aff *src1,
+	__isl_keep isl_multi_pw_aff *src2)
+{
+	isl_space *space;
+	isl_set *dom;
+	isl_map *map;
+
+	if (!src1 || !src2)
+		return FN(isl_multi_pw_aff,free)(dst);
+	space = isl_multi_pw_aff_get_domain_space(dst);
+	dom = isl_set_universe(space);
+	map = isl_set_unwrap(dom);
+	if (isl_multi_pw_aff_has_explicit_domain(src1)) {
+		dom = isl_set_copy(src1->u.dom);
+		map = isl_map_intersect_domain(map, dom);
+	}
+	if (isl_multi_pw_aff_has_explicit_domain(src2)) {
+		dom = isl_set_copy(src2->u.dom);
+		map = isl_map_intersect_range(map, dom);
+	}
+	dom = isl_map_wrap(map);
+	dst = isl_multi_pw_aff_intersect_domain(dst, dom);
+	return dst;
+}
+
+/* Check whether the explicit domain of "mpa" has non-zero coefficients
+ * for any dimension in the given range or if any of these dimensions appear
+ * with non-zero coefficients in any of the integer divisions involved.
+ */
+isl_bool isl_multi_pw_aff_involves_explicit_domain_dims(
+	__isl_keep isl_multi_pw_aff *mpa,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	if (isl_multi_pw_aff_check_has_explicit_domain(mpa) < 0)
+		return isl_bool_error;
+	if (type == isl_dim_in)
+		type = isl_dim_set;
+	return isl_set_involves_dims(mpa->u.dom, type, pos, n);
+}
+
+/* Insert "n" dimensions of type "type" at position "pos"
+ * of the explicit domain of "mpa".
+ */
+static __isl_give isl_multi_pw_aff *
+isl_multi_pw_aff_insert_explicit_domain_dims(__isl_take isl_multi_pw_aff *mpa,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	if (isl_multi_pw_aff_check_has_explicit_domain(mpa) < 0)
+		return isl_multi_pw_aff_free(mpa);
+	mpa = isl_multi_pw_aff_cow(mpa);
+	if (!mpa)
+		return NULL;
+	if (type == isl_dim_in)
+		type = isl_dim_set;
+	mpa->u.dom = isl_set_insert_dims(mpa->u.dom, type, pos, n);
+	if (!mpa->u.dom)
+		return isl_multi_pw_aff_free(mpa);
+	return mpa;
+}
+
+/* Drop the "n" dimensions of type "type" starting at position "pos"
+ * of the explicit domain of "mpa".
+ */
+static __isl_give isl_multi_pw_aff *
+isl_multi_pw_aff_drop_explicit_domain_dims(__isl_take isl_multi_pw_aff *mpa,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	if (isl_multi_pw_aff_check_has_explicit_domain(mpa) < 0)
+		return isl_multi_pw_aff_free(mpa);
+	mpa = isl_multi_pw_aff_cow(mpa);
+	if (!mpa)
+		return NULL;
+	if (type == isl_dim_in)
+		type = isl_dim_set;
+	mpa->u.dom = isl_set_drop(mpa->u.dom, type, pos, n);
+	if (!mpa->u.dom)
+		return isl_multi_pw_aff_free(mpa);
+	return mpa;
+}
+
+/* Move the "n" dimensions of "src_type" starting at "src_pos" of
+ * of the explicit domain of "mpa" to dimensions of "dst_type" at "dst_pos".
+ */
+static __isl_give isl_multi_pw_aff *isl_multi_pw_aff_move_explicit_domain_dims(
+	__isl_take isl_multi_pw_aff *mpa,
+	enum isl_dim_type dst_type, unsigned dst_pos,
+	enum isl_dim_type src_type, unsigned src_pos, unsigned n)
+{
+	if (isl_multi_pw_aff_check_has_explicit_domain(mpa) < 0)
+		return isl_multi_pw_aff_free(mpa);
+	mpa = isl_multi_pw_aff_cow(mpa);
+	if (!mpa)
+		return NULL;
+	if (dst_type == isl_dim_in)
+		dst_type = isl_dim_set;
+	if (src_type == isl_dim_in)
+		src_type = isl_dim_set;
+	mpa->u.dom = isl_set_move_dims(mpa->u.dom, dst_type, dst_pos,
+				src_type, src_pos, n);
+	if (!mpa->u.dom)
+		return isl_multi_pw_aff_free(mpa);
+	return mpa;
+}

Modified: polly/trunk/lib/External/isl/isl_multi_templ.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_templ.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_templ.c (original)
+++ polly/trunk/lib/External/isl/isl_multi_templ.c Sat Apr 21 01:34:22 2018
@@ -8,7 +8,9 @@
  * Ecole Normale Superieure, 45 rue d’Ulm, 75230 Paris, France
  */
 
+#include <isl/id.h>
 #include <isl_space_private.h>
+#include <isl_val_private.h>
 #include <isl/set.h>
 #include <isl_reordering.h>
 
@@ -46,6 +48,12 @@ __isl_give isl_space *FN(MULTI(BASE),get
 	return multi ? isl_space_domain(isl_space_copy(multi->space)) : NULL;
 }
 
+/* Allocate a multi expression living in "space".
+ *
+ * If the number of base expressions is zero, then make sure
+ * there is enough room in the structure for the explicit domain,
+ * in case the type supports such an explicit domain.
+ */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),alloc)(__isl_take isl_space *space)
 {
 	isl_ctx *ctx;
@@ -57,14 +65,19 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),a
 
 	ctx = isl_space_get_ctx(space);
 	n = isl_space_dim(space, isl_dim_out);
-	multi = isl_calloc(ctx, MULTI(BASE),
+	if (n > 0)
+		multi = isl_calloc(ctx, MULTI(BASE),
 			 sizeof(MULTI(BASE)) + (n - 1) * sizeof(struct EL *));
+	else
+		multi = isl_calloc(ctx, MULTI(BASE), sizeof(MULTI(BASE)));
 	if (!multi)
 		goto error;
 
 	multi->space = space;
 	multi->n = n;
 	multi->ref = 1;
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		multi = FN(MULTI(BASE),init_explicit_domain)(multi);
 	return multi;
 error:
 	isl_space_free(space);
@@ -85,7 +98,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),d
 
 	for (i = 0; i < multi->n; ++i)
 		dup = FN(FN(MULTI(BASE),set),BASE)(dup, i,
-						    FN(EL,copy)(multi->p[i]));
+						    FN(EL,copy)(multi->u.p[i]));
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		dup = FN(MULTI(BASE),copy_explicit_domain)(dup, multi);
 
 	return dup;
 }
@@ -123,7 +138,9 @@ __isl_null MULTI(BASE) *FN(MULTI(BASE),f
 
 	isl_space_free(multi->space);
 	for (i = 0; i < multi->n; ++i)
-		FN(EL,free)(multi->p[i]);
+		FN(EL,free)(multi->u.p[i]);
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		FN(MULTI(BASE),free_explicit_domain)(multi);
 	free(multi);
 
 	return NULL;
@@ -171,8 +188,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),s
 	if (type == isl_dim_out)
 		return multi;
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,set_dim_name)(multi->p[i], type, pos, s);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,set_dim_name)(multi->u.p[i],
+							type, pos, s);
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 
@@ -214,7 +232,7 @@ __isl_give EL *FN(FN(MULTI(BASE),get),BA
 	if (pos < 0 || pos >= multi->n)
 		isl_die(ctx, isl_error_invalid,
 			"index out of bounds", return NULL);
-	return FN(EL,copy)(multi->p[pos]);
+	return FN(EL,copy)(multi->u.p[pos]);
 }
 
 __isl_give MULTI(BASE) *FN(FN(MULTI(BASE),set),BASE)(
@@ -246,8 +264,8 @@ __isl_give MULTI(BASE) *FN(FN(MULTI(BASE
 		isl_die(FN(MULTI(BASE),get_ctx)(multi), isl_error_invalid,
 			"index out of bounds", goto error);
 
-	FN(EL,free)(multi->p[pos]);
-	multi->p[pos] = el;
+	FN(EL,free)(multi->u.p[pos]);
+	multi->u.p[pos] = el;
 
 	isl_space_free(multi_space);
 	isl_space_free(el_space);
@@ -266,6 +284,10 @@ error:
  * directly or through its domain.  It therefore passes along both,
  * which we pass along to the element function since we don't know how
  * that is represented either.
+ *
+ * If "multi" has an explicit domain, then the caller is expected
+ * to make sure that any modification that would change the dimensions
+ * of the explicit domain has bee applied before this function is called.
  */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),reset_space_and_domain)(
 	__isl_take MULTI(BASE) *multi, __isl_take isl_space *space,
@@ -278,9 +300,15 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),r
 		goto error;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,reset_domain_space)(multi->p[i],
+		multi->u.p[i] = FN(EL,reset_domain_space)(multi->u.p[i],
 				 isl_space_copy(domain));
-		if (!multi->p[i])
+		if (!multi->u.p[i])
+			goto error;
+	}
+	if (FN(MULTI(BASE),has_explicit_domain)(multi)) {
+		multi = FN(MULTI(BASE),reset_explicit_domain_space)(multi,
+							isl_space_copy(domain));
+		if (!multi)
 			goto error;
 	}
 	isl_space_free(domain);
@@ -417,9 +445,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),r
 		goto error;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,realign_domain)(multi->p[i],
+		multi->u.p[i] = FN(EL,realign_domain)(multi->u.p[i],
 						isl_reordering_copy(exp));
-		if (!multi->p[i])
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -435,6 +463,9 @@ error:
 }
 
 /* Align the parameters of "multi" to those of "model".
+ *
+ * If "multi" has an explicit domain, then align the parameters
+ * of the domain first.
  */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),align_params)(
 	__isl_take MULTI(BASE) *multi, __isl_take isl_space *model)
@@ -462,6 +493,12 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),a
 		isl_die(ctx, isl_error_invalid,
 			"input has unnamed parameters", goto error);
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi)) {
+		multi = FN(MULTI(BASE),align_explicit_domain_params)(multi,
+							isl_space_copy(model));
+		if (!multi)
+			goto error;
+	}
 	model = isl_space_params(model);
 	exp = isl_parameter_alignment_reordering(multi->space, model);
 	exp = isl_reordering_extend_space(exp,
@@ -644,17 +681,25 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),d
 
 	if (type == isl_dim_out) {
 		for (i = 0; i < n; ++i)
-			FN(EL,free)(multi->p[first + i]);
+			FN(EL,free)(multi->u.p[first + i]);
 		for (i = first; i + n < multi->n; ++i)
-			multi->p[i] = multi->p[i + n];
+			multi->u.p[i] = multi->u.p[i + n];
 		multi->n -= n;
+		if (n > 0 && FN(MULTI(BASE),has_explicit_domain)(multi))
+			multi = FN(MULTI(BASE),init_explicit_domain)(multi);
 
 		return multi;
 	}
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		multi = FN(MULTI(BASE),drop_explicit_domain_dims)(multi,
+								type, first, n);
+	if (!multi)
+		return NULL;
+
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,drop_dims)(multi->p[i], type, first, n);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,drop_dims)(multi->u.p[i], type, first, n);
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 
@@ -698,6 +743,9 @@ error:
  * construct a MULTI(BASE) (A * C) -> [B -> D].
  *
  * The parameters are assumed to have been aligned.
+ *
+ * If "multi1" and/or "multi2" has an explicit domain, then
+ * intersect the domain of the result with these explicit domains.
  */
 static __isl_give MULTI(BASE) *FN(MULTI(BASE),range_product_aligned)(
 	__isl_take MULTI(BASE) *multi1, __isl_take MULTI(BASE) *multi2)
@@ -727,6 +775,11 @@ static __isl_give MULTI(BASE) *FN(MULTI(
 		res = FN(FN(MULTI(BASE),set),BASE)(res, n1 + i, el);
 	}
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi1))
+		res = FN(MULTI(BASE),intersect_explicit_domain)(res, multi1);
+	if (FN(MULTI(BASE),has_explicit_domain)(multi2))
+		res = FN(MULTI(BASE),intersect_explicit_domain)(res, multi2);
+
 	FN(MULTI(BASE),free)(multi1);
 	FN(MULTI(BASE),free)(multi2);
 	return res;
@@ -835,6 +888,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),f
  * construct a MULTI(BASE) [A -> C] -> [B -> D].
  *
  * The parameters are assumed to have been aligned.
+ *
+ * If "multi1" and/or "multi2" has an explicit domain, then
+ * intersect the domain of the result with these explicit domains.
  */
 __isl_give MULTI(BASE) *FN(MULTI(BASE),product_aligned)(
 	__isl_take MULTI(BASE) *multi1, __isl_take MULTI(BASE) *multi2)
@@ -868,6 +924,11 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),p
 		res = FN(FN(MULTI(BASE),set),BASE)(res, out1 + i, el);
 	}
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi1) ||
+	    FN(MULTI(BASE),has_explicit_domain)(multi2))
+		res = FN(MULTI(BASE),intersect_explicit_domain_product)(res,
+								multi1, multi2);
+
 	isl_space_free(space);
 	FN(MULTI(BASE),free)(multi1);
 	FN(MULTI(BASE),free)(multi2);
@@ -1013,6 +1074,27 @@ error:
 }
 #endif
 
+/* Check that "multi1" and "multi2" live in the same space,
+ * reporting an error if they do not.
+ */
+static isl_stat FN(MULTI(BASE),check_equal_space)(
+	__isl_keep MULTI(BASE) *multi1, __isl_keep MULTI(BASE) *multi2)
+{
+	isl_bool equal;
+
+	if (!multi1 || !multi2)
+		return isl_stat_error;
+
+	equal = isl_space_is_equal(multi1->space, multi2->space);
+	if (equal < 0)
+		return isl_stat_error;
+	if (!equal)
+		isl_die(FN(MULTI(BASE),get_ctx)(multi1), isl_error_invalid,
+			"spaces don't match", return isl_stat_error);
+
+	return isl_stat_ok;
+}
+
 /* This function is currently only used from isl_aff.c
  */
 static __isl_give MULTI(BASE) *FN(MULTI(BASE),bin_op)(
@@ -1022,29 +1104,31 @@ static __isl_give MULTI(BASE) *FN(MULTI(
 
 /* Pairwise perform "fn" to the elements of "multi1" and "multi2" and
  * return the result.
+ *
+ * If "multi2" has an explicit domain, then
+ * intersect the domain of the result with this explicit domain.
  */
 static __isl_give MULTI(BASE) *FN(MULTI(BASE),bin_op)(
 	__isl_take MULTI(BASE) *multi1, __isl_take MULTI(BASE) *multi2,
 	__isl_give EL *(*fn)(__isl_take EL *, __isl_take EL *))
 {
 	int i;
-	isl_ctx *ctx;
 
 	multi1 = FN(MULTI(BASE),cow)(multi1);
-	if (!multi1 || !multi2)
+	if (FN(MULTI(BASE),check_equal_space)(multi1, multi2) < 0)
 		goto error;
 
-	ctx = FN(MULTI(BASE),get_ctx)(multi1);
-	if (!isl_space_is_equal(multi1->space, multi2->space))
-		isl_die(ctx, isl_error_invalid,
-			"spaces don't match", goto error);
-
 	for (i = 0; i < multi1->n; ++i) {
-		multi1->p[i] = fn(multi1->p[i], FN(EL,copy)(multi2->p[i]));
-		if (!multi1->p[i])
+		multi1->u.p[i] = fn(multi1->u.p[i],
+						FN(EL,copy)(multi2->u.p[i]));
+		if (!multi1->u.p[i])
 			goto error;
 	}
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi2))
+		multi1 = FN(MULTI(BASE),intersect_explicit_domain)(multi1,
+								    multi2);
+
 	FN(MULTI(BASE),free)(multi2);
 	return multi1;
 error:
@@ -1115,8 +1199,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),s
 		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,scale_val)(multi->p[i], isl_val_copy(v));
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,scale_val)(multi->u.p[i],
+						isl_val_copy(v));
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -1154,9 +1239,9 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),s
 		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,scale_down_val)(multi->p[i],
+		multi->u.p[i] = FN(EL,scale_down_val)(multi->u.p[i],
 						    isl_val_copy(v));
-		if (!multi->p[i])
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -1191,8 +1276,8 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),s
 		isl_val *v;
 
 		v = isl_multi_val_get_val(mv, i);
-		multi->p[i] = FN(EL,scale_val)(multi->p[i], v);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,scale_val)(multi->u.p[i], v);
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -1227,8 +1312,8 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),s
 		isl_val *v;
 
 		v = isl_multi_val_get_val(mv, i);
-		multi->p[i] = FN(EL,scale_down_val)(multi->p[i], v);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,scale_down_val)(multi->u.p[i], v);
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -1263,8 +1348,8 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),m
 		isl_val *v;
 
 		v = isl_multi_val_get_val(mv, i);
-		multi->p[i] = FN(EL,mod_val)(multi->p[i], v);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,mod_val)(multi->u.p[i], v);
+		if (!multi->u.p[i])
 			goto error;
 	}
 
@@ -1320,11 +1405,17 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),m
 						src_type, src_pos, n);
 	if (!multi->space)
 		return FN(MULTI(BASE),free)(multi);
+	if (FN(MULTI(BASE),has_explicit_domain)(multi))
+		multi = FN(MULTI(BASE),move_explicit_domain_dims)(multi,
+				dst_type, dst_pos, src_type, src_pos, n);
+	if (!multi)
+		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,move_dims)(multi->p[i], dst_type, dst_pos,
+		multi->u.p[i] = FN(EL,move_dims)(multi->u.p[i],
+						dst_type, dst_pos,
 						src_type, src_pos, n);
-		if (!multi->p[i])
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 
@@ -1371,7 +1462,14 @@ isl_bool FN(MULTI(BASE),plain_is_equal)(
 		return equal;
 
 	for (i = 0; i < multi1->n; ++i) {
-		equal = FN(EL,plain_is_equal)(multi1->p[i], multi2->p[i]);
+		equal = FN(EL,plain_is_equal)(multi1->u.p[i], multi2->u.p[i]);
+		if (equal < 0 || !equal)
+			return equal;
+	}
+
+	if (FN(MULTI(BASE),has_explicit_domain)(multi1) ||
+	    FN(MULTI(BASE),has_explicit_domain)(multi2)) {
+		equal = FN(MULTI(BASE),equal_explicit_domain)(multi1, multi2);
 		if (equal < 0 || !equal)
 			return equal;
 	}
@@ -1391,7 +1489,7 @@ isl_bool FN(MULTI(BASE),involves_nan)(__
 		return isl_bool_false;
 
 	for (i = 0; i < multi->n; ++i) {
-		isl_bool has_nan = FN(EL,involves_nan)(multi->p[i]);
+		isl_bool has_nan = FN(EL,involves_nan)(multi->u.p[i]);
 		if (has_nan < 0 || has_nan)
 			return has_nan;
 	}
@@ -1401,6 +1499,8 @@ isl_bool FN(MULTI(BASE),involves_nan)(__
 
 #ifndef NO_DOMAIN
 /* Return the shared domain of the elements of "multi".
+ *
+ * If "multi" has an explicit domain, then return this domain.
  */
 __isl_give isl_set *FN(MULTI(BASE),domain)(__isl_take MULTI(BASE) *multi)
 {
@@ -1410,6 +1510,12 @@ __isl_give isl_set *FN(MULTI(BASE),domai
 	if (!multi)
 		return NULL;
 
+	if (FN(MULTI(BASE),has_explicit_domain)(multi)) {
+		dom = FN(MULTI(BASE),get_explicit_domain)(multi);
+		FN(MULTI(BASE),free)(multi);
+		return dom;
+	}
+
 	dom = isl_set_universe(FN(MULTI(BASE),get_domain_space)(multi));
 	for (i = 0; i < multi->n; ++i) {
 		isl_set *dom_i;
@@ -1435,8 +1541,8 @@ __isl_give MULTI(BASE) *FN(MULTI(BASE),n
 		return NULL;
 
 	for (i = 0; i < multi->n; ++i) {
-		multi->p[i] = FN(EL,neg)(multi->p[i]);
-		if (!multi->p[i])
+		multi->u.p[i] = FN(EL,neg)(multi->u.p[i]);
+		if (!multi->u.p[i])
 			return FN(MULTI(BASE),free)(multi);
 	}
 

Modified: polly/trunk/lib/External/isl/isl_multi_templ.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_templ.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_templ.h (original)
+++ polly/trunk/lib/External/isl/isl_multi_templ.h Sat Apr 21 01:34:22 2018
@@ -2,12 +2,32 @@
 
 #include <isl_multi_macro.h>
 
+/* A multiple expression with base expressions of type EL.
+ *
+ * "space" is the space in which the multiple expression lives.
+ * "n" is the number of base expression and is equal
+ * to the output or set dimension of "space".
+ * "p" is an array of size "n" of base expressions.
+ * The array is only accessible when n > 0.
+ * "dom" is the explicit domain, if present
+ * The explicit domain is only accessible when n == 0.
+ */
 struct MULTI(BASE) {
 	int ref;
 	isl_space *space;
 
 	int n;
-	EL *p[1];
+	struct {
+#ifdef EXPLICIT_DOMAIN
+		DOM *dom;
+#endif
+		EL *p[1];
+	} u;
 };
 
 __isl_give MULTI(BASE) *CAT(MULTI(BASE),_alloc)(__isl_take isl_space *space);
+
+#ifdef EXPLICIT_DOMAIN
+isl_bool CAT(MULTI(BASE),_has_non_trivial_domain)(
+	__isl_keep MULTI(BASE) *multi);
+#endif

Added: polly/trunk/lib/External/isl/isl_multi_union_pw_aff_explicit_domain.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_multi_union_pw_aff_explicit_domain.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_multi_union_pw_aff_explicit_domain.c (added)
+++ polly/trunk/lib/External/isl/isl_multi_union_pw_aff_explicit_domain.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,51 @@
+/*
+ * Copyright 2017      Sven Verdoolaege
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege.
+ */
+
+/* Initialize the explicit domain of "mupa".
+ *
+ * The explicit domain is initialized to a universe parameter set.
+ * It may later be specialized with constraints on the parameter or
+ * specific domain instances.
+ */
+static __isl_give isl_multi_union_pw_aff *
+isl_multi_union_pw_aff_init_explicit_domain(
+	__isl_take isl_multi_union_pw_aff *mupa)
+{
+	isl_space *space;
+
+	if (isl_multi_union_pw_aff_check_has_explicit_domain(mupa) < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+	space = isl_space_params(isl_multi_union_pw_aff_get_space(mupa));
+	mupa->u.dom = isl_union_set_from_set(isl_set_universe(space));
+	if (!mupa->u.dom)
+		return isl_multi_union_pw_aff_free(mupa);
+	return mupa;
+}
+
+/* Drop the "n" dimensions of type "type" starting at position "pos"
+ * of the explicit domain of "mupa".
+ */
+static __isl_give isl_multi_union_pw_aff *
+isl_multi_union_pw_aff_drop_explicit_domain_dims(
+	__isl_take isl_multi_union_pw_aff *mupa,
+	enum isl_dim_type type, unsigned pos, unsigned n)
+{
+	if (isl_multi_union_pw_aff_check_has_explicit_domain(mupa) < 0)
+		return isl_multi_union_pw_aff_free(mupa);
+	if (type != isl_dim_param)
+		isl_die(isl_multi_union_pw_aff_get_ctx(mupa), isl_error_invalid,
+			"can only drop parameters",
+			return isl_multi_union_pw_aff_free(mupa));
+	mupa = isl_multi_union_pw_aff_cow(mupa);
+	if (!mupa)
+		return NULL;
+	mupa->u.dom = isl_union_set_project_out(mupa->u.dom, type, pos, n);
+	if (!mupa->u.dom)
+		return isl_multi_union_pw_aff_free(mupa);
+	return mupa;
+}

Modified: polly/trunk/lib/External/isl/isl_output.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_output.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_output.c (original)
+++ polly/trunk/lib/External/isl/isl_output.c Sat Apr 21 01:34:22 2018
@@ -23,6 +23,7 @@
 #include <isl_space_private.h>
 #include <isl_mat_private.h>
 #include <isl_vec_private.h>
+#include <isl/union_set.h>
 #include <isl/union_map.h>
 #include <isl/constraint.h>
 #include <isl_local_space_private.h>
@@ -1175,6 +1176,16 @@ static __isl_give isl_printer *print_dis
 		return print_disjuncts(map, space, p, latex);
 }
 
+/* Print the disjuncts of a set.
+ * The names of the variables are taken from "space".
+ * "latex" is set if the constraints should be printed in LaTeX format.
+ */
+static __isl_give isl_printer *print_disjuncts_set(__isl_keep isl_set *set,
+	__isl_keep isl_space *space, __isl_take isl_printer *p, int latex)
+{
+	return print_disjuncts_map(set_to_map(set), space, p, latex);
+}
+
 struct isl_aff_split {
 	isl_basic_map *aff;
 	isl_map *map;
@@ -1567,16 +1578,14 @@ static isl_stat print_map_body(__isl_tak
 	return isl_stat_ok;
 }
 
-static __isl_give isl_printer *isl_union_map_print_isl(
-	__isl_keep isl_union_map *umap, __isl_take isl_printer *p)
+/* Print the body of "umap" (everything except the parameter declarations)
+ * to "p" in isl format.
+ */
+static __isl_give isl_printer *isl_printer_print_union_map_isl_body(
+	__isl_take isl_printer *p, __isl_keep isl_union_map *umap)
 {
 	struct isl_union_print_data data;
-	struct isl_print_space_data space_data = { 0 };
-	isl_space *space;
 
-	space = isl_union_map_get_space(umap);
-	p = print_param_tuple(p, space, &space_data);
-	isl_space_free(space);
 	p = isl_printer_print_str(p, s_open_set[0]);
 	data.p = p;
 	data.first = 1;
@@ -1586,6 +1595,32 @@ static __isl_give isl_printer *isl_union
 	return p;
 }
 
+/* Print the body of "uset" (everything except the parameter declarations)
+ * to "p" in isl format.
+ */
+static __isl_give isl_printer *isl_printer_print_union_set_isl_body(
+	__isl_take isl_printer *p, __isl_keep isl_union_set *uset)
+{
+	return isl_printer_print_union_map_isl_body(p, uset_to_umap(uset));
+}
+
+/* Print the isl_union_map "umap" to "p" in isl format.
+ */
+static __isl_give isl_printer *isl_union_map_print_isl(
+	__isl_keep isl_union_map *umap, __isl_take isl_printer *p)
+{
+	struct isl_print_space_data space_data = { 0 };
+	isl_space *space;
+
+	space = isl_union_map_get_space(umap);
+	p = print_param_tuple(p, space, &space_data);
+	isl_space_free(space);
+
+	p = isl_printer_print_union_map_isl_body(p, umap);
+
+	return p;
+}
+
 static isl_stat print_latex_map_body(__isl_take isl_map *map, void *user)
 {
 	struct isl_union_print_data *data;
@@ -2897,7 +2932,7 @@ static __isl_give isl_printer *print_dim
 	isl_multi_aff *ma = data->user;
 
 	if (data->type == isl_dim_out)
-		p = print_aff_body(p, ma->p[pos]);
+		p = print_aff_body(p, ma->u.p[pos]);
 	else
 		p = print_name(data->space, p, data->type, pos, data->latex);
 
@@ -3003,12 +3038,12 @@ static __isl_give isl_printer *print_unn
 		p = isl_printer_print_str(p, "(");
 		p = print_set_c(p, space, pma->p[i].set);
 		p = isl_printer_print_str(p, ") ? (");
-		p = print_aff_c(p, pma->p[i].maff->p[0]);
+		p = print_aff_c(p, pma->p[i].maff->u.p[0]);
 		p = isl_printer_print_str(p, ") : ");
 	}
 	isl_space_free(space);
 
-	return print_aff_c(p, pma->p[pma->n - 1].maff->p[0]);
+	return print_aff_c(p, pma->p[pma->n - 1].maff->u.p[0]);
 }
 
 static __isl_give isl_printer *print_pw_multi_aff_c(__isl_take isl_printer *p,
@@ -3130,7 +3165,7 @@ static __isl_give isl_printer *print_dim
 	if (data->type != isl_dim_out)
 		return print_name(data->space, p, data->type, pos, data->latex);
 
-	pa = mpa->p[pos];
+	pa = mpa->u.p[pos];
 	if (pa->n == 0)
 		return isl_printer_print_str(p, "(0 : false)");
 
@@ -3154,11 +3189,15 @@ static __isl_give isl_printer *print_dim
 }
 
 /* Print "mpa" to "p" in isl format.
+ *
+ * If "mpa" is zero-dimensional and has a non-trivial explicit domain,
+ * then it is printed after the tuple of affine expressions.
  */
 static __isl_give isl_printer *print_multi_pw_aff_isl(__isl_take isl_printer *p,
 	__isl_keep isl_multi_pw_aff *mpa)
 {
 	struct isl_print_space_data data = { 0 };
+	isl_bool has_domain;
 
 	if (!mpa)
 		return isl_printer_free(p);
@@ -3168,6 +3207,16 @@ static __isl_give isl_printer *print_mul
 	data.print_dim = &print_dim_mpa;
 	data.user = mpa;
 	p = isl_print_space(mpa->space, p, 0, &data);
+	has_domain = isl_multi_pw_aff_has_non_trivial_domain(mpa);
+	if (has_domain < 0)
+		return isl_printer_free(p);
+	if (has_domain) {
+		isl_space *space;
+
+		space = isl_space_domain(isl_space_copy(mpa->space));
+		p = print_disjuncts_set(mpa->u.dom, space, p, 0);
+		isl_space_free(space);
+	}
 	p = isl_printer_print_str(p, " }");
 	return p;
 }
@@ -3197,7 +3246,7 @@ static __isl_give isl_printer *print_dim
 	isl_multi_val *mv = data->user;
 
 	if (data->type == isl_dim_out)
-		return isl_printer_print_val(p, mv->p[pos]);
+		return isl_printer_print_val(p, mv->u.p[pos]);
 	else
 		return print_name(data->space, p, data->type, pos, data->latex);
 }
@@ -3259,22 +3308,45 @@ static __isl_give isl_printer *print_uni
 }
 
 /* Print the isl_multi_union_pw_aff "mupa" to "p" in isl format.
+ *
+ * If "mupa" is zero-dimensional and has a non-trivial explicit domain,
+ * then it is printed after the tuple of affine expressions.
+ * In order to clarify that this domain belongs to the expression,
+ * the tuple along with the domain are placed inside parentheses.
+ * If "mupa" has any parameters, then the opening parenthesis
+ * appears after the parameter declarations.
  */
 static __isl_give isl_printer *print_multi_union_pw_aff_isl(
 	__isl_take isl_printer *p, __isl_keep isl_multi_union_pw_aff *mupa)
 {
 	struct isl_print_space_data data = { 0 };
+	isl_bool has_domain;
 	isl_space *space;
 
+	if (!mupa)
+		return isl_printer_free(p);
+	has_domain = isl_multi_union_pw_aff_has_non_trivial_domain(mupa);
+	if (has_domain < 0)
+		return isl_printer_free(p);
+
 	space = isl_multi_union_pw_aff_get_space(mupa);
 	p = print_param_tuple(p, space, &data);
 
+	if (has_domain)
+		p = isl_printer_print_str(p, "(");
+
 	data.print_dim = &print_union_pw_aff_dim;
 	data.user = mupa;
 
 	p = isl_print_space(space, p, 0, &data);
 	isl_space_free(space);
 
+	if (has_domain) {
+		p = isl_printer_print_str(p, " : ");
+		p = isl_printer_print_union_set_isl_body(p, mupa->u.dom);
+		p = isl_printer_print_str(p, ")");
+	}
+
 	return p;
 }
 

Modified: polly/trunk/lib/External/isl/isl_point.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_point.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_point.c (original)
+++ polly/trunk/lib/External/isl/isl_point.c Sat Apr 21 01:34:22 2018
@@ -17,9 +17,16 @@ isl_ctx *isl_point_get_ctx(__isl_keep is
 	return pnt ? isl_space_get_ctx(pnt->dim) : NULL;
 }
 
+/* Return the space of "pnt".
+ */
+__isl_keep isl_space *isl_point_peek_space(__isl_keep isl_point *pnt)
+{
+	return pnt ? pnt->dim : NULL;
+}
+
 __isl_give isl_space *isl_point_get_space(__isl_keep isl_point *pnt)
 {
-	return pnt ? isl_space_copy(pnt->dim) : NULL;
+	return isl_space_copy(isl_point_peek_space(pnt));
 }
 
 __isl_give isl_point *isl_point_alloc(__isl_take isl_space *dim,
@@ -132,6 +139,123 @@ isl_bool isl_point_is_void(__isl_keep is
 	return pnt->vec->size == 0;
 }
 
+/* Return the space of "pnt".
+ * This may be either a copy or the space itself
+ * if there is only one reference to "pnt".
+ * This allows the space to be modified inplace
+ * if both the point and its space have only a single reference.
+ * The caller is not allowed to modify "pnt" between this call and
+ * a subsequent call to isl_point_restore_space.
+ * The only exception is that isl_point_free can be called instead.
+ */
+__isl_give isl_space *isl_point_take_space(__isl_keep isl_point *pnt)
+{
+	isl_space *space;
+
+	if (!pnt)
+		return NULL;
+	if (pnt->ref != 1)
+		return isl_point_get_space(pnt);
+	space = pnt->dim;
+	pnt->dim = NULL;
+	return space;
+}
+
+/* Set the space of "pnt" to "space", where the space of "pnt" may be missing
+ * due to a preceding call to isl_point_take_space.
+ * However, in this case, "pnt" only has a single reference and
+ * then the call to isl_point_cow has no effect.
+ */
+__isl_give isl_point *isl_point_restore_space(__isl_take isl_point *pnt,
+	__isl_take isl_space *space)
+{
+	if (!pnt || !space)
+		goto error;
+
+	if (pnt->dim == space) {
+		isl_space_free(space);
+		return pnt;
+	}
+
+	pnt = isl_point_cow(pnt);
+	if (!pnt)
+		goto error;
+	isl_space_free(pnt->dim);
+	pnt->dim = space;
+
+	return pnt;
+error:
+	isl_point_free(pnt);
+	isl_space_free(space);
+	return NULL;
+}
+
+/* Return the coordinate vector of "pnt".
+ */
+__isl_keep isl_vec *isl_point_peek_vec(__isl_keep isl_point *pnt)
+{
+	return pnt ? pnt->vec : NULL;
+}
+
+/* Return a copy of the coordinate vector of "pnt".
+ */
+__isl_give isl_vec *isl_point_get_vec(__isl_keep isl_point *pnt)
+{
+	return isl_vec_copy(isl_point_peek_vec(pnt));
+}
+
+/* Return the coordinate vector of "pnt".
+ * This may be either a copy or the coordinate vector itself
+ * if there is only one reference to "pnt".
+ * This allows the coordinate vector to be modified inplace
+ * if both the point and its coordinate vector have only a single reference.
+ * The caller is not allowed to modify "pnt" between this call and
+ * a subsequent call to isl_point_restore_vec.
+ * The only exception is that isl_point_free can be called instead.
+ */
+__isl_give isl_vec *isl_point_take_vec(__isl_keep isl_point *pnt)
+{
+	isl_vec *vec;
+
+	if (!pnt)
+		return NULL;
+	if (pnt->ref != 1)
+		return isl_point_get_vec(pnt);
+	vec = pnt->vec;
+	pnt->vec = NULL;
+	return vec;
+}
+
+/* Set the coordinate vector of "pnt" to "vec",
+ * where the coordinate vector of "pnt" may be missing
+ * due to a preceding call to isl_point_take_vec.
+ * However, in this case, "pnt" only has a single reference and
+ * then the call to isl_point_cow has no effect.
+ */
+__isl_give isl_point *isl_point_restore_vec(__isl_take isl_point *pnt,
+	__isl_take isl_vec *vec)
+{
+	if (!pnt || !vec)
+		goto error;
+
+	if (pnt->vec == vec) {
+		isl_vec_free(vec);
+		return pnt;
+	}
+
+	pnt = isl_point_cow(pnt);
+	if (!pnt)
+		goto error;
+	isl_vec_free(pnt->vec);
+	pnt->vec = vec;
+
+	return pnt;
+error:
+	isl_point_free(pnt);
+	isl_vec_free(vec);
+	return NULL;
+}
+
 /* Return the value of coordinate "pos" of type "type" of "pnt".
  */
 __isl_give isl_val *isl_point_get_coordinate_val(__isl_keep isl_point *pnt,

Modified: polly/trunk/lib/External/isl/isl_point_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_point_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_point_private.h (original)
+++ polly/trunk/lib/External/isl/isl_point_private.h Sat Apr 21 01:34:22 2018
@@ -1,3 +1,6 @@
+#ifndef ISL_POINT_PRIVATE_H
+#define ISL_POINT_PRIVATE_H
+
 #include <isl/space.h>
 #include <isl/point.h>
 #include <isl/vec.h>
@@ -10,3 +13,15 @@ struct isl_point {
 
 __isl_give isl_point *isl_point_alloc(__isl_take isl_space *dim,
 	__isl_take isl_vec *vec);
+
+__isl_keep isl_space *isl_point_peek_space(__isl_keep isl_point *pnt);
+__isl_give isl_space *isl_point_take_space(__isl_keep isl_point *pnt);
+__isl_give isl_point *isl_point_restore_space(__isl_take isl_point *pnt,
+	__isl_take isl_space *space);
+__isl_keep isl_vec *isl_point_peek_vec(__isl_keep isl_point *pnt);
+__isl_give isl_vec *isl_point_get_vec(__isl_keep isl_point *pnt);
+__isl_give isl_vec *isl_point_take_vec(__isl_keep isl_point *pnt);
+__isl_give isl_point *isl_point_restore_vec(__isl_take isl_point *pnt,
+	__isl_take isl_vec *vec);
+
+#endif

Modified: polly/trunk/lib/External/isl/isl_polynomial.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_polynomial.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_polynomial.c (original)
+++ polly/trunk/lib/External/isl/isl_polynomial.c Sat Apr 21 01:34:22 2018
@@ -9,7 +9,6 @@
  */
 
 #include <stdlib.h>
-#define ISL_DIM_H
 #include <isl_ctx_private.h>
 #include <isl_map_private.h>
 #include <isl_factorization.h>
@@ -2957,6 +2956,7 @@ __isl_give isl_pw_qpolynomial *isl_pw_qp
 #define NO_PULLBACK
 
 #include <isl_pw_templ.c>
+#include <isl_pw_eval.c>
 
 #undef UNION
 #define UNION isl_union_pw_qpolynomial
@@ -3071,7 +3071,7 @@ __isl_give isl_val *isl_upoly_eval(__isl
 	}
 
 	rec = isl_upoly_as_rec(up);
-	if (!rec)
+	if (!rec || !vec)
 		goto error;
 
 	isl_assert(up->ctx, rec->n >= 1, goto error);
@@ -3129,23 +3129,7 @@ __isl_give isl_val *isl_qpolynomial_eval
 	if (is_void)
 		return eval_void(qp, pnt);
 
-	if (qp->div->n_row == 0)
-		ext = isl_vec_copy(pnt->vec);
-	else {
-		int i;
-		unsigned dim = isl_space_dim(qp->dim, isl_dim_all);
-		ext = isl_vec_alloc(qp->dim->ctx, 1 + dim + qp->div->n_row);
-		if (!ext)
-			goto error;
-
-		isl_seq_cpy(ext->el, pnt->vec->el, pnt->vec->size);
-		for (i = 0; i < qp->div->n_row; ++i) {
-			isl_seq_inner_product(qp->div->row[i] + 1, ext->el,
-						1 + dim + i, &ext->el[1+dim+i]);
-			isl_int_fdiv_q(ext->el[1+dim+i], ext->el[1+dim+i],
-					qp->div->row[i][0]);
-		}
-	}
+	ext = isl_local_extend_point_vec(qp->div, isl_vec_copy(pnt->vec));
 
 	v = isl_upoly_eval(isl_upoly_copy(qp->upoly), ext);
 

Modified: polly/trunk/lib/External/isl/isl_polynomial_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_polynomial_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_polynomial_private.h (original)
+++ polly/trunk/lib/External/isl/isl_polynomial_private.h Sat Apr 21 01:34:22 2018
@@ -65,6 +65,11 @@ struct isl_pw_qpolynomial {
 	struct isl_pw_qpolynomial_piece p[1];
 };
 
+#undef PW
+#define PW isl_pw_qpolynomial
+
+#include <isl_pw_templ.h>
+
 /* dim represents the domain space.
  */
 struct isl_qpolynomial_fold {
@@ -96,6 +101,11 @@ struct isl_pw_qpolynomial_fold {
 	struct isl_pw_qpolynomial_fold_piece p[1];
 };
 
+#undef PW
+#define PW isl_pw_qpolynomial_fold
+
+#include <isl_pw_templ.h>
+
 void isl_term_get_num(__isl_keep isl_term *term, isl_int *n);
 
 __isl_give struct isl_upoly *isl_upoly_zero(struct isl_ctx *ctx);

Modified: polly/trunk/lib/External/isl/isl_printer.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_printer.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_printer.c (original)
+++ polly/trunk/lib/External/isl/isl_printer.c Sat Apr 21 01:34:22 2018
@@ -1,5 +1,7 @@
 #include <string.h>
 #include <isl_int.h>
+#include <isl/id.h>
+#include <isl/id_to_id.h>
 #include <isl_printer_private.h>
 
 static __isl_give isl_printer *file_start_line(__isl_take isl_printer *p)

Added: polly/trunk/lib/External/isl/isl_pw_eval.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_pw_eval.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_pw_eval.c (added)
+++ polly/trunk/lib/External/isl/isl_pw_eval.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,86 @@
+/*
+ * Copyright 2010      INRIA Saclay
+ * Copyright 2013      Ecole Normale Superieure
+ *
+ * Use of this software is governed by the MIT license
+ *
+ * Written by Sven Verdoolaege, INRIA Saclay - Ile-de-France,
+ * Parc Club Orsay Universite, ZAC des vignes, 4 rue Jacques Monod,
+ * 91893 Orsay, France
+ * and Ecole Normale Superieure, 45 rue d'Ulm, 75230 Paris, France
+ */
+
+#include <isl/val.h>
+#include <isl_space_private.h>
+#include <isl_point_private.h>
+
+#include <isl_pw_macro.h>
+
+/* Evaluate "pw" in the void point "pnt".
+ * In particular, return the value NaN.
+ */
+static __isl_give isl_val *FN(PW,eval_void)(__isl_take PW *pw,
+	__isl_take isl_point *pnt)
+{
+	isl_ctx *ctx;
+
+	ctx = isl_point_get_ctx(pnt);
+	FN(PW,free)(pw);
+	isl_point_free(pnt);
+	return isl_val_nan(ctx);
+}
+
+/* Evaluate the piecewise function "pw" in "pnt".
+ * If the point is void, then return NaN.
+ * If the point lies outside the domain of "pw", then return 0 or NaN
+ * depending on whether 0 is the default value for this type of function.
+ */
+__isl_give isl_val *FN(PW,eval)(__isl_take PW *pw, __isl_take isl_point *pnt)
+{
+	int i;
+	isl_bool is_void;
+	isl_bool found;
+	isl_ctx *ctx;
+	isl_bool ok;
+	isl_space *pnt_space, *pw_space;
+	isl_val *v;
+
+	pnt_space = isl_point_peek_space(pnt);
+	pw_space = FN(PW,peek_space)(pw);
+	ok = isl_space_is_domain_internal(pnt_space, pw_space);
+	if (ok < 0)
+		goto error;
+	ctx = isl_point_get_ctx(pnt);
+	if (!ok)
+		isl_die(ctx, isl_error_invalid,
+			"incompatible spaces", goto error);
+	is_void = isl_point_is_void(pnt);
+	if (is_void < 0)
+		goto error;
+	if (is_void)
+		return FN(PW,eval_void)(pw, pnt);
+
+	found = isl_bool_false;
+	for (i = 0; i < pw->n; ++i) {
+		found = isl_set_contains_point(pw->p[i].set, pnt);
+		if (found < 0)
+			goto error;
+		if (found)
+			break;
+	}
+	if (found) {
+		v = FN(EL,eval)(FN(EL,copy)(pw->p[i].FIELD),
+					    isl_point_copy(pnt));
+	} else if (DEFAULT_IS_ZERO) {
+		v = isl_val_zero(ctx);
+	} else {
+		v = isl_val_nan(ctx);
+	}
+	FN(PW,free)(pw);
+	isl_point_free(pnt);
+	return v;
+error:
+	FN(PW,free)(pw);
+	isl_point_free(pnt);
+	return NULL;
+}

Modified: polly/trunk/lib/External/isl/isl_pw_templ.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_pw_templ.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_pw_templ.c (original)
+++ polly/trunk/lib/External/isl/isl_pw_templ.c Sat Apr 21 01:34:22 2018
@@ -11,6 +11,7 @@
  * and Ecole Normale Superieure, 45 rue d’Ulm, 75230 Paris, France
  */
 
+#include <isl/id.h>
 #include <isl/aff.h>
 #include <isl_sort.h>
 #include <isl_val_private.h>
@@ -699,46 +700,6 @@ __isl_give PW *FN(PW,sub)(__isl_take PW
 }
 #endif
 
-#ifndef NO_EVAL
-__isl_give isl_val *FN(PW,eval)(__isl_take PW *pw, __isl_take isl_point *pnt)
-{
-	int i;
-	int found = 0;
-	isl_ctx *ctx;
-	isl_space *pnt_dim = NULL;
-	isl_val *v;
-
-	if (!pw || !pnt)
-		goto error;
-	ctx = isl_point_get_ctx(pnt);
-	pnt_dim = isl_point_get_space(pnt);
-	isl_assert(ctx, isl_space_is_domain_internal(pnt_dim, pw->dim),
-		    goto error);
-
-	for (i = 0; i < pw->n; ++i) {
-		found = isl_set_contains_point(pw->p[i].set, pnt);
-		if (found < 0)
-			goto error;
-		if (found)
-			break;
-	}
-	if (found)
-		v = FN(EL,eval)(FN(EL,copy)(pw->p[i].FIELD),
-					    isl_point_copy(pnt));
-	else
-		v = isl_val_zero(ctx);
-	FN(PW,free)(pw);
-	isl_space_free(pnt_dim);
-	isl_point_free(pnt);
-	return v;
-error:
-	FN(PW,free)(pw);
-	isl_space_free(pnt_dim);
-	isl_point_free(pnt);
-	return NULL;
-}
-#endif
-
 /* Return the parameter domain of "pw".
  */
 __isl_give isl_set *FN(PW,params)(__isl_take PW *pw)

Added: polly/trunk/lib/External/isl/isl_pw_templ.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_pw_templ.h?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/isl_pw_templ.h (added)
+++ polly/trunk/lib/External/isl/isl_pw_templ.h Sat Apr 21 01:34:22 2018
@@ -0,0 +1,5 @@
+#include <isl/space.h>
+
+#include <isl_pw_macro.h>
+
+__isl_keep isl_space *FN(PW,peek_space)(__isl_keep PW *pw);

Modified: polly/trunk/lib/External/isl/isl_reordering.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_reordering.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_reordering.c (original)
+++ polly/trunk/lib/External/isl/isl_reordering.c Sat Apr 21 01:34:22 2018
@@ -9,6 +9,7 @@
  */
 
 #include <isl_ctx_private.h>
+#include <isl/id.h>
 #include <isl_space_private.h>
 #include <isl_reordering.h>
 

Modified: polly/trunk/lib/External/isl/isl_schedule.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_schedule.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_schedule.c (original)
+++ polly/trunk/lib/External/isl/isl_schedule.c Sat Apr 21 01:34:22 2018
@@ -589,7 +589,7 @@ static __isl_give isl_schedule_tree *ins
  * with two filters corresponding to the domains of the input schedules.
  * If one (or both) of the top-level nodes of the two schedules is itself
  * of type "type", then the filter is pushed into the children of that
- * node and the sequence of set is flattened.
+ * node and the sequence or set is flattened.
  */
 __isl_give isl_schedule *isl_schedule_pair(enum isl_schedule_node_type type,
 	__isl_take isl_schedule *schedule1, __isl_take isl_schedule *schedule2)

Modified: polly/trunk/lib/External/isl/isl_schedule_node.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_schedule_node.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_schedule_node.c (original)
+++ polly/trunk/lib/External/isl/isl_schedule_node.c Sat Apr 21 01:34:22 2018
@@ -11,6 +11,7 @@
  * B.P. 105 - 78153 Le Chesnay, France
  */
 
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl/space.h>
 #include <isl/set.h>

Modified: polly/trunk/lib/External/isl/isl_schedule_read.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_schedule_read.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_schedule_read.c (original)
+++ polly/trunk/lib/External/isl/isl_schedule_read.c Sat Apr 21 01:34:22 2018
@@ -1,3 +1,4 @@
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl/schedule.h>
 #include <isl/stream.h>

Modified: polly/trunk/lib/External/isl/isl_schedule_tree.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_schedule_tree.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_schedule_tree.c (original)
+++ polly/trunk/lib/External/isl/isl_schedule_tree.c Sat Apr 21 01:34:22 2018
@@ -13,6 +13,7 @@
  * CS 42112, 75589 Paris Cedex 12, France
  */
 
+#include <isl/id.h>
 #include <isl/val.h>
 #include <isl/space.h>
 #include <isl/map.h>

Modified: polly/trunk/lib/External/isl/isl_scheduler.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_scheduler.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_scheduler.c (original)
+++ polly/trunk/lib/External/isl/isl_scheduler.c Sat Apr 21 01:34:22 2018
@@ -20,6 +20,7 @@
 #include <isl_space_private.h>
 #include <isl_aff_private.h>
 #include <isl/hash.h>
+#include <isl/id.h>
 #include <isl/constraint.h>
 #include <isl/schedule.h>
 #include <isl_schedule_constraints.h>

Modified: polly/trunk/lib/External/isl/isl_space.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_space.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_space.c (original)
+++ polly/trunk/lib/External/isl/isl_space.c Sat Apr 21 01:34:22 2018
@@ -1914,6 +1914,24 @@ isl_bool isl_space_is_equal(__isl_keep i
 	return isl_space_has_equal_tuples(space1, space2);
 }
 
+/* Do the tuples of "space1" correspond to those of the domain of "space2"?
+ * That is, is "space1" eqaul to the domain of "space2", ignoring parameters.
+ *
+ * "space2" is allowed to be a set space, in which case "space1"
+ * should be a parameter space.
+ */
+isl_bool isl_space_has_domain_tuples(__isl_keep isl_space *space1,
+	__isl_keep isl_space *space2)
+{
+	isl_bool is_set;
+
+	is_set = isl_space_is_set(space1);
+	if (is_set < 0 || !is_set)
+		return is_set;
+	return isl_space_tuple_is_equal(space1, isl_dim_set,
+					space2, isl_dim_in);
+}
+
 /* Is space1 equal to the domain of space2?
  *
  * In the internal version we also allow space2 to be the space of a set,
@@ -1926,13 +1944,10 @@ isl_bool isl_space_is_domain_internal(__
 
 	if (!space1 || !space2)
 		return isl_bool_error;
-	if (!isl_space_is_set(space1))
-		return isl_bool_false;
 	equal_params = isl_space_has_equal_params(space1, space2);
 	if (equal_params < 0 || !equal_params)
 		return equal_params;
-	return isl_space_tuple_is_equal(space1, isl_dim_set,
-					space2, isl_dim_in);
+	return isl_space_has_domain_tuples(space1, space2);
 }
 
 /* Is space1 equal to the domain of space2?
@@ -2286,8 +2301,15 @@ __isl_give isl_space *isl_space_flatten_
 __isl_give isl_space *isl_space_replace_params(__isl_take isl_space *dst,
 	__isl_keep isl_space *src)
 {
+	isl_bool equal_params;
 	enum isl_dim_type type = isl_dim_param;
 
+	equal_params = isl_space_has_equal_params(dst, src);
+	if (equal_params < 0)
+		return isl_space_free(dst);
+	if (equal_params)
+		return dst;
+
 	dst = isl_space_cow(dst);
 
 	if (!dst || !src)

Modified: polly/trunk/lib/External/isl/isl_space_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_space_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_space_private.h (original)
+++ polly/trunk/lib/External/isl/isl_space_private.h Sat Apr 21 01:34:22 2018
@@ -31,6 +31,8 @@ uint32_t isl_space_get_tuple_hash(__isl_
 uint32_t isl_space_get_hash(__isl_keep isl_space *space);
 uint32_t isl_space_get_domain_hash(__isl_keep isl_space *space);
 
+isl_bool isl_space_has_domain_tuples(__isl_keep isl_space *space1,
+	__isl_keep isl_space *space2);
 isl_bool isl_space_is_domain_internal(__isl_keep isl_space *space1,
 	__isl_keep isl_space *space2);
 isl_bool isl_space_is_range_internal(__isl_keep isl_space *space1,

Modified: polly/trunk/lib/External/isl/isl_stride.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_stride.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_stride.c (original)
+++ polly/trunk/lib/External/isl/isl_stride.c Sat Apr 21 01:34:22 2018
@@ -8,7 +8,8 @@
  */
 
 #include <isl/val.h>
-#include <isl/aff.h>
+#include <isl_map_private.h>
+#include <isl_aff_private.h>
 #include <isl/constraint.h>
 #include <isl/set.h>
 
@@ -208,9 +209,13 @@ static isl_stat detect_stride(__isl_take
 	isl_ctx *ctx;
 	isl_stat r = isl_stat_ok;
 	isl_val *v, *stride, *m;
+	isl_bool is_eq, relevant, has_stride;
 
-	if (!isl_constraint_is_equality(c) ||
-	    !isl_constraint_involves_dims(c, isl_dim_set, data->pos, 1)) {
+	is_eq = isl_constraint_is_equality(c);
+	relevant = isl_constraint_involves_dims(c, isl_dim_set, data->pos, 1);
+	if (is_eq < 0 || relevant < 0)
+		goto error;
+	if (!is_eq || !relevant) {
 		isl_constraint_free(c);
 		return isl_stat_ok;
 	}
@@ -228,7 +233,8 @@ static isl_stat detect_stride(__isl_take
 	stride = isl_val_div(stride, isl_val_copy(m));
 	v = isl_val_div(v, isl_val_copy(m));
 
-	if (!isl_val_is_zero(stride) && !isl_val_is_one(stride)) {
+	has_stride = isl_val_gt_si(stride, 1);
+	if (has_stride >= 0 && has_stride) {
 		isl_aff *aff;
 		isl_val *gcd, *a, *b;
 
@@ -252,7 +258,12 @@ static isl_stat detect_stride(__isl_take
 	}
 
 	isl_constraint_free(c);
+	if (has_stride < 0)
+		return isl_stat_error;
 	return r;
+error:
+	isl_constraint_free(c);
+	return isl_stat_error;
 }
 
 /* Check if the constraints in "set" imply any stride on set dimension "pos" and
@@ -322,3 +333,32 @@ __isl_give isl_val *isl_set_get_stride(_
 
 	return data.stride;
 }
+
+/* Check if the constraints in "map" imply any stride on output dimension "pos",
+ * independently of any other output dimensions, and
+ * return the results in the form of an offset and a stride.
+ *
+ * Convert the input to a set with only the input dimensions and
+ * the single output dimension such that it be passed to
+ * isl_set_get_stride_info and convert the result back to
+ * an expression defined over the domain of "map".
+ */
+__isl_give isl_stride_info *isl_map_get_range_stride_info(
+	__isl_keep isl_map *map, int pos)
+{
+	isl_stride_info *si;
+	isl_set *set;
+
+	map = isl_map_copy(map);
+	map = isl_map_project_onto(map, isl_dim_out, pos, 1);
+	pos = isl_map_dim(map, isl_dim_in);
+	set = isl_map_wrap(map);
+	si = isl_set_get_stride_info(set, pos);
+	isl_set_free(set);
+	if (!si)
+		return NULL;
+	si->offset = isl_aff_domain_factor_domain(si->offset);
+	if (!si->offset)
+		return isl_stride_info_free(si);
+	return si;
+}

Modified: polly/trunk/lib/External/isl/isl_tab_pip.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_tab_pip.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_tab_pip.c (original)
+++ polly/trunk/lib/External/isl/isl_tab_pip.c Sat Apr 21 01:34:22 2018
@@ -5765,7 +5765,7 @@ static int need_substitution(__isl_keep
 	pos = isl_multi_aff_dim(maff, isl_dim_in) - 1;
 
 	for (i = 0; i < maff->n; ++i)
-		if (isl_aff_involves_dims(maff->p[i], isl_dim_in, pos, 1))
+		if (isl_aff_involves_dims(maff->u.p[i], isl_dim_in, pos, 1))
 			return 1;
 
 	return 0;

Modified: polly/trunk/lib/External/isl/isl_test.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_test.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_test.c (original)
+++ polly/trunk/lib/External/isl/isl_test.c Sat Apr 21 01:34:22 2018
@@ -22,6 +22,7 @@
 #include <isl_map_private.h>
 #include <isl_aff_private.h>
 #include <isl_space_private.h>
+#include <isl/id.h>
 #include <isl/set.h>
 #include <isl/flow.h>
 #include <isl_constraint_private.h>
@@ -119,6 +120,200 @@ static int test_parse_multi_val(isl_ctx
 	return mv ? 0 : -1;
 }
 
+/* Check that printing "mpa" and parsing the output results
+ * in the same expression.
+ */
+static isl_stat check_reparse_mpa(isl_ctx *ctx,
+	__isl_take isl_multi_pw_aff *mpa)
+{
+	char *str;
+	isl_bool equal;
+	isl_multi_pw_aff *mpa2;
+
+	str = isl_multi_pw_aff_to_str(mpa);
+	mpa2 = isl_multi_pw_aff_read_from_str(ctx, str);
+	free(str);
+	equal = isl_multi_pw_aff_plain_is_equal(mpa, mpa2);
+	isl_multi_pw_aff_free(mpa);
+	isl_multi_pw_aff_free(mpa2);
+	if (equal < 0)
+		return isl_stat_error;
+	if (!equal)
+		isl_die(ctx, isl_error_unknown,
+			"parsed function not equal to original",
+			return isl_stat_error);
+
+	return isl_stat_ok;
+}
+
+/* String descriptions of multi piecewise affine expressions
+ * that are used for testing printing and parsing.
+ */
+const char *parse_multi_mpa_tests[] = {
+	"{ A[x, y] -> [] : x + y >= 0 }",
+	"{ A[x, y] -> B[] : x + y >= 0 }",
+	"{ A[x, y] -> [x] : x + y >= 0 }",
+	"[N] -> { A[x, y] -> [x] : x + y <= N }",
+	"{ A[x, y] -> [x, y] : x + y >= 0 }",
+	"{ A[x, y] -> [(x : x >= 0), (y : y >= 0)] : x + y >= 0 }",
+	"[N] -> { [] : N >= 0 }",
+	"[N] -> { [] : N >= 0 }",
+	"[N] -> { [N] : N >= 0 }",
+	"[N] -> { [N, N + 1] : N >= 0 }",
+	"[N, M] -> { [(N : N >= 0), (M : M >= 0)] : N + M >= 0 }",
+};
+
+/* Test parsing of multi piecewise affine expressions by printing
+ * the expressions and checking that parsing the output results
+ * in the same expression.
+ * Do this for a couple of manually constructed expressions and
+ * a set of expressions parsed from strings.
+ */
+static int test_parse_mpa(isl_ctx *ctx)
+{
+	int i;
+	isl_space *space;
+	isl_set *dom;
+	isl_multi_pw_aff *mpa;
+	isl_stat r;
+
+	space = isl_space_set_alloc(ctx, 0, 0);
+	space = isl_space_set_tuple_name(space, isl_dim_set, "A");
+	mpa = isl_multi_pw_aff_zero(space);
+	r = check_reparse_mpa(ctx, mpa);
+	if (r < 0)
+		return -1;
+
+	space = isl_space_set_alloc(ctx, 1, 0);
+	space = isl_space_set_dim_name(space, isl_dim_param, 0, "N");
+	space = isl_space_set_tuple_name(space, isl_dim_set, "A");
+	dom = isl_set_universe(isl_space_params(isl_space_copy(space)));
+	dom = isl_set_lower_bound_si(dom, isl_dim_param, 0, 5);
+	mpa = isl_multi_pw_aff_zero(space);
+	mpa = isl_multi_pw_aff_intersect_domain(mpa, dom);
+	r = check_reparse_mpa(ctx, mpa);
+	if (r < 0)
+		return -1;
+
+	for (i = 0; i < ARRAY_SIZE(parse_multi_mpa_tests); ++i) {
+		const char *str;
+
+		str = parse_multi_mpa_tests[i];
+		mpa = isl_multi_pw_aff_read_from_str(ctx, str);
+		r = check_reparse_mpa(ctx, mpa);
+		if (r < 0)
+			return -1;
+	}
+
+	return 0;
+}
+
+/* Check that printing "mupa" and parsing the output results
+ * in the same expression.
+ */
+static isl_stat check_reparse_mupa(isl_ctx *ctx,
+	__isl_take isl_multi_union_pw_aff *mupa)
+{
+	char *str;
+	isl_bool equal;
+	isl_multi_union_pw_aff *mupa2;
+
+	str = isl_multi_union_pw_aff_to_str(mupa);
+	mupa2 = isl_multi_union_pw_aff_read_from_str(ctx, str);
+	free(str);
+	equal = isl_multi_union_pw_aff_plain_is_equal(mupa, mupa2);
+	isl_multi_union_pw_aff_free(mupa);
+	isl_multi_union_pw_aff_free(mupa2);
+	if (equal < 0)
+		return isl_stat_error;
+	if (!equal)
+		isl_die(ctx, isl_error_unknown,
+			"parsed function not equal to original",
+			return isl_stat_error);
+
+	return isl_stat_ok;
+}
+
+/* String descriptions of multi union piecewise affine expressions
+ * that are used for testing printing and parsing.
+ */
+const char *parse_multi_mupa_tests[] = {
+	"[]",
+	"A[]",
+	"A[B[] -> C[]]",
+	"(A[] : { S[x] : x > 0; T[y] : y >= 0 })",
+	"(A[] : { })",
+	"[N] -> (A[] : { })",
+	"[N] -> (A[] : { : N >= 0 })",
+	"[N] -> (A[] : { S[x] : x > N; T[y] : y >= 0 })",
+	"(A[] : [N] -> { S[x] : x > N; T[y] : y >= 0 })",
+	"A[{ S[x] -> [x + 1]; T[x] -> [x] }]",
+	"(A[{ S[x] -> [x + 1]; T[x] -> [x] }] : "
+		"{ S[x] : x > 0; T[y] : y >= 0 })",
+};
+
+/* Test parsing of multi union piecewise affine expressions by printing
+ * the expressions and checking that parsing the output results
+ * in the same expression.
+ * Do this for a couple of manually constructed expressions and
+ * a set of expressions parsed from strings.
+ */
+static int test_parse_mupa(isl_ctx *ctx)
+{
+	int i;
+	isl_space *space;
+	isl_multi_union_pw_aff *mupa;
+	isl_set *dom;
+	isl_union_set *uset;
+	isl_stat r;
+
+	space = isl_space_set_alloc(ctx, 0, 0);
+	space = isl_space_set_tuple_name(space, isl_dim_set, "A");
+	mupa = isl_multi_union_pw_aff_zero(space);
+	r = check_reparse_mupa(ctx, mupa);
+	if (r < 0)
+		return -1;
+
+	space = isl_space_set_alloc(ctx, 1, 0);
+	space = isl_space_set_dim_name(space, isl_dim_param, 0, "N");
+	space = isl_space_set_tuple_name(space, isl_dim_set, "A");
+	dom = isl_set_universe(space);
+	dom = isl_set_lower_bound_si(dom, isl_dim_param, 0, 5);
+	uset = isl_union_set_from_set(dom);
+	space = isl_space_set_alloc(ctx, 1, 0);
+	space = isl_space_set_dim_name(space, isl_dim_param, 0, "N");
+	space = isl_space_set_tuple_name(space, isl_dim_set, "B");
+	mupa = isl_multi_union_pw_aff_zero(space);
+	mupa = isl_multi_union_pw_aff_intersect_domain(mupa, uset);
+	r = check_reparse_mupa(ctx, mupa);
+	if (r < 0)
+		return -1;
+
+	for (i = 0; i < ARRAY_SIZE(parse_multi_mupa_tests); ++i) {
+		const char *str;
+
+		str = parse_multi_mupa_tests[i];
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx, str);
+		r = check_reparse_mupa(ctx, mupa);
+		if (r < 0)
+			return -1;
+	}
+
+	return 0;
+}
+
+/* Test parsing of multi expressions.
+ */
+static int test_parse_multi(isl_ctx *ctx)
+{
+	if (test_parse_mpa(ctx) < 0)
+		return -1;
+	if (test_parse_mupa(ctx) < 0)
+		return -1;
+
+	return 0;
+}
+
 /* Pairs of binary relation representations that should represent
  * the same binary relations.
  */
@@ -206,6 +401,8 @@ int test_parse(struct isl_ctx *ctx)
 		return -1;
 	if (test_parse_multi_val(ctx, "{ A[4, infty, NaN, -1/2, 2/3] }") < 0)
 		return -1;
+	if (test_parse_multi(ctx) < 0)
+		return -1;
 
 	str = "{ [i] -> [-i] }";
 	map = isl_map_read_from_str(ctx, str);
@@ -445,6 +642,36 @@ static int test_dim(isl_ctx *ctx)
 	return 0;
 }
 
+/* Check that "val" is equal to the value described by "str".
+ * If "str" is "NaN", then check for a NaN value explicitly.
+ */
+static isl_stat val_check_equal(__isl_keep isl_val *val, const char *str)
+{
+	isl_bool ok, is_nan;
+	isl_ctx *ctx;
+	isl_val *res;
+
+	if (!val)
+		return isl_stat_error;
+
+	ctx = isl_val_get_ctx(val);
+	res = isl_val_read_from_str(ctx, str);
+	is_nan = isl_val_is_nan(res);
+	if (is_nan < 0)
+		ok = isl_bool_error;
+	else if (is_nan)
+		ok = isl_val_is_nan(val);
+	else
+		ok = isl_val_eq(val, res);
+	isl_val_free(res);
+	if (ok < 0)
+		return isl_stat_error;
+	if (!ok)
+		isl_die(ctx, isl_error_unknown,
+			"unexpected result", return isl_stat_error);
+	return isl_stat_ok;
+}
+
 struct {
 	__isl_give isl_val *(*op)(__isl_take isl_val *v);
 	const char *arg;
@@ -504,29 +731,19 @@ struct {
 static int test_un_val(isl_ctx *ctx)
 {
 	int i;
-	isl_val *v, *res;
+	isl_val *v;
 	__isl_give isl_val *(*fn)(__isl_take isl_val *v);
-	isl_bool ok, is_nan;
 
 	for (i = 0; i < ARRAY_SIZE(val_un_tests); ++i) {
+		isl_stat r;
+
 		v = isl_val_read_from_str(ctx, val_un_tests[i].arg);
-		res = isl_val_read_from_str(ctx, val_un_tests[i].res);
 		fn = val_un_tests[i].op;
 		v = fn(v);
-		is_nan = isl_val_is_nan(res);
-		if (is_nan < 0)
-			ok = isl_bool_error;
-		else if (is_nan)
-			ok = isl_val_is_nan(v);
-		else
-			ok = isl_val_eq(v, res);
+		r = val_check_equal(v, val_un_tests[i].res);
 		isl_val_free(v);
-		isl_val_free(res);
-		if (ok < 0)
+		if (r < 0)
 			return -1;
-		if (!ok)
-			isl_die(ctx, isl_error_unknown,
-				"unexpected result", return -1);
 	}
 
 	return 0;
@@ -4842,43 +5059,263 @@ static int test_bin_upma_fail(isl_ctx *c
 	return 0;
 }
 
-/* Inputs for basic tests of binary operations on
- * pairs of isl_multi_union_pw_aff and isl_union_set objects.
+/* Inputs for basic tests of unary operations on isl_multi_pw_aff objects.
+ * "fn" is the function that is tested.
+ * "arg" is a string description of the input.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_pw_aff *(*fn)(__isl_take isl_multi_pw_aff *mpa);
+	const char *arg;
+	const char *res;
+} mpa_un_tests[] = {
+	{ &isl_multi_pw_aff_range_factor_domain,
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[(2 : x <= 10)]] }",
+	  "{ A[x] -> B[(1 : x >= 5)] }" },
+	{ &isl_multi_pw_aff_range_factor_range,
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[(2 : x <= 10)]] }",
+	  "{ A[y] -> C[(2 : y <= 10)] }" },
+	{ &isl_multi_pw_aff_range_factor_domain,
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[]] }",
+	  "{ A[x] -> B[(1 : x >= 5)] }" },
+	{ &isl_multi_pw_aff_range_factor_range,
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[]] }",
+	  "{ A[y] -> C[] }" },
+	{ &isl_multi_pw_aff_range_factor_domain,
+	  "{ A[x] -> [B[] -> C[(2 : x <= 10)]] }",
+	  "{ A[x] -> B[] }" },
+	{ &isl_multi_pw_aff_range_factor_range,
+	  "{ A[x] -> [B[] -> C[(2 : x <= 10)]] }",
+	  "{ A[y] -> C[(2 : y <= 10)] }" },
+	{ &isl_multi_pw_aff_range_factor_domain,
+	  "{ A[x] -> [B[] -> C[]] }",
+	  "{ A[x] -> B[] }" },
+	{ &isl_multi_pw_aff_range_factor_range,
+	  "{ A[x] -> [B[] -> C[]] }",
+	  "{ A[y] -> C[] }" },
+	{ &isl_multi_pw_aff_factor_range,
+	  "{ [B[] -> C[]] }",
+	  "{ C[] }" },
+	{ &isl_multi_pw_aff_range_factor_domain,
+	  "{ A[x] -> [B[] -> C[]] : x >= 0 }",
+	  "{ A[x] -> B[] : x >= 0 }" },
+	{ &isl_multi_pw_aff_range_factor_range,
+	  "{ A[x] -> [B[] -> C[]] : x >= 0 }",
+	  "{ A[y] -> C[] : y >= 0 }" },
+	{ &isl_multi_pw_aff_factor_range,
+	  "[N] -> { [B[] -> C[]] : N >= 0 }",
+	  "[N] -> { C[] : N >= 0 }" },
+};
+
+/* Perform some basic tests of unary operations on isl_multi_pw_aff objects.
+ */
+static int test_un_mpa(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_pw_aff *mpa, *res;
+
+	for (i = 0; i < ARRAY_SIZE(mpa_un_tests); ++i) {
+		mpa = isl_multi_pw_aff_read_from_str(ctx, mpa_un_tests[i].arg);
+		res = isl_multi_pw_aff_read_from_str(ctx, mpa_un_tests[i].res);
+		mpa = mpa_un_tests[i].fn(mpa);
+		ok = isl_multi_pw_aff_plain_is_equal(mpa, res);
+		isl_multi_pw_aff_free(mpa);
+		isl_multi_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on isl_multi_pw_aff objects.
  * "fn" is the function that is tested.
  * "arg1" and "arg2" are string descriptions of the inputs.
  * "res" is a string description of the expected result.
  */
 struct {
-	__isl_give isl_multi_union_pw_aff *(*fn)(
-		__isl_take isl_multi_union_pw_aff *mupa,
-		__isl_take isl_union_set *uset);
+	__isl_give isl_multi_pw_aff *(*fn)(
+		__isl_take isl_multi_pw_aff *mpa1,
+		__isl_take isl_multi_pw_aff *mpa2);
 	const char *arg1;
 	const char *arg2;
 	const char *res;
-} mupa_uset_tests[] = {
-	{ &isl_multi_union_pw_aff_intersect_domain,
-	  "C[{ B[i,j] -> [i + 2j] }]", "{ B[i,i] }",
-	  "C[{ B[i,i] -> [3i] }]" },
+} mpa_bin_tests[] = {
+	{ &isl_multi_pw_aff_add, "{ A[] -> [1] }", "{ A[] -> [2] }",
+	  "{ A[] -> [3] }" },
+	{ &isl_multi_pw_aff_add, "{ A[x] -> [(1 : x >= 5)] }",
+	  "{ A[x] -> [(x : x <= 10)] }",
+	  "{ A[x] -> [(1 + x : 5 <= x <= 10)] }" },
+	{ &isl_multi_pw_aff_add, "{ A[x] -> [] : x >= 5 }",
+	  "{ A[x] -> [] : x <= 10 }",
+	  "{ A[x] -> [] : 5 <= x <= 10 }" },
+	{ &isl_multi_pw_aff_add, "{ A[x] -> [] : x >= 5 }",
+	  "[N] -> { A[x] -> [] : x <= N }",
+	  "[N] -> { A[x] -> [] : 5 <= x <= N }" },
+	{ &isl_multi_pw_aff_add,
+	  "[N] -> { A[x] -> [] : x <= N }",
+	  "{ A[x] -> [] : x >= 5 }",
+	  "[N] -> { A[x] -> [] : 5 <= x <= N }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ A[y] -> C[(2 : y <= 10)] }",
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[(2 : x <= 10)]] }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[x] -> B[1] : x >= 5 }",
+	  "{ A[y] -> C[2] : y <= 10 }",
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[(2 : x <= 10)]] }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[x] -> B[1] : x >= 5 }",
+	  "[N] -> { A[y] -> C[2] : y <= N }",
+	  "[N] -> { A[x] -> [B[(1 : x >= 5)] -> C[(2 : x <= N)]] }" },
+	{ &isl_multi_pw_aff_range_product, "[N] -> { A[x] -> B[1] : x >= N }",
+	  "{ A[y] -> C[2] : y <= 10 }",
+	  "[N] -> { A[x] -> [B[(1 : x >= N)] -> C[(2 : x <= 10)]] }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[] -> B[1] }", "{ A[] -> C[2] }",
+	  "{ A[] -> [B[1] -> C[2]] }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[] -> B[] }", "{ A[] -> C[] }",
+	  "{ A[] -> [B[] -> C[]] }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ A[y] -> C[] : y <= 10 }",
+	  "{ A[x] -> [B[(1 : x >= 5)] -> C[]] : x <= 10 }" },
+	{ &isl_multi_pw_aff_range_product, "{ A[y] -> C[] : y <= 10 }",
+	  "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ A[x] -> [C[] -> B[(1 : x >= 5)]] : x <= 10 }" },
+	{ &isl_multi_pw_aff_product, "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ A[y] -> C[(2 : y <= 10)] }",
+	  "{ [A[x] -> A[y]] -> [B[(1 : x >= 5)] -> C[(2 : y <= 10)]] }" },
+	{ &isl_multi_pw_aff_product, "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ A[y] -> C[] : y <= 10 }",
+	  "{ [A[x] -> A[y]] -> [B[(1 : x >= 5)] -> C[]] : y <= 10 }" },
+	{ &isl_multi_pw_aff_product, "{ A[y] -> C[] : y <= 10 }",
+	  "{ A[x] -> B[(1 : x >= 5)] }",
+	  "{ [A[y] -> A[x]] -> [C[] -> B[(1 : x >= 5)]] : y <= 10 }" },
+	{ &isl_multi_pw_aff_product, "{ A[x] -> B[(1 : x >= 5)] }",
+	  "[N] -> { A[y] -> C[] : y <= N }",
+	  "[N] -> { [A[x] -> A[y]] -> [B[(1 : x >= 5)] -> C[]] : y <= N }" },
+	{ &isl_multi_pw_aff_product, "[N] -> { A[y] -> C[] : y <= N }",
+	  "{ A[x] -> B[(1 : x >= 5)] }",
+	  "[N] -> { [A[y] -> A[x]] -> [C[] -> B[(1 : x >= 5)]] : y <= N }" },
+	{ &isl_multi_pw_aff_product, "{ A[x] -> B[] : x >= 5 }",
+	  "{ A[y] -> C[] : y <= 10 }",
+	  "{ [A[x] -> A[y]] -> [B[] -> C[]] : x >= 5 and y <= 10 }" },
+	{ &isl_multi_pw_aff_product, "{ A[] -> B[1] }", "{ A[] -> C[2] }",
+	  "{ [A[] -> A[]] -> [B[1] -> C[2]] }" },
+	{ &isl_multi_pw_aff_product, "{ A[] -> B[] }", "{ A[] -> C[] }",
+	  "{ [A[] -> A[]] -> [B[] -> C[]] }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[i + 2j] }", "{ A[a,b] -> B[b,a] }",
+	  "{ A[a,b] -> C[b + 2a] }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[i + 2j] }",
+	  "{ A[a,b] -> B[(b : b > a),(a : b > a)] }",
+	  "{ A[a,b] -> C[(b + 2a : b > a)] }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[(i + 2j : j > 4)] }",
+	  "{ A[a,b] -> B[(b : b > a),(a : b > a)] }",
+	  "{ A[a,b] -> C[(b + 2a : b > a > 4)] }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[] }",
+	  "{ A[a,b] -> B[(b : b > a),(a : b > a)] }",
+	  "{ A[a,b] -> C[] }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[] : i > j }",
+	  "{ A[a,b] -> B[b,a] }",
+	  "{ A[a,b] -> C[] : b > a }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "{ B[i,j] -> C[] : j > 5 }",
+	  "{ A[a,b] -> B[(b : b > a),(a : b > a)] }",
+	  "{ A[a,b] -> C[] : b > a > 5 }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "[N] -> { B[i,j] -> C[] : j > N }",
+	  "{ A[a,b] -> B[(b : b > a),(a : b > a)] }",
+	  "[N] -> { A[a,b] -> C[] : b > a > N }" },
+	{ &isl_multi_pw_aff_pullback_multi_pw_aff,
+	  "[M,N] -> { B[] -> C[] : N > 5 }",
+	  "[M,N] -> { A[] -> B[] : M > N }",
+	  "[M,N] -> { A[] -> C[] : M > N > 5 }" },
 };
 
-/* Perform some basic tests of binary operations on
- * pairs of isl_multi_union_pw_aff and isl_union_set objects.
+/* Perform some basic tests of binary operations on isl_multi_pw_aff objects.
  */
-static int test_mupa_uset(isl_ctx *ctx)
+static int test_bin_mpa(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_pw_aff *mpa1, *mpa2, *res;
+
+	for (i = 0; i < ARRAY_SIZE(mpa_bin_tests); ++i) {
+		mpa1 = isl_multi_pw_aff_read_from_str(ctx,
+							mpa_bin_tests[i].arg1);
+		mpa2 = isl_multi_pw_aff_read_from_str(ctx,
+							mpa_bin_tests[i].arg2);
+		res = isl_multi_pw_aff_read_from_str(ctx,
+							mpa_bin_tests[i].res);
+		mpa1 = mpa_bin_tests[i].fn(mpa1, mpa2);
+		ok = isl_multi_pw_aff_plain_is_equal(mpa1, res);
+		isl_multi_pw_aff_free(mpa1);
+		isl_multi_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of unary operations on
+ * isl_multi_union_pw_aff objects.
+ * "fn" is the function that is tested.
+ * "arg" is a string description of the input.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa);
+	const char *arg;
+	const char *res;
+} mupa_un_tests[] = {
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[B[{ A[] -> [1] }] -> C[{ A[] -> [2] }]]",
+	  "C[{ A[] -> [2] }]" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[B[] -> C[{ A[] -> [2] }]]",
+	  "C[{ A[] -> [2] }]" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[B[{ A[] -> [1] }] -> C[]]",
+	  "C[]" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[B[] -> C[]]",
+	  "C[]" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "([B[] -> C[]] : { A[x] : x >= 0 })",
+	  "(C[] : { A[x] : x >= 0 })" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[N] -> ([B[] -> C[]] : { A[x] : x <= N })",
+	  "[N] -> (C[] : { A[x] : x <= N })" },
+	{ &isl_multi_union_pw_aff_factor_range,
+	  "[N] -> ([B[] -> C[]] : { : N >= 0 })",
+	  "[N] -> (C[] : { : N >= 0 })" },
+};
+
+/* Perform some basic tests of unary operations on
+ * isl_multi_union_pw_aff objects.
+ */
+static int test_un_mupa(isl_ctx *ctx)
 {
 	int i;
 	isl_bool ok;
 	isl_multi_union_pw_aff *mupa, *res;
-	isl_union_set *uset;
 
-	for (i = 0; i < ARRAY_SIZE(mupa_uset_tests); ++i) {
+	for (i = 0; i < ARRAY_SIZE(mupa_un_tests); ++i) {
 		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
-						    mupa_uset_tests[i].arg1);
-		uset = isl_union_set_read_from_str(ctx,
-						    mupa_uset_tests[i].arg2);
+							mupa_un_tests[i].arg);
 		res = isl_multi_union_pw_aff_read_from_str(ctx,
-						    mupa_uset_tests[i].res);
-		mupa = mupa_uset_tests[i].fn(mupa, uset);
+							mupa_un_tests[i].res);
+		mupa = mupa_un_tests[i].fn(mupa);
 		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
 		isl_multi_union_pw_aff_free(mupa);
 		isl_multi_union_pw_aff_free(res);
@@ -4892,65 +5329,762 @@ static int test_mupa_uset(isl_ctx *ctx)
 	return 0;
 }
 
-int test_aff(isl_ctx *ctx)
-{
-	const char *str;
-	isl_set *set;
-	isl_space *space;
-	isl_local_space *ls;
-	isl_aff *aff;
-	int zero, equal;
-
-	if (test_upa(ctx) < 0)
-		return -1;
-	if (test_bin_aff(ctx) < 0)
-		return -1;
-	if (test_bin_pw_aff(ctx) < 0)
-		return -1;
-	if (test_bin_upma(ctx) < 0)
-		return -1;
-	if (test_bin_upma_fail(ctx) < 0)
-		return -1;
-	if (test_mupa_uset(ctx) < 0)
-		return -1;
-
-	space = isl_space_set_alloc(ctx, 0, 1);
-	ls = isl_local_space_from_space(space);
-	aff = isl_aff_zero_on_domain(ls);
-
-	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
-	aff = isl_aff_scale_down_ui(aff, 3);
-	aff = isl_aff_floor(aff);
-	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
-	aff = isl_aff_scale_down_ui(aff, 2);
-	aff = isl_aff_floor(aff);
-	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
-
-	str = "{ [10] }";
-	set = isl_set_read_from_str(ctx, str);
-	aff = isl_aff_gist(aff, set);
-
-	aff = isl_aff_add_constant_si(aff, -16);
-	zero = isl_aff_plain_is_zero(aff);
-	isl_aff_free(aff);
+/* Inputs for basic tests of binary operations on
+ * isl_multi_union_pw_aff objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa1,
+		__isl_take isl_multi_union_pw_aff *mupa2);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_bin_tests[] = {
+	{ &isl_multi_union_pw_aff_add, "[{ A[] -> [1] }]", "[{ A[] -> [2] }]",
+	  "[{ A[] -> [3] }]" },
+	{ &isl_multi_union_pw_aff_sub, "[{ A[] -> [1] }]", "[{ A[] -> [2] }]",
+	  "[{ A[] -> [-1] }]" },
+	{ &isl_multi_union_pw_aff_add,
+	  "[{ A[] -> [1]; B[] -> [4] }]",
+	  "[{ A[] -> [2]; C[] -> [5] }]",
+	  "[{ A[] -> [3] }]" },
+	{ &isl_multi_union_pw_aff_union_add,
+	  "[{ A[] -> [1]; B[] -> [4] }]",
+	  "[{ A[] -> [2]; C[] -> [5] }]",
+	  "[{ A[] -> [3]; B[] -> [4]; C[] -> [5] }]" },
+	{ &isl_multi_union_pw_aff_add, "[{ A[x] -> [(1)] : x >= 5 }]",
+	  "[{ A[x] -> [(x)] : x <= 10 }]",
+	  "[{ A[x] -> [(1 + x)] : 5 <= x <= 10 }]" },
+	{ &isl_multi_union_pw_aff_add, "([] : { A[x] : x >= 5 })",
+	  "([] : { A[x] : x <= 10 })",
+	  "([] : { A[x] : 5 <= x <= 10 })" },
+	{ &isl_multi_union_pw_aff_add, "([] : { A[x] : x >= 5 })",
+	  "[N] -> ([] : { A[x] : x <= N })",
+	  "[N] -> ([] : { A[x] : 5 <= x <= N })" },
+	{ &isl_multi_union_pw_aff_add, "[N] -> ([] : { A[x] : x >= N })",
+	  "([] : { A[x] : x <= 10 })",
+	  "[N] -> ([] : { A[x] : N <= x <= 10 })" },
+	{ &isl_multi_union_pw_aff_union_add, "[{ A[x] -> [(1)] : x >= 5 }]",
+	  "[{ A[x] -> [(x)] : x <= 10 }]",
+	  "[{ A[x] -> [(1 + x)] : 5 <= x <= 10; "
+	     "A[x] -> [(1)] : x > 10; A[x] -> [(x)] : x < 5 }]" },
+	{ &isl_multi_union_pw_aff_union_add, "([] : { A[x] : x >= 5 })",
+	  "([] : { A[x] : x <= 10 })",
+	  "([] : { A[x] })" },
+	{ &isl_multi_union_pw_aff_union_add, "([] : { A[x] : x >= 0 })",
+	  "[N] -> ([] : { A[x] : x >= N })",
+	  "[N] -> ([] : { A[x] : x >= 0 or x >= N })" },
+	{ &isl_multi_union_pw_aff_union_add,
+	  "[N] -> ([] : { A[] : N >= 0})",
+	  "[N] -> ([] : { A[] : N <= 0})",
+	  "[N] -> ([] : { A[] })" },
+	{ &isl_multi_union_pw_aff_union_add,
+	  "[N] -> ([] : { A[] })",
+	  "[N] -> ([] : { : })",
+	  "[N] -> ([] : { : })" },
+	{ &isl_multi_union_pw_aff_union_add,
+	  "[N] -> ([] : { : })",
+	  "[N] -> ([] : { A[] })",
+	  "[N] -> ([] : { : })" },
+	{ &isl_multi_union_pw_aff_union_add,
+	  "[N] -> ([] : { : N >= 0})",
+	  "[N] -> ([] : { : N <= 0})",
+	  "[N] -> ([] : { : })" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "B[{ A[] -> [1] }]",
+	  "C[{ A[] -> [2] }]",
+	  "[B[{ A[] -> [1] }] -> C[{ A[] -> [2] }]]" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "(B[] : { A[x] : x >= 5 })",
+	  "(C[] : { A[x] : x <= 10 })",
+	  "([B[] -> C[]] : { A[x] : 5 <= x <= 10 })" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "B[{ A[x] -> [x + 1] : x >= 5 }]",
+	  "(C[] : { A[x] : x <= 10 })",
+	  "[B[{ A[x] -> [x + 1] : 5 <= x <= 10 }] -> C[]]" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "(C[] : { A[x] : x <= 10 })",
+	  "B[{ A[x] -> [x + 1] : x >= 5 }]",
+	  "[C[] -> B[{ A[x] -> [x + 1] : 5 <= x <= 10 }]]" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "B[{ A[x] -> [x + 1] : x >= 5 }]",
+	  "[N] -> (C[] : { A[x] : x <= N })",
+	  "[N] -> [B[{ A[x] -> [x + 1] : 5 <= x <= N }] -> C[]]" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "[N] -> (C[] : { A[x] : x <= N })",
+	  "B[{ A[x] -> [x + 1] : x >= 5 }]",
+	  "[N] -> [C[] -> B[{ A[x] -> [x + 1] : 5 <= x <= N }]]" },
+	{ &isl_multi_union_pw_aff_range_product,
+	  "B[{ A[] -> [1]; D[] -> [3] }]",
+	  "C[{ A[] -> [2] }]",
+	  "[B[{ A[] -> [1]; D[] -> [3] }] -> C[{ A[] -> [2] }]]" },
+};
 
-	if (zero < 0)
-		return -1;
-	if (!zero)
-		isl_die(ctx, isl_error_unknown, "unexpected result", return -1);
+/* Perform some basic tests of binary operations on
+ * isl_multi_union_pw_aff objects.
+ */
+static int test_bin_mupa(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa1, *mupa2, *res;
 
-	aff = isl_aff_read_from_str(ctx, "{ [-1] }");
-	aff = isl_aff_scale_down_ui(aff, 64);
-	aff = isl_aff_floor(aff);
-	equal = aff_check_plain_equal(aff, "{ [-1] }");
-	isl_aff_free(aff);
-	if (equal < 0)
-		return -1;
+	for (i = 0; i < ARRAY_SIZE(mupa_bin_tests); ++i) {
+		mupa1 = isl_multi_union_pw_aff_read_from_str(ctx,
+							mupa_bin_tests[i].arg1);
+		mupa2 = isl_multi_union_pw_aff_read_from_str(ctx,
+							mupa_bin_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+							mupa_bin_tests[i].res);
+		mupa1 = mupa_bin_tests[i].fn(mupa1, mupa2);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa1, res);
+		isl_multi_union_pw_aff_free(mupa1);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
 
 	return 0;
 }
 
-/* Check that "pa" consists of a single expression.
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_set objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_set *set);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_set_tests[] = {
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "C[{ B[i,j] -> [i + 2j] }]", "{ C[1] }",
+	  "C[{ B[i,j] -> [i + 2j] : i + 2j = 1 }]" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "C[{ B[i,j] -> [i + 2j] }]", "[N] -> { C[N] }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : i + 2j = N }]" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "[N] -> C[{ B[i,j] -> [i + 2j + N] }]", "{ C[1] }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j + N] : i + 2j + N = 1 }]" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "C[{ B[i,j] -> [i + 2j] }]", "[N] -> { C[x] : N >= 0 }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : N >= 0 }]" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "C[]", "{ C[] }", "C[]" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ C[] }",
+	  "[N] -> (C[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "(C[] : { A[a,b] })",
+	  "{ C[] }",
+	  "(C[] : { A[a,b] })" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "[N] -> (C[] : { A[a,b] : a,b <= N })",
+	  "{ C[] }",
+	  "[N] -> (C[] : { A[a,b] : a,b <= N })" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "C[]",
+	  "[N] -> { C[] : N >= 0 }",
+	  "[N] -> (C[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "(C[] : { A[a,b] })",
+	  "[N] -> { C[] : N >= 0 }",
+	  "[N] -> (C[] : { A[a,b] : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_intersect_range,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "[N] -> { C[] : N < 1024 }",
+	  "[N] -> (C[] : { : 0 <= N < 1024 })" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "C[{ B[i,j] -> [i + 2j] }]", "[N] -> { : N >= 0 }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : N >= 0}]" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : N <= 256 }]", "[N] -> { : N >= 0 }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : 0 <= N <= 256 }]" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : N <= 256 }]", "{ : }",
+	  "[N] -> C[{ B[i,j] -> [i + 2j] : N <= 256 }]" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "C[]", "[N] -> { : N >= 0 }",
+	  "[N] -> (C[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "(C[] : { A[a,b] })", "[N] -> { : N >= 0 }",
+	  "[N] -> (C[] : { A[a,b] : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "[N] -> (C[] : { A[a,N] })", "{ : }",
+	  "[N] -> (C[] : { A[a,N] })" },
+	{ &isl_multi_union_pw_aff_intersect_params,
+	  "[N] -> (C[] : { A[a,b] : N <= 256 })", "[N] -> { : N >= 0 }",
+	  "[N] -> (C[] : { A[a,b] : 0 <= N <= 256 })" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_set objects.
+ */
+static int test_mupa_set(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa, *res;
+	isl_set *set;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_set_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_set_tests[i].arg1);
+		set = isl_set_read_from_str(ctx, mupa_set_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_set_tests[i].res);
+		mupa = mupa_set_tests[i].fn(mupa, set);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
+		isl_multi_union_pw_aff_free(mupa);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_union_set objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_union_set *uset);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_uset_tests[] = {
+	{ &isl_multi_union_pw_aff_intersect_domain,
+	  "C[{ B[i,j] -> [i + 2j] }]", "{ B[i,i] }",
+	  "C[{ B[i,i] -> [3i] }]" },
+	{ &isl_multi_union_pw_aff_intersect_domain,
+	  "(C[] : { B[i,j] })", "{ B[i,i] }",
+	  "(C[] : { B[i,i] })" },
+	{ &isl_multi_union_pw_aff_intersect_domain,
+	  "(C[] : { B[i,j] })", "[N] -> { B[N,N] }",
+	  "[N] -> (C[] : { B[N,N] })" },
+	{ &isl_multi_union_pw_aff_intersect_domain,
+	  "C[]", "{ B[i,i] }",
+	  "(C[] : { B[i,i] })" },
+	{ &isl_multi_union_pw_aff_intersect_domain,
+	  "[N] -> (C[] : { : N >= 0 })", "{ B[i,i] }",
+	  "[N] -> (C[] : { B[i,i] : N >= 0 })" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_union_set objects.
+ */
+static int test_mupa_uset(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa, *res;
+	isl_union_set *uset;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_uset_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_uset_tests[i].arg1);
+		uset = isl_union_set_read_from_str(ctx,
+						    mupa_uset_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_uset_tests[i].res);
+		mupa = mupa_uset_tests[i].fn(mupa, uset);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
+		isl_multi_union_pw_aff_free(mupa);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_multi_aff objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_multi_aff *ma);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_ma_tests[] = {
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [i] }]",
+	  "{ C[a,b] -> D[b,a] }",
+	  "D[{ A[i,j] -> [j]; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [i]; B[i,j] -> [j] }]" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "C[{ A[i,j] -> [i] : i >= 0; B[i,j] -> [j] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [i] }]",
+	  "{ C[a,b] -> D[b,a] }",
+	  "D[{ A[i,j] -> [j] : i >= 0; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [i] : i >= 0; B[i,j] -> [j] }]" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }]",
+	  "[N] -> { C[a] -> D[a + N] }",
+	  "[N] -> D[{ A[i,j] -> [i + N]; B[i,j] -> [j + N] }] " },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "C[]",
+	  "{ C[] -> D[] }",
+	  "D[]" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ C[] -> D[] }",
+	  "[N] -> (D[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "C[]",
+	  "[N] -> { C[] -> D[N] }",
+	  "[N] -> D[{ [N] }]" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "{ C[] -> D[] }",
+	  "(D[] : { A[i,j] : i >= j })" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "[N] -> (C[] : { A[i,j] : N >= 0 })",
+	  "{ C[] -> D[] }",
+	  "[N] -> (D[] : { A[i,j] : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_apply_multi_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "[N] -> { C[] -> D[N] }",
+	  "[N] -> (D[{ A[i,j] -> [N] : i >= j }])" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_multi_aff objects.
+ */
+static int test_mupa_ma(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa, *res;
+	isl_multi_aff *ma;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_ma_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_ma_tests[i].arg1);
+		ma = isl_multi_aff_read_from_str(ctx, mupa_ma_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_ma_tests[i].res);
+		mupa = mupa_ma_tests[i].fn(mupa, ma);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
+		isl_multi_union_pw_aff_free(mupa);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_pw_aff objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_pw_aff *pa);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_pa_tests[] = {
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }]",
+	  "[N] -> { C[a] -> [a + N] }",
+	  "[N] -> { A[i,j] -> [i + N]; B[i,j] -> [j + N] }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }]",
+	  "{ C[a] -> [a] : a >= 0; C[a] -> [-a] : a < 0 }",
+	  "{ A[i,j] -> [i] : i >= 0; A[i,j] -> [-i] : i < 0; "
+	    "B[i,j] -> [j] : j >= 0; B[i,j] -> [-j] : j < 0 }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "C[]",
+	  "[N] -> { C[] -> [N] }",
+	  "[N] -> { [N] }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "C[]",
+	  "[N] -> { C[] -> [N] : N >= 0; C[] -> [-N] : N < 0 }",
+	  "[N] -> { [N] : N >= 0; [-N] : N < 0 }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "[N] -> { C[] -> [N] }",
+	  "[N] -> { [N] : N >= 0 }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "[N] -> { C[] -> [N] : N >= 0; C[] -> [-N] : N < 0 }",
+	  "[N] -> { [N] : N >= 0 }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ C[] -> [0] }",
+	  "[N] -> { [0] : N >= 0 }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "[N] -> { C[] -> [N] }",
+	  "[N] -> { A[i,j] -> [N] : i >= j }" },
+	{ &isl_multi_union_pw_aff_apply_pw_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "[N] -> { C[] -> [N] : N >= 0 }",
+	  "[N] -> { A[i,j] -> [N] : i >= j and N >= 0 }" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_pw_aff objects.
+ */
+static int test_mupa_pa(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa;
+	isl_union_pw_aff *upa, *res;
+	isl_pw_aff *pa;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_pa_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_pa_tests[i].arg1);
+		pa = isl_pw_aff_read_from_str(ctx, mupa_pa_tests[i].arg2);
+		res = isl_union_pw_aff_read_from_str(ctx,
+						    mupa_pa_tests[i].res);
+		upa = mupa_pa_tests[i].fn(mupa, pa);
+		ok = isl_union_pw_aff_plain_is_equal(upa, res);
+		isl_union_pw_aff_free(upa);
+		isl_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_pw_multi_aff objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_pw_multi_aff *pma);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_pma_tests[] = {
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [i] }]",
+	  "{ C[a,b] -> D[b,a] }",
+	  "D[{ A[i,j] -> [j]; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [i]; B[i,j] -> [j] }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[{ A[i,j] -> [i] : i >= 0; B[i,j] -> [j] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [i] }]",
+	  "{ C[a,b] -> D[b,a] }",
+	  "D[{ A[i,j] -> [j] : i >= 0; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [i] : i >= 0; B[i,j] -> [j] }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }]",
+	  "[N] -> { C[a] -> D[a + N] }",
+	  "[N] -> D[{ A[i,j] -> [i + N]; B[i,j] -> [j + N] }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }]",
+	  "{ C[a] -> D[a] : a >= 0; C[a] -> D[-a] : a < 0 }",
+	  "D[{ A[i,j] -> [i] : i >= 0; A[i,j] -> [-i] : i < 0; "
+	      "B[i,j] -> [j] : j >= 0; B[i,j] -> [-j] : j < 0 }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[{ A[i,j] -> [i]; B[i,j] -> [j] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [i] }]",
+	  "{ C[a,b] -> D[a,b] : a >= b; C[a,b] -> D[b,a] : a < b }",
+	  "D[{ A[i,j] -> [i] : i >= j; A[i,j] -> [j] : i < j; "
+	      "B[i,j] -> [j] : i <= j; B[i,j] -> [i] : i > j }, "
+	    "{ A[i,j] -> [j] : i >= j; A[i,j] -> [i] : i < j; "
+	      "B[i,j] -> [i] : i <= j; B[i,j] -> [j] : i > j }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[]",
+	  "{ C[] -> D[] }",
+	  "D[]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ C[] -> D[] }",
+	  "[N] -> (D[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[]",
+	  "[N] -> { C[] -> D[N] }",
+	  "[N] -> D[{ [N] }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "{ C[] -> D[] }",
+	  "(D[] : { A[i,j] : i >= j })" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "[N] -> (C[] : { A[i,j] : N >= 0 })",
+	  "{ C[] -> D[] }",
+	  "[N] -> (D[] : { A[i,j] : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "[N] -> { C[] -> D[N] }",
+	  "[N] -> (D[{ A[i,j] -> [N] : i >= j }])" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "C[]",
+	  "[N] -> { C[] -> D[N] : N >= 0; C[] -> D[-N] : N < 0 }",
+	  "[N] -> D[{ [N] : N >= 0; [-N] : N < 0 }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "[N] -> { C[] -> D[N] }",
+	  "[N] -> D[{ [N] : N >= 0 }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "[N] -> { C[] -> D[N] : N >= 0; C[] -> D[-N] : N < 0 }",
+	  "[N] -> D[{ [N] : N >= 0 }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ C[] -> D[0] }",
+	  "[N] -> D[{ [0] : N >= 0 }]" },
+	{ &isl_multi_union_pw_aff_apply_pw_multi_aff,
+	  "(C[] : { A[i,j] : i >= j })",
+	  "[N] -> { C[] -> D[N] : N >= 0 }",
+	  "[N] -> D[{ A[i,j] -> [N] : i >= j and N >= 0 }]" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_pw_multi_aff objects.
+ */
+static int test_mupa_pma(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa, *res;
+	isl_pw_multi_aff *pma;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_pma_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_pma_tests[i].arg1);
+		pma = isl_pw_multi_aff_read_from_str(ctx,
+						    mupa_pma_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_pma_tests[i].res);
+		mupa = mupa_pma_tests[i].fn(mupa, pma);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
+		isl_multi_union_pw_aff_free(mupa);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_union_pw_multi_aff objects.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_multi_union_pw_aff *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa,
+		__isl_take isl_union_pw_multi_aff *upma);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} mupa_upma_tests[] = {
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[{ B[i,j] -> [i + 2j] }]", "{ A[a,b] -> B[b,a] }",
+	  "C[{ A[a,b] -> [b + 2a] }]" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[{ B[i,j] -> [i + 2j] }]",
+	  "{ A[a,b] -> B[b,a] : b > a }",
+	  "C[{ A[a,b] -> [b + 2a] : b > a }]" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[{ B[i,j] -> [i + 2j] : j > 4 }]",
+	  "{ A[a,b] -> B[b,a] : b > a }",
+	  "C[{ A[a,b] -> [b + 2a] : b > a > 4 }]" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[{ B[i,j] -> [i + 2j] }]",
+	  "{ A[a,b] -> B[b,a] : a > b; A[a,b] -> B[a,b] : a <= b }",
+	  "C[{ A[a,b] -> [b + 2a] : a > b; A[a,b] -> [a + 2b] : a <= b }]" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "(C[] : { B[a,b] })",
+	  "{ A[a,b] -> B[b,a] }",
+	  "(C[] : { A[a,b] })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "(C[] : { B[a,b] })",
+	  "{ B[a,b] -> A[b,a] }",
+	  "(C[] : { })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "(C[] : { B[a,b] })",
+	  "{ A[a,b] -> B[b,a] : a > b }",
+	  "(C[] : { A[a,b] : a > b })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "(C[] : { B[a,b] : a > b })",
+	  "{ A[a,b] -> B[b,a] }",
+	  "(C[] : { A[a,b] : b > a })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "[N] -> (C[] : { B[a,b] : a > N })",
+	  "{ A[a,b] -> B[b,a] : a > b }",
+	  "[N] -> (C[] : { A[a,b] : a > b > N })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "(C[] : { B[a,b] : a > b })",
+	  "[N] -> { A[a,b] -> B[b,a] : a > N }",
+	  "[N] -> (C[] : { A[a,b] : b > a > N })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[]",
+	  "{ A[a,b] -> B[b,a] }",
+	  "C[]" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "[N] -> (C[] : { : N >= 0 })",
+	  "{ A[a,b] -> B[b,a] }",
+	  "[N] -> (C[] : { : N >= 0 })" },
+	{ &isl_multi_union_pw_aff_pullback_union_pw_multi_aff,
+	  "C[]",
+	  "[N] -> { A[a,b] -> B[b,a] : N >= 0 }",
+	  "[N] -> (C[] : { : N >= 0 })" },
+};
+
+/* Perform some basic tests of binary operations on
+ * pairs of isl_multi_union_pw_aff and isl_union_pw_multi_aff objects.
+ */
+static int test_mupa_upma(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_multi_union_pw_aff *mupa, *res;
+	isl_union_pw_multi_aff *upma;
+
+	for (i = 0; i < ARRAY_SIZE(mupa_upma_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_upma_tests[i].arg1);
+		upma = isl_union_pw_multi_aff_read_from_str(ctx,
+						    mupa_upma_tests[i].arg2);
+		res = isl_multi_union_pw_aff_read_from_str(ctx,
+						    mupa_upma_tests[i].res);
+		mupa = mupa_upma_tests[i].fn(mupa, upma);
+		ok = isl_multi_union_pw_aff_plain_is_equal(mupa, res);
+		isl_multi_union_pw_aff_free(mupa);
+		isl_multi_union_pw_aff_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+int test_aff(isl_ctx *ctx)
+{
+	const char *str;
+	isl_set *set;
+	isl_space *space;
+	isl_local_space *ls;
+	isl_aff *aff;
+	int zero, equal;
+
+	if (test_upa(ctx) < 0)
+		return -1;
+	if (test_bin_aff(ctx) < 0)
+		return -1;
+	if (test_bin_pw_aff(ctx) < 0)
+		return -1;
+	if (test_bin_upma(ctx) < 0)
+		return -1;
+	if (test_bin_upma_fail(ctx) < 0)
+		return -1;
+	if (test_un_mpa(ctx) < 0)
+		return -1;
+	if (test_bin_mpa(ctx) < 0)
+		return -1;
+	if (test_un_mupa(ctx) < 0)
+		return -1;
+	if (test_bin_mupa(ctx) < 0)
+		return -1;
+	if (test_mupa_set(ctx) < 0)
+		return -1;
+	if (test_mupa_uset(ctx) < 0)
+		return -1;
+	if (test_mupa_ma(ctx) < 0)
+		return -1;
+	if (test_mupa_pa(ctx) < 0)
+		return -1;
+	if (test_mupa_pma(ctx) < 0)
+		return -1;
+	if (test_mupa_upma(ctx) < 0)
+		return -1;
+
+	space = isl_space_set_alloc(ctx, 0, 1);
+	ls = isl_local_space_from_space(space);
+	aff = isl_aff_zero_on_domain(ls);
+
+	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
+	aff = isl_aff_scale_down_ui(aff, 3);
+	aff = isl_aff_floor(aff);
+	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
+	aff = isl_aff_scale_down_ui(aff, 2);
+	aff = isl_aff_floor(aff);
+	aff = isl_aff_add_coefficient_si(aff, isl_dim_in, 0, 1);
+
+	str = "{ [10] }";
+	set = isl_set_read_from_str(ctx, str);
+	aff = isl_aff_gist(aff, set);
+
+	aff = isl_aff_add_constant_si(aff, -16);
+	zero = isl_aff_plain_is_zero(aff);
+	isl_aff_free(aff);
+
+	if (zero < 0)
+		return -1;
+	if (!zero)
+		isl_die(ctx, isl_error_unknown, "unexpected result", return -1);
+
+	aff = isl_aff_read_from_str(ctx, "{ [-1] }");
+	aff = isl_aff_scale_down_ui(aff, 64);
+	aff = isl_aff_floor(aff);
+	equal = aff_check_plain_equal(aff, "{ [-1] }");
+	isl_aff_free(aff);
+	if (equal < 0)
+		return -1;
+
+	return 0;
+}
+
+/* Check that "pa" consists of a single expression.
  */
 static int check_single_piece(isl_ctx *ctx, __isl_take isl_pw_aff *pa)
 {
@@ -5466,6 +6600,167 @@ int test_union_pw(isl_ctx *ctx)
 	return 0;
 }
 
+/* Inputs for basic tests of functions that select
+ * subparts of the domain of an isl_multi_union_pw_aff.
+ * "fn" is the function that is tested.
+ * "arg" is a string description of the input.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_union_set *(*fn)(
+		__isl_take isl_multi_union_pw_aff *mupa);
+	const char *arg;
+	const char *res;
+} un_locus_tests[] = {
+	{ &isl_multi_union_pw_aff_zero_union_set,
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }]",
+	  "{ A[0,j]; B[0,j] }" },
+	{ &isl_multi_union_pw_aff_zero_union_set,
+	  "F[{ A[i,j] -> [i-j]; B[i,j] -> [i-j] : i >= 0 }]",
+	  "{ A[i,i]; B[i,i] : i >= 0 }" },
+	{ &isl_multi_union_pw_aff_zero_union_set,
+	  "(F[] : { A[i,j]; B[i,i] : i >= 0 })",
+	  "{ A[i,j]; B[i,i] : i >= 0 }" },
+};
+
+/* Perform some basic tests of functions that select
+ * subparts of the domain of an isl_multi_union_pw_aff.
+ */
+static int test_un_locus(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_union_set *uset, *res;
+	isl_multi_union_pw_aff *mupa;
+
+	for (i = 0; i < ARRAY_SIZE(un_locus_tests); ++i) {
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    un_locus_tests[i].arg);
+		res = isl_union_set_read_from_str(ctx, un_locus_tests[i].res);
+		uset = un_locus_tests[i].fn(mupa);
+		ok = isl_union_set_is_equal(uset, res);
+		isl_union_set_free(uset);
+		isl_union_set_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Inputs for basic tests of functions that select
+ * subparts of an isl_union_map based on a relation
+ * specified by an isl_multi_union_pw_aff.
+ * "fn" is the function that is tested.
+ * "arg1" and "arg2" are string descriptions of the inputs.
+ * "res" is a string description of the expected result.
+ */
+struct {
+	__isl_give isl_union_map *(*fn)(
+		__isl_take isl_union_map *umap,
+		__isl_take isl_multi_union_pw_aff *mupa);
+	const char *arg1;
+	const char *arg2;
+	const char *res;
+} bin_locus_tests[] = {
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }]",
+	  "{ A[i,j] -> B[i,j'] }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [j] }]",
+	  "{ A[i,j] -> B[i,j] }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j']; A[i,j] -> C[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }]",
+	  "{ A[i,j] -> B[i,j'] }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j']; A[i,j] -> C[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i]; C[i,j] -> [0] }]",
+	  "{ A[i,j] -> B[i,j']; A[0,j] -> C[i',j'] }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "F[{ A[i,j] -> [i] : i > j; B[i,j] -> [i] }]",
+	  "{ A[i,j] -> B[i,j'] : i > j }" },
+	{ &isl_union_map_lex_lt_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [j] }]",
+	  "{ A[i,j] -> B[i',j'] : i,j << i',j' }" },
+	{ &isl_union_map_lex_gt_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "F[{ A[i,j] -> [i]; B[i,j] -> [i] }, "
+	    "{ A[i,j] -> [j]; B[i,j] -> [j] }]",
+	  "{ A[i,j] -> B[i',j'] : i,j >> i',j' }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j']; A[i,j] -> C[i',j'] }",
+	  "(F[] : { A[i,j]; B[i,j] })",
+	  "{ A[i,j] -> B[i',j'] }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "(F[] : { A[i,j] : i > j; B[i,j] : i < j })",
+	  "{ A[i,j] -> B[i',j'] : i > j and i' < j' }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "[N] -> { A[i,j] -> B[i',j'] : i,i' <= N }",
+	  "(F[] : { A[i,j] : i > j; B[i,j] : i < j })",
+	  "[N] -> { A[i,j] -> B[i',j'] : i > j and i' < j' and i,i' <= N }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "[N] -> (F[] : { A[i,j] : i < N; B[i,j] : i < N })",
+	  "[N] -> { A[i,j] -> B[i',j'] : i,i' < N }" },
+	{ &isl_union_map_eq_at_multi_union_pw_aff,
+	  "{ A[i,j] -> B[i',j'] }",
+	  "[N] -> (F[] : { : N >= 0 })",
+	  "[N] -> { A[i,j] -> B[i',j'] : N >= 0 }" },
+};
+
+/* Perform some basic tests of functions that select
+ * subparts of an isl_union_map based on a relation
+ * specified by an isl_multi_union_pw_aff.
+ */
+static int test_bin_locus(isl_ctx *ctx)
+{
+	int i;
+	isl_bool ok;
+	isl_union_map *umap, *res;
+	isl_multi_union_pw_aff *mupa;
+
+	for (i = 0; i < ARRAY_SIZE(bin_locus_tests); ++i) {
+		umap = isl_union_map_read_from_str(ctx,
+						    bin_locus_tests[i].arg1);
+		mupa = isl_multi_union_pw_aff_read_from_str(ctx,
+						    bin_locus_tests[i].arg2);
+		res = isl_union_map_read_from_str(ctx, bin_locus_tests[i].res);
+		umap = bin_locus_tests[i].fn(umap, mupa);
+		ok = isl_union_map_is_equal(umap, res);
+		isl_union_map_free(umap);
+		isl_union_map_free(res);
+		if (ok < 0)
+			return -1;
+		if (!ok)
+			isl_die(ctx, isl_error_unknown,
+				"unexpected result", return -1);
+	}
+
+	return 0;
+}
+
+/* Perform basic locus tests.
+ */
+static int test_locus(isl_ctx *ctx)
+{
+	if (test_un_locus(ctx) < 0)
+		return -1;
+	if (test_bin_locus(ctx) < 0)
+		return -1;
+	return 0;
+}
+
 /* Test that isl_union_pw_qpolynomial_eval picks up the function
  * defined over the correct domain space.
  */
@@ -5523,7 +6818,67 @@ static int test_eval_2(isl_ctx *ctx)
 	return 0;
 }
 
-/* Perform basic polynomial evaluation tests.
+/* Inputs for isl_pw_aff_eval test.
+ * "f" is the affine function.
+ * "p" is the point where the function should be evaluated.
+ * "res" is the expected result.
+ */
+struct {
+	const char *f;
+	const char *p;
+	const char *res;
+} aff_eval_tests[] = {
+	{ "{ [i] -> [2 * i] }", "{ [4] }", "8" },
+	{ "{ [i] -> [2 * i] }", "{ [x] : false }", "NaN" },
+	{ "{ [i] -> [i + floor(i/2) + floor(i/3)] }", "{ [0] }", "0" },
+	{ "{ [i] -> [i + floor(i/2) + floor(i/3)] }", "{ [1] }", "1" },
+	{ "{ [i] -> [i + floor(i/2) + floor(i/3)] }", "{ [2] }", "3" },
+	{ "{ [i] -> [i + floor(i/2) + floor(i/3)] }", "{ [3] }", "5" },
+	{ "{ [i] -> [i + floor(i/2) + floor(i/3)] }", "{ [4] }", "7" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [0] }", "0" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [1] }", "0" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [2] }", "0" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [3] }", "0" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [4] }", "1" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [6] }", "1" },
+	{ "{ [i] -> [floor((3 * floor(i/2))/5)] }", "{ [8] }", "2" },
+	{ "{ [i] -> [i] : i > 0; [i] -> [-i] : i < 0 }", "{ [4] }", "4" },
+	{ "{ [i] -> [i] : i > 0; [i] -> [-i] : i < 0 }", "{ [-2] }", "2" },
+	{ "{ [i] -> [i] : i > 0; [i] -> [-i] : i < 0 }", "{ [0] }", "NaN" },
+	{ "[N] -> { [2 * N] }", "[N] -> { : N = 4 }", "8" },
+	{ "{ [i, j] -> [(i + j)/2] }", "{ [1, 1] }", "1" },
+	{ "{ [i, j] -> [(i + j)/2] }", "{ [1, 2] }", "3/2" },
+	{ "{ [i] -> [i] : i mod 2 = 0 }", "{ [4] }", "4" },
+	{ "{ [i] -> [i] : i mod 2 = 0 }", "{ [3] }", "NaN" },
+	{ "{ [i] -> [i] : i mod 2 = 0 }", "{ [x] : false }", "NaN" },
+};
+
+/* Perform basic isl_pw_aff_eval tests.
+ */
+static int test_eval_aff(isl_ctx *ctx)
+{
+	int i;
+
+	for (i = 0; i < ARRAY_SIZE(aff_eval_tests); ++i) {
+		isl_stat r;
+		isl_pw_aff *pa;
+		isl_set *set;
+		isl_point *pnt;
+		isl_val *v;
+
+		pa = isl_pw_aff_read_from_str(ctx, aff_eval_tests[i].f);
+		set = isl_set_read_from_str(ctx, aff_eval_tests[i].p);
+		pnt = isl_set_sample_point(set);
+		v = isl_pw_aff_eval(pa, pnt);
+		r = val_check_equal(v, aff_eval_tests[i].res);
+		isl_val_free(v);
+		if (r < 0)
+			return -1;
+	}
+	return 0;
+}
+
+/* Perform basic evaluation tests.
  */
 static int test_eval(isl_ctx *ctx)
 {
@@ -5531,6 +6886,8 @@ static int test_eval(isl_ctx *ctx)
 		return -1;
 	if (test_eval_2(ctx) < 0)
 		return -1;
+	if (test_eval_aff(ctx) < 0)
+		return -1;
 	return 0;
 }
 
@@ -5936,12 +7293,106 @@ static int test_map_conversion(isl_ctx *
 	return 0;
 }
 
+/* Descriptions of isl_pw_multi_aff objects for testing conversion
+ * to isl_multi_pw_aff and back.
+ */
+const char *mpa_conversion_tests[] = {
+	"{ [x] -> A[x] }",
+	"{ [x] -> A[x] : x >= 0 }",
+	"{ [x] -> A[x] : x >= 0; [x] -> A[-x] : x < 0 }",
+	"{ [x] -> A[x, x + 1] }",
+	"{ [x] -> A[] }",
+	"{ [x] -> A[] : x >= 0 }",
+};
+
+/* Check that conversion from isl_pw_multi_aff to isl_multi_pw_aff and
+ * back to isl_pw_multi_aff preserves the original meaning.
+ */
+static int test_mpa_conversion(isl_ctx *ctx)
+{
+	int i;
+	isl_pw_multi_aff *pma1, *pma2;
+	isl_multi_pw_aff *mpa;
+	int equal;
+
+	for (i = 0; i < ARRAY_SIZE(mpa_conversion_tests); ++i) {
+		const char *str;
+		str = mpa_conversion_tests[i];
+		pma1 = isl_pw_multi_aff_read_from_str(ctx, str);
+		pma2 = isl_pw_multi_aff_copy(pma1);
+		mpa = isl_multi_pw_aff_from_pw_multi_aff(pma1);
+		pma1 = isl_pw_multi_aff_from_multi_pw_aff(mpa);
+		equal = isl_pw_multi_aff_plain_is_equal(pma1, pma2);
+		isl_pw_multi_aff_free(pma1);
+		isl_pw_multi_aff_free(pma2);
+
+		if (equal < 0)
+			return -1;
+		if (!equal)
+			isl_die(ctx, isl_error_unknown, "bad conversion",
+				return -1);
+	}
+
+	return 0;
+}
+
+/* Descriptions of union maps that should be convertible
+ * to an isl_multi_union_pw_aff.
+ */
+const char *umap_mupa_conversion_tests[] = {
+	"{ [a, b, c, d] -> s0[a, b, e, f] : "
+	    "exists (e0 = [(a - 2c)/3], e1 = [(-4 + b - 5d)/9], "
+	    "e2 = [(-d + f)/9]: 3e0 = a - 2c and 9e1 = -4 + b - 5d and "
+	    "9e2 = -d + f and f >= 0 and f <= 8 and 9e >= -5 - 2a and "
+	    "9e <= -2 - 2a) }",
+	"{ [a, b] -> [c] : exists (e0 = floor((-a - b + c)/5): "
+	    "5e0 = -a - b + c and c >= -a and c <= 4 - a) }",
+	"{ [a, b] -> [c] : exists d : 18 * d = -3 - a + 2c and 1 <= c <= 3 }",
+	"{ A[] -> B[0]; C[] -> B[1] }",
+	"{ A[] -> B[]; C[] -> B[] }",
+};
+
+/* Check that converting from isl_union_map to isl_multi_union_pw_aff and back
+ * to isl_union_map produces the original isl_union_map.
+ */
+static int test_union_map_mupa_conversion(isl_ctx *ctx)
+{
+	int i;
+	isl_union_map *umap1, *umap2;
+	isl_multi_union_pw_aff *mupa;
+	int equal;
+
+	for (i = 0; i < ARRAY_SIZE(umap_mupa_conversion_tests); ++i) {
+		const char *str;
+		str = umap_mupa_conversion_tests[i];
+		umap1 = isl_union_map_read_from_str(ctx, str);
+		umap2 = isl_union_map_copy(umap1);
+		mupa = isl_multi_union_pw_aff_from_union_map(umap2);
+		umap2 = isl_union_map_from_multi_union_pw_aff(mupa);
+		equal = isl_union_map_is_equal(umap1, umap2);
+		isl_union_map_free(umap1);
+		isl_union_map_free(umap2);
+
+		if (equal < 0)
+			return -1;
+		if (!equal)
+			isl_die(ctx, isl_error_unknown, "bad conversion",
+				return -1);
+	}
+
+	return 0;
+}
+
 static int test_conversion(isl_ctx *ctx)
 {
 	if (test_set_conversion(ctx) < 0)
 		return -1;
 	if (test_map_conversion(ctx) < 0)
 		return -1;
+	if (test_mpa_conversion(ctx) < 0)
+		return -1;
+	if (test_union_map_mupa_conversion(ctx) < 0)
+		return -1;
 	return 0;
 }
 
@@ -6674,7 +8125,7 @@ static int test_pw_multi_aff(isl_ctx *ct
 /* Check that we can properly parse multi piecewise affine expressions
  * where the piecewise affine expressions have different domains.
  */
-static int test_multi_pw_aff(isl_ctx *ctx)
+static int test_multi_pw_aff_1(isl_ctx *ctx)
 {
 	const char *str;
 	isl_set *dom, *dom2;
@@ -6719,6 +8170,61 @@ static int test_multi_pw_aff(isl_ctx *ct
 	return 0;
 }
 
+/* Check that the dimensions in the explicit domain
+ * of a multi piecewise affine expression are properly
+ * taken into account.
+ */
+static int test_multi_pw_aff_2(isl_ctx *ctx)
+{
+	const char *str;
+	isl_bool involves1, involves2, involves3, equal;
+	isl_multi_pw_aff *mpa, *mpa1, *mpa2;
+
+	str = "{ A[x,y] -> B[] : x >= y }";
+	mpa = isl_multi_pw_aff_read_from_str(ctx, str);
+	involves1 = isl_multi_pw_aff_involves_dims(mpa, isl_dim_in, 0, 2);
+	mpa1 = isl_multi_pw_aff_copy(mpa);
+
+	mpa = isl_multi_pw_aff_insert_dims(mpa, isl_dim_in, 0, 1);
+	involves2 = isl_multi_pw_aff_involves_dims(mpa, isl_dim_in, 0, 1);
+	involves3 = isl_multi_pw_aff_involves_dims(mpa, isl_dim_in, 1, 2);
+	str = "{ [a,x,y] -> B[] : x >= y }";
+	mpa2 = isl_multi_pw_aff_read_from_str(ctx, str);
+	equal = isl_multi_pw_aff_plain_is_equal(mpa, mpa2);
+	isl_multi_pw_aff_free(mpa2);
+
+	mpa = isl_multi_pw_aff_drop_dims(mpa, isl_dim_in, 0, 1);
+	mpa = isl_multi_pw_aff_set_tuple_name(mpa, isl_dim_in, "A");
+	if (equal >= 0 && equal)
+		equal = isl_multi_pw_aff_plain_is_equal(mpa, mpa1);
+	isl_multi_pw_aff_free(mpa1);
+	isl_multi_pw_aff_free(mpa);
+
+	if (involves1 < 0 || involves2 < 0 || involves3 < 0 || equal < 0)
+		return -1;
+	if (!equal)
+		isl_die(ctx, isl_error_unknown,
+			"incorrect result of dimension insertion/removal",
+			return isl_stat_error);
+	if (!involves1 || involves2 || !involves3)
+		isl_die(ctx, isl_error_unknown,
+			"incorrect characterization of involved dimensions",
+			return isl_stat_error);
+
+	return 0;
+}
+
+/* Perform some tests on multi piecewise affine expressions.
+ */
+static int test_multi_pw_aff(isl_ctx *ctx)
+{
+	if (test_multi_pw_aff_1(ctx) < 0)
+		return -1;
+	if (test_multi_pw_aff_2(ctx) < 0)
+		return -1;
+	return 0;
+}
+
 /* This is a regression test for a bug where isl_basic_map_simplify
  * would end up in an infinite loop.  In particular, we construct
  * an empty basic set that is not obviously empty.
@@ -6861,6 +8367,50 @@ static int test_schedule_tree(isl_ctx *c
 	return 0;
 }
 
+/* Check that a zero-dimensional prefix schedule keeps track
+ * of the domain and outer filters.
+ */
+static int test_schedule_tree_prefix(isl_ctx *ctx)
+{
+	const char *str;
+	isl_bool equal;
+	isl_union_set *uset;
+	isl_union_set_list *filters;
+	isl_multi_union_pw_aff *mupa, *mupa2;
+	isl_schedule_node *node;
+
+	str = "{ S1[i,j] : 0 <= i,j < 10; S2[i,j] : 0 <= i,j < 10 }";
+	uset = isl_union_set_read_from_str(ctx, str);
+	node = isl_schedule_node_from_domain(uset);
+	node = isl_schedule_node_child(node, 0);
+
+	str = "{ S1[i,j] : i > j }";
+	uset = isl_union_set_read_from_str(ctx, str);
+	filters = isl_union_set_list_from_union_set(uset);
+	str = "{ S1[i,j] : i <= j; S2[i,j] }";
+	uset = isl_union_set_read_from_str(ctx, str);
+	filters = isl_union_set_list_add(filters, uset);
+	node = isl_schedule_node_insert_sequence(node, filters);
+
+	node = isl_schedule_node_child(node, 0);
+	node = isl_schedule_node_child(node, 0);
+	mupa = isl_schedule_node_get_prefix_schedule_multi_union_pw_aff(node);
+	str = "([] : { S1[i,j] : i > j })";
+	mupa2 = isl_multi_union_pw_aff_read_from_str(ctx, str);
+	equal = isl_multi_union_pw_aff_plain_is_equal(mupa, mupa2);
+	isl_multi_union_pw_aff_free(mupa2);
+	isl_multi_union_pw_aff_free(mupa);
+	isl_schedule_node_free(node);
+
+	if (equal < 0)
+		return -1;
+	if (!equal)
+		isl_die(ctx, isl_error_unknown, "unexpected prefix schedule",
+			return -1);
+
+	return 0;
+}
+
 /* Check that the reaching domain elements and the prefix schedule
  * at a leaf node are the same before and after grouping.
  */
@@ -7382,9 +8932,11 @@ struct {
 	{ "schedule (whole component)", &test_schedule_whole },
 	{ "schedule (incremental)", &test_schedule_incremental },
 	{ "schedule tree", &test_schedule_tree },
+	{ "schedule tree prefix", &test_schedule_tree_prefix },
 	{ "schedule tree grouping", &test_schedule_tree_group },
 	{ "tile", &test_tile },
 	{ "union_pw", &test_union_pw },
+	{ "locus", &test_locus },
 	{ "eval", &test_eval },
 	{ "parse", &test_parse },
 	{ "single-valued", &test_sv },

Modified: polly/trunk/lib/External/isl/isl_union_eval.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_union_eval.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_union_eval.c (original)
+++ polly/trunk/lib/External/isl/isl_union_eval.c Sat Apr 21 01:34:22 2018
@@ -10,6 +10,20 @@
 
 #include <isl_union_macro.h>
 
+/* Evaluate "u" in the void point "pnt".
+ * In particular, return the value NaN.
+ */
+static __isl_give isl_val *FN(UNION,eval_void)(__isl_take UNION *u,
+	__isl_take isl_point *pnt)
+{
+	isl_ctx *ctx;
+
+	ctx = isl_point_get_ctx(pnt);
+	FN(UNION,free)(u);
+	isl_point_free(pnt);
+	return isl_val_nan(ctx);
+}
+
 /* Is the domain space of "entry" equal to "space"?
  */
 static int FN(UNION,has_domain_space)(const void *entry, const void *val)
@@ -29,11 +43,17 @@ __isl_give isl_val *FN(UNION,eval)(__isl
 {
 	uint32_t hash;
 	struct isl_hash_table_entry *entry;
+	isl_bool is_void;
 	isl_space *space;
 	isl_val *v;
 
 	if (!u || !pnt)
 		goto error;
+	is_void = isl_point_is_void(pnt);
+	if (is_void < 0)
+		goto error;
+	if (is_void)
+		return FN(UNION,eval_void)(u, pnt);
 
 	space = isl_space_copy(pnt->dim);
 	if (!space)

Modified: polly/trunk/lib/External/isl/isl_union_map.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_union_map.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_union_map.c (original)
+++ polly/trunk/lib/External/isl/isl_union_map.c Sat Apr 21 01:34:22 2018
@@ -13,12 +13,11 @@
  * B.P. 105 - 78153 Le Chesnay, France
  */
 
-#define ISL_DIM_H
 #include <isl_map_private.h>
 #include <isl_union_map_private.h>
 #include <isl/ctx.h>
 #include <isl/hash.h>
-#include <isl/aff.h>
+#include <isl_aff_private.h>
 #include <isl/map.h>
 #include <isl/set.h>
 #include <isl_space_private.h>
@@ -29,6 +28,7 @@
 #include <set_to_map.c>
 #include <set_from_map.c>
 #include <uset_to_umap.c>
+#include <uset_from_umap.c>
 
 /* Return the number of parameters of "umap", where "type"
  * is required to be set to isl_dim_param.
@@ -88,6 +88,15 @@ isl_bool isl_union_set_is_params(__isl_k
 	return params;
 }
 
+/* Is this union map actually a parameter domain?
+ * Users should never call this function.  Outside of isl,
+ * a union map can never be a parameter domain.
+ */
+isl_bool isl_union_map_is_params(__isl_keep isl_union_map *umap)
+{
+	return isl_union_set_is_params(uset_from_umap(umap));
+}
+
 static __isl_give isl_union_map *isl_union_map_alloc(
 	__isl_take isl_space *space, int size)
 {
@@ -3783,6 +3792,85 @@ __isl_give isl_union_map *isl_union_map_
 	return data.res;
 }
 
+/* Check that "umap" and "space" have the same number of parameters.
+ */
+static isl_stat check_union_map_space_equal_dim(__isl_keep isl_union_map *umap,
+	__isl_keep isl_space *space)
+{
+	unsigned dim1, dim2;
+
+	if (!umap || !space)
+		return isl_stat_error;
+	dim1 = isl_union_map_dim(umap, isl_dim_param);
+	dim2 = isl_space_dim(space, isl_dim_param);
+	if (dim1 == dim2)
+		return isl_stat_ok;
+	isl_die(isl_union_map_get_ctx(umap), isl_error_invalid,
+		"number of parameters does not match", return isl_stat_error);
+}
+
+/* Internal data structure for isl_union_map_reset_equal_dim_space.
+ * "space" is the target space.
+ * "res" collects the results.
+ */
+struct isl_union_map_reset_params_data {
+	isl_space *space;
+	isl_union_map *res;
+};
+
+/* Replace the parameters of "map" by those of data->space and
+ * add the result to data->res.
+ */
+static isl_stat reset_params(__isl_take isl_map *map, void *user)
+{
+	struct isl_union_map_reset_params_data *data = user;
+	isl_space *space;
+
+	space = isl_map_get_space(map);
+	space = isl_space_replace_params(space, data->space);
+	map = isl_map_reset_equal_dim_space(map, space);
+	data->res = isl_union_map_add_map(data->res, map);
+
+	return data->res ? isl_stat_ok : isl_stat_error;
+}
+
+/* Replace the space of "umap" by "space", without modifying
+ * the dimension of "umap", i.e., the number of parameters of "umap".
+ *
+ * Since the hash values of the maps in the union map depend
+ * on the parameters, a new union map needs to be constructed.
+ */
+__isl_give isl_union_map *isl_union_map_reset_equal_dim_space(
+	__isl_take isl_union_map *umap, __isl_take isl_space *space)
+{
+	struct isl_union_map_reset_params_data data = { space };
+	isl_bool equal;
+	isl_space *umap_space;
+
+	umap_space = isl_union_map_peek_space(umap);
+	equal = isl_space_is_equal(umap_space, space);
+	if (equal < 0)
+		goto error;
+	if (equal) {
+		isl_space_free(space);
+		return umap;
+	}
+	if (check_union_map_space_equal_dim(umap, space) < 0)
+		goto error;
+
+	data.res = isl_union_map_empty(isl_space_copy(space));
+	if (isl_union_map_foreach_map(umap, &reset_params, &data) < 0)
+		data.res = isl_union_map_free(data.res);
+
+	isl_space_free(space);
+	isl_union_map_free(umap);
+	return data.res;
+error:
+	isl_union_map_free(umap);
+	isl_space_free(space);
+	return NULL;
+}
+
 /* Internal data structure for isl_union_map_order_at_multi_union_pw_aff.
  * "mupa" is the function from which the isl_multi_pw_affs are extracted.
  * "order" is applied to the extracted isl_multi_pw_affs that correspond
@@ -3818,6 +3906,41 @@ static isl_stat order_at(__isl_take isl_
 	return data->res ? isl_stat_ok : isl_stat_error;
 }
 
+/* If "mupa" has a non-trivial explicit domain, then intersect
+ * domain and range of "umap" with this explicit domain.
+ * If the explicit domain only describes constraints on the parameters,
+ * then the intersection only needs to be performed once.
+ */
+static __isl_give isl_union_map *intersect_explicit_domain(
+	__isl_take isl_union_map *umap, __isl_keep isl_multi_union_pw_aff *mupa)
+{
+	isl_bool non_trivial, is_params;
+	isl_union_set *dom;
+
+	non_trivial = isl_multi_union_pw_aff_has_non_trivial_domain(mupa);
+	if (non_trivial < 0)
+		return isl_union_map_free(umap);
+	if (!non_trivial)
+		return umap;
+	mupa = isl_multi_union_pw_aff_copy(mupa);
+	dom = isl_multi_union_pw_aff_domain(mupa);
+	is_params = isl_union_set_is_params(dom);
+	if (is_params < 0) {
+		isl_union_set_free(dom);
+		return isl_union_map_free(umap);
+	}
+	if (is_params) {
+		isl_set *set;
+
+		set = isl_union_set_params(dom);
+		umap = isl_union_map_intersect_params(umap, set);
+		return umap;
+	}
+	umap = isl_union_map_intersect_domain(umap, isl_union_set_copy(dom));
+	umap = isl_union_map_intersect_range(umap, dom);
+	return umap;
+}
+
 /* Intersect each map in "umap" with the result of calling "order"
  * on the functions is "mupa" that apply to the domain and the range
  * of the map.
@@ -3833,6 +3956,7 @@ static __isl_give isl_union_map *isl_uni
 				isl_multi_union_pw_aff_get_space(mupa));
 	mupa = isl_multi_union_pw_aff_align_params(mupa,
 				isl_union_map_get_space(umap));
+	umap = intersect_explicit_domain(umap, mupa);
 	data.mupa = mupa;
 	data.order = order;
 	data.res = isl_union_map_empty(isl_union_map_get_space(umap));

Modified: polly/trunk/lib/External/isl/isl_union_map_private.h
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_union_map_private.h?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_union_map_private.h (original)
+++ polly/trunk/lib/External/isl/isl_union_map_private.h Sat Apr 21 01:34:22 2018
@@ -10,9 +10,13 @@ struct isl_union_map {
 	struct isl_hash_table	table;
 };
 
+__isl_keep isl_space *isl_union_map_peek_space(__isl_keep isl_union_map *umap);
+isl_bool isl_union_map_is_params(__isl_keep isl_union_map *umap);
 isl_bool isl_union_map_space_has_equal_params(__isl_keep isl_union_map *umap,
 	__isl_keep isl_space *space);
 isl_bool isl_union_set_space_has_equal_params(__isl_keep isl_union_set *uset,
 	__isl_keep isl_space *space);
 __isl_give isl_union_map *isl_union_map_reset_range_space(
 	__isl_take isl_union_map *umap, __isl_take isl_space *space);
+__isl_give isl_union_map *isl_union_map_reset_equal_dim_space(
+	__isl_take isl_union_map *umap, __isl_take isl_space *space);

Modified: polly/trunk/lib/External/isl/isl_union_templ.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_union_templ.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_union_templ.c (original)
+++ polly/trunk/lib/External/isl/isl_union_templ.c Sat Apr 21 01:34:22 2018
@@ -17,11 +17,20 @@ isl_ctx *FN(UNION,get_ctx)(__isl_keep UN
 	return u ? u->space->ctx : NULL;
 }
 
-__isl_give isl_space *FN(UNION,get_space)(__isl_keep UNION *u)
+/* Return the space of "u".
+ */
+static __isl_keep isl_space *FN(UNION,peek_space)(__isl_keep UNION *u)
 {
 	if (!u)
 		return NULL;
-	return isl_space_copy(u->space);
+	return u->space;
+}
+
+/* Return a copy of the space of "u".
+ */
+__isl_give isl_space *FN(UNION,get_space)(__isl_keep UNION *u)
+{
+	return isl_space_copy(FN(UNION,peek_space)(u));
 }
 
 /* Return the number of parameters of "u", where "type"
@@ -112,21 +121,8 @@ __isl_give PART *FN(FN(UNION,extract),PA
 	__isl_take isl_space *space)
 {
 	struct isl_hash_table_entry *entry;
-	isl_bool equal_params;
 
-	if (!u || !space)
-		goto error;
-	equal_params = isl_space_has_equal_params(u->space, space);
-	if (equal_params < 0)
-		goto error;
-	if (!equal_params) {
-		space = isl_space_drop_dims(space, isl_dim_param,
-					0, isl_space_dim(space, isl_dim_param));
-		space = isl_space_align_params(space,
-					FN(UNION,get_space)(u));
-		if (!space)
-			goto error;
-	}
+	space = isl_space_replace_params(space, FN(UNION,peek_space)(u));
 
 	entry = FN(UNION,find_part_entry)(u, space, 0);
 	if (!entry)

Modified: polly/trunk/lib/External/isl/isl_val.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_val.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_val.c (original)
+++ polly/trunk/lib/External/isl/isl_val.c Sat Apr 21 01:34:22 2018
@@ -1312,6 +1312,31 @@ isl_bool isl_val_gt(__isl_keep isl_val *
 	return isl_val_lt(v2, v1);
 }
 
+/* Is "v" (strictly) greater than "i"?
+ */
+isl_bool isl_val_gt_si(__isl_keep isl_val *v, long i)
+{
+	isl_val *vi;
+	isl_bool res;
+
+	if (!v)
+		return isl_bool_error;
+	if (isl_val_is_int(v))
+		return isl_int_cmp_si(v->n, i) > 0;
+	if (isl_val_is_nan(v))
+		return isl_bool_false;
+	if (isl_val_is_infty(v))
+		return isl_bool_true;
+	if (isl_val_is_neginfty(v))
+		return isl_bool_false;
+
+	vi = isl_val_int_from_si(isl_val_get_ctx(v), i);
+	res = isl_val_gt(v, vi);
+	isl_val_free(vi);
+
+	return res;
+}
+
 /* Is "v1" less than or equal to "v2"?
  */
 isl_bool isl_val_le(__isl_keep isl_val *v1, __isl_keep isl_val *v2)
@@ -1640,6 +1665,7 @@ isl_stat isl_val_check_match_domain_spac
 #define NO_IDENTITY
 #define NO_FROM_BASE
 #define NO_MOVE_DIMS
+#include <isl_multi_no_explicit_domain.c>
 #include <isl_multi_templ.c>
 #include <isl_multi_dims.c>
 
@@ -1658,8 +1684,8 @@ static __isl_give isl_multi_val *isl_mul
 		goto error;
 
 	for (i = 0; i < mv->n; ++i) {
-		mv->p[i] = fn(mv->p[i], isl_val_copy(v));
-		if (!mv->p[i])
+		mv->u.p[i] = fn(mv->u.p[i], isl_val_copy(v));
+		if (!mv->u.p[i])
 			goto error;
 	}
 

Modified: polly/trunk/lib/External/isl/isl_vec.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/isl_vec.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/isl_vec.c (original)
+++ polly/trunk/lib/External/isl/isl_vec.c Sat Apr 21 01:34:22 2018
@@ -585,6 +585,15 @@ error:
 	return NULL;
 }
 
+/* Add "n" elements at the end of "vec".
+ */
+__isl_give isl_vec *isl_vec_add_els(__isl_take isl_vec *vec, unsigned n)
+{
+	if (!vec)
+		return NULL;
+	return isl_vec_insert_els(vec, vec->size, n);
+}
+
 __isl_give isl_vec *isl_vec_insert_zero_els(__isl_take isl_vec *vec,
 	unsigned pos, unsigned n)
 {

Modified: polly/trunk/lib/External/isl/ltmain.sh
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/ltmain.sh?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/ltmain.sh (original)
+++ polly/trunk/lib/External/isl/ltmain.sh Sat Apr 21 01:34:22 2018
@@ -31,7 +31,7 @@
 
 PROGRAM=libtool
 PACKAGE=libtool
-VERSION="2.4.6 Debian-2.4.6-1"
+VERSION="2.4.6 Debian-2.4.6-2"
 package_revision=2.4.6
 
 
@@ -1977,7 +1977,7 @@ func_version ()
 # End:
 
 # Set a version string.
-scriptversion='(GNU libtool) 2.4.6 Debian-2.4.6-1'
+scriptversion='(GNU libtool) 2.4.6'
 
 
 # func_echo ARG...
@@ -2068,7 +2068,7 @@ include the following information:
        compiler:       $LTCC
        compiler flags: $LTCFLAGS
        linker:         $LD (gnu? $with_gnu_ld)
-       version:        $progname $scriptversion
+       version:        $progname $scriptversion Debian-2.4.6-2
        automake:       `($AUTOMAKE --version) 2>/dev/null |$SED 1q`
        autoconf:       `($AUTOCONF --version) 2>/dev/null |$SED 1q`
 

Added: polly/trunk/lib/External/isl/test_inputs/codegen/component7.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/test_inputs/codegen/component7.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/test_inputs/codegen/component7.c (added)
+++ polly/trunk/lib/External/isl/test_inputs/codegen/component7.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,6 @@
+{
+  S();
+  for (int c0 = 0; c0 < K; c0 += 32)
+    for (int c1 = c0; c1 <= min(K - 1, c0 + 31); c1 += 1)
+      T(c1);
+}

Added: polly/trunk/lib/External/isl/test_inputs/codegen/component7.st
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/test_inputs/codegen/component7.st?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/test_inputs/codegen/component7.st (added)
+++ polly/trunk/lib/External/isl/test_inputs/codegen/component7.st Sat Apr 21 01:34:22 2018
@@ -0,0 +1,11 @@
+# Check that component detection is not confused by values
+# of the schedule dimension that do not correspond to any statement instances.
+domain: "[K] -> { S[]; T[i] : 0 <= i < K }"
+child:
+  context: "[K] -> { [] : K > 0 }"
+  child:
+    schedule: "[K] -> [{ S[] -> [(0)]; T[i] -> [(32*floor((i)/32))] }]"
+    child:
+      sequence:
+      - filter: "[K] -> { S[] }"
+      - filter: "[K] -> { T[i] }"

Modified: polly/trunk/lib/External/isl/test_inputs/codegen/shift2.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/test_inputs/codegen/shift2.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/test_inputs/codegen/shift2.c (original)
+++ polly/trunk/lib/External/isl/test_inputs/codegen/shift2.c Sat Apr 21 01:34:22 2018
@@ -45,12 +45,9 @@ for (int c0 = 0; c0 <= 1; c0 += 1) {
     if (c1 == 0 && length % 32 == 0)
       S_4(c0);
   }
-  if (length <= 1)
-    for (int c5 = 0; c5 <= length; c5 += 1) {
-      if (c5 == length) {
-        S_4(c0);
-      } else {
-        S_0(c0, 0, 0);
-      }
-    }
+  if (length <= 1) {
+    if (length == 1)
+      S_0(c0, 0, 0);
+    S_4(c0);
+  }
 }

Modified: polly/trunk/lib/External/isl/test_inputs/codegen/stride7.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/test_inputs/codegen/stride7.c?rev=330496&r1=330495&r2=330496&view=diff
==============================================================================
--- polly/trunk/lib/External/isl/test_inputs/codegen/stride7.c (original)
+++ polly/trunk/lib/External/isl/test_inputs/codegen/stride7.c Sat Apr 21 01:34:22 2018
@@ -1,6 +1,8 @@
-for (int c0 = 2; c0 <= 200; c0 += 64) {
-  for (int c2 = c0 - 1; c2 <= 120; c2 += 1)
-    s2(c0, c2);
-  for (int c2 = 122; c2 <= c0 + 62; c2 += 1)
-    s4(c0, c2);
+{
+  for (int c0 = 2; c0 <= 100; c0 += 64)
+    for (int c2 = c0 - 1; c2 <= 120; c2 += 1)
+      s2(c0, c2);
+  for (int c0 = 66; c0 <= 200; c0 += 64)
+    for (int c2 = 122; c2 <= c0 + 62; c2 += 1)
+      s4(c0, c2);
 }

Added: polly/trunk/lib/External/isl/uset_from_umap.c
URL: http://llvm.org/viewvc/llvm-project/polly/trunk/lib/External/isl/uset_from_umap.c?rev=330496&view=auto
==============================================================================
--- polly/trunk/lib/External/isl/uset_from_umap.c (added)
+++ polly/trunk/lib/External/isl/uset_from_umap.c Sat Apr 21 01:34:22 2018
@@ -0,0 +1,8 @@
+#include <isl/union_map_type.h>
+
+/* Return the union set that was treated as the union map "umap".
+ */
+static __isl_give isl_union_set *uset_from_umap(__isl_take isl_union_map *umap)
+{
+	return (isl_union_set *) umap;
+}




More information about the llvm-commits mailing list