Deadlock during multi-coupling

Hi,
I am trying to work with an FSI problem which involves 3 participants:

  • Solid
  • Fluid1
  • Fluid2 (openfoam adapter pimplefoam)

like this:

Fluid1 talks to Solid and Fluid2. Solid talks to Fluid1 only and Fluid2 talks to Fluid1 only.

I am using multi-coupling scheme and Fluid1 is controller participant.

My problem is that, when I try to run the simulation, it sticks into a deadlock and doesn’t move ahead.

I am attching following content here:

CODE

  • code from main solver loop of Fluid1
  • code from main solver loop of Solid

it seems to me that, fluid2 and solid enters into receive and the code runs into a deadlock. The Fluid2 is using and openfoam solver: pimplefoam.

CODE:

The main sover loop for Fluid1 is:

while (interface.is_coupling_ongoing()):# and interface.is_coupling_ongoing()):
    # When an implicit coupling scheme is used, checkpointing is required
    if interface.is_action_required(action_write_iteration_checkpoint()):
        interface.mark_action_fulfilled(action_write_iteration_checkpoint())
    
    velocity, pressure, success = perform_partitioned_implicit_euler_step(
        velocity_old, pressure_old, crossSectionLength_old, crossSectionLength, dx, precice_dt, velocity_in(
            t + precice_dt), custom_coupling=True)
    interface.write_vector_data(velocityID_fluid, vertexIDs_fluid1tofluid2, [0.0, 0.0, velocity[-1]])
    pressure_solid_send = pressure[0:51]
    interface.write_block_scalar_data(pressureID_solid, vertexIDs_fluid1tosolid, pressure_solid_send)

    interface.advance(precice_dt)
    
    pressure[-1] = interface.read_scalar_data(pressureID_fluid, vertexIDs_fluid1tofluid2)

    crossSectionLength_recv = interface.read_block_scalar_data(
        crossSectionLengthID, vertexIDs_fluid1tosolid)
    crossSectionLength[0:51] = crossSectionLength_recv
   
    # i.e. not yet converged
    if interface.is_action_required(action_read_iteration_checkpoint()):
        interface.mark_action_fulfilled(action_read_iteration_checkpoint())
    else:  # converged, timestep complete
        t += precice_dt
        velocity_old = np.copy(velocity)
        pressure_old = np.copy(pressure)
        crossSectionLength_old = np.copy(crossSectionLength)
        time_it += 1

the main solver loop for the Solid participant is:

while interface.is_coupling_ongoing():
    # When an implicit coupling scheme is used, checkpointing is required
    if interface.is_action_required(action_write_iteration_checkpoint()):
        interface.mark_action_fulfilled(action_write_iteration_checkpoint())

    crossSectionLength = crossSection0 * (
        (pressure0 - 2.0 * c_mk ** 2) ** 2 / (pressure - 2.0 * c_mk ** 2) ** 2)
    interface.write_block_scalar_data(crossSectionLengthID, vertexIDs, crossSectionLength)
    precice_dt = interface.advance(precice_dt)
    pressure = interface.read_block_scalar_data(pressureID, vertexIDs)

    if interface.is_action_required(action_read_iteration_checkpoint()):  # i.e. not yet converged
        interface.mark_action_fulfilled(action_read_iteration_checkpoint())
    else:
        t += precice_dt

Please let me know if there anything which I am missing either from config file or code.

For ease, following is the config visualization:

Hi @arslansadiq :wave:

I didn’t spot any any obvious mistakes in your setup.

What happens if you use

initialize="true"

in all exchange tags. I could imagine this could indeed be buggy in preCICE.

Other recommendations:

  • Try to restrict your logging to make it more readable. The first example from Logging configuration | preCICE - The Coupling Library is a good setting to start with.
  • Personal taste: I find the naming scheme you use a bit confusing. PressureSolid for example sounds like the pressure of the solid. Or SolidToFluid-Mesh sounds like a mapping. Maybe names like PressureBack, PressureOutflow, PressureUpstream, FluidRadialMesh, FluidOuterWallMesh etc could help.

Hi,
thank you for your suggestion. By putting initialization tag it works as intended. BTW can you tell me what difference does this make?

OK, then this is indeed a bug. It should be allowed that you initialize some, but not all data. If you only couple two participants this work. But if you couple three, the third participant does not get informed (apparently). I guess this is simply a case we never had before. Could you please open an issue? Please attach the “good” and the “bad” config.

Information on data initialization: Step 7 - Data initialization | preCICE - The Coupling Library

But this is the same as the multiple perpendicular flaps tutorial, right? Muliple perpendicular flaps | preCICE - The Coupling Library

No, there we don’t initialize any data:

      <exchange data="Stress1" mesh="Fluid1-Mesh-Centers" from="Fluid" to="Solid1" />
      <exchange data="Stress2" mesh="Fluid2-Mesh-Centers" from="Fluid" to="Solid2" />
      <exchange data="Displacement1" mesh="Solid1-Mesh" from="Solid1" to="Fluid" />
      <exchange data="Displacement2" mesh="Solid2-Mesh" from="Solid2" to="Fluid" />

Ah, I now see that we are actually initializing the CrossSectionLength and I understand that this is the untested situation, then.