еще раз: поведение кода, который вы написали, в стандарте определено сложнее, чем вы себе представляете
я не претендую на експерта по знанию стандарта но существует банальная цепочка россуждений которая и приводит меня к моему представлению:
1) елементы массивов идут последовательно даже если елементом масива выступает масив
2) прибавление числа к указателю на некоторый тип смешает указатель на это число
3) разыменование указателя указываюшего на кусок памяти выделеный под вашу програму ub вызвать не способно по определению
что мы имеем с точки зрения компилятора в foo перебор некоторых указателей, на легальной области памяти, да формально мы вышли за пределы масива, он должен состоять из 5ти елементов, но дальше идет память точно так же принадлежащая нам, и компилятор не имеет ничего против, он не анализирует как ты пришел к этому адресу, его волнует только принодлежит эта память тебе или нет, а память принадлижит тебе (смотри пункт первый) так что array + i, ошибка только И ТОЛЬКО логического характера...