Hi Mikael, Am 05.07.23 um 16:54 schrieb Mikael Morin: > Here is an example, admittedly artificial.  Fails with the above change, > but fails with master as well. > > program p >   implicit none >   type t >     integer :: i >   end type t >   type u >     class(t), allocatable :: ta(:) >   end type u >   type(u), allocatable, target :: c(:) >   c = [u([t(1), t(3)]), u([t(4), t(9)])] >   call bar (allocated (c(c(1)%ta(1)%i)%ta), c(c(1)%ta(1)%i)%ta, > allocated (c(c(1)%ta(1)%i)%ta)) >   if (allocated(c(1)%ta)) stop 11 >   if (.not. allocated(c(2)%ta)) stop 12 > contains >   subroutine bar (alloc, x, alloc2) >     logical :: alloc, alloc2 >     class(t), allocatable, intent(out) :: x(:) >     if (allocated (x)) stop 1 >     if (.not. alloc)   stop 2 >     if (.not. alloc2)  stop 3 >   end subroutine bar > end while it looks artificial, it is valid, and IMHO it is a beast... I've played around and added another argument gfc_se *convse to gfc_conv_class_to_class in an attempt to implement what I thought you suggested (to get the .pre/.post separately), but in the end this did not lead to working code. And the tree-dump for your example above is beyond what I can grasp. I've noticed that my attempt does not properly handle the parmse.post; at least this is what the above example shows: there is a small part after the call to bar that should have been executed before that call, which I attribute to .post. But my attempts in moving that part regresses on a couple of testcases with class and intent(out). I am at a loss now. I am attaching the latest version of my patch to give you or Paul or others the opportunity to see what is wrong or add the missing pieces. Thanks for your help so far. Harald