It's the same example as in 6.7.3.1 of C99 spec.
EXAMPLE 3 The function parameter declarations
void h(int n, int * restrict p, int * restrict q, int * restrict r) { int i; for (i = 0; i < n; i++) p[i] = q[i] + r[i]; }
illustrate how an unmodified object can be aliased through two restricted pointers. In particular, if a and b are disjoint arrays, a call of the form h(100, a, b, b) has defined behavior, because array b is not modified within function h.
In short, it is explicitly mentioned it's defined behavior if b is not modified within function h. However, whether is it undefined behavior if a call of the form h(100, a, a, b)?
A little bit more backgrounds why I want to make it clear. There are some basic functions which we want to use in in-place or out-of-place manner. In order to reduce the effort, it is desired if we don't need to provide both h(int n, int * restrict p, int * restrict q, int * restrict r) and h_inplace(int n, int * restrict p, int * restrict q). From current observation, it seems icc and msvc can give correct result even if we call it as the form of h(100, a, a, b). However, we definitely don't want to have the risk if it is undefined behavior (which means it may be wrong from other compilers or future versions of icc and msvc). What do you think?