Hello,

I ran into a seemingly non-consistent behavior of the function

[DMPlexComputeCellGeometryFEM](https://urldefense.us/v3/__https://petsc.org/release/manualpages/DMPlex/DMPlexComputeCellGeometryFEM/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_rJABo0_$
 )
(
[DM](https://urldefense.us/v3/__https://petsc.org/release/manualpages/DM/DM/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_kyYWLFi$
 )
dm

,
[PetscInt](https://urldefense.us/v3/__https://petsc.org/release/manualpages/Sys/PetscInt/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_jAVrwAd$
 )
cell

,
[PetscQuadrature](https://urldefense.us/v3/__https://petsc.org/release/manualpages/DT/PetscQuadrature/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_jVjnRvX$
 )
quad

,
[PetscReal](https://urldefense.us/v3/__https://petsc.org/release/manualpages/Sys/PetscReal/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_heQHCRx$
 )
*

v

,
[PetscReal](https://urldefense.us/v3/__https://petsc.org/release/manualpages/Sys/PetscReal/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_heQHCRx$
 )
J

[],
[PetscReal](https://urldefense.us/v3/__https://petsc.org/release/manualpages/Sys/PetscReal/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_heQHCRx$
 )
invJ

[],
[PetscReal](https://urldefense.us/v3/__https://petsc.org/release/manualpages/Sys/PetscReal/__;!!G_uCfscf7eWS!YEv7_aaCdN0cxV8sUhRBIACYZGNNcwQusNjEpfVep6yOAxRYE9f8kw4XiVENrjEvQEVwiheebMTQVhPw4eenYApT_heQHCRx$
 )
*

detJ

)

Calling it in a loop happens to crash, only some times, when the input npoints 
is not equal to one.
Attached is a mesh file (msh format), consisting of four quadrilaterals. Small 
examples in both C and Fortran also attached; they read the mesh, create a 
Gauss tensor quadrature rule and then loop through all cells in order to get 
the mapped quadrature points.

When the quadrature created has a single point per dimension (npoints = 1), 
there seems to be no issue. The program runs and the output is the expected.

On the C side, For npoints = 2 the program hangs, usually no errors; sometimes

*** stack smashing detected ***: terminated,
[:1345101] *** Process received signal ***
[:1345101] Signal: Aborted (6)
[:1345101] Signal code: (-6)

or

LeakSanitizer: detected memory leaks (when compiled with -fsanitize=addres).

On the Fortran side, similar behavior for npoints = 1 or 2. Either no error at 
all (no error meaning the one that only mentions "probably memory access out of 
bounds"), or sometimes "corrupted size vs. prev_size", followed by a stack 
trace.

Question: Do the arguments J, invJ need to be allocated (e.g. allocate(J(4))) 
before calling DMPlexComputeCellGeometryFEM? Allocation seems to be the cause 
for triggering an error.

---

NOTE: The interface to DMPlexComputeCellGeometryFEM, under 
$PETSC_ARCH$/ftn/dm/petscdmplex.h90, read:

interface DMPlexComputeCellGeometryFEM
subroutine DMPlexComputeCellGeometryFEM(a,b,c,d,e,f,g, z)
import tDM,tPetscQuadrature
DM :: a
PetscInt :: b
PetscQuadrature :: c
PetscReal :: d #### should it be d(*) ?
PetscReal :: e(*)
PetscReal :: f(*)
PetscReal :: g
PetscErrorCode z
end subroutine
end interface

Should argument d (referring to the array of the mapped integration points v) 
be defined differently?

---

NOTE: Tested with PETSc 3.23.1 (from the tarball) and the latest git.
Configured with ./configure --with-fortran-bindings=1
Using gcc/gfortran 11.4.0, OpenMPI 4.1.2

Thanks,
Noam

Attachment: mesh_quad.msh
Description: Mesh model

program test
#include <petsc/finclude/petscdm.h>
#include <petsc/finclude/petscdmplex.h>
  use PETScDMplex
    implicit none

    DM :: dm
    PetscInt  :: c
    PetscInt  :: plexdim, Nc, npoints
    PetscInt  :: cell, cStart, cEnd
    PetscInt  :: ierr
    PetscReal :: vv(8), detJ        ! change size of v accordingly
    PetscQuadrature :: quad

    PetscReal, dimension(:), pointer :: J, invJ

    PetscCallA(PetscInitialize(ierr))

    PetscCallA(DMPlexCreateFromFile(PETSC_COMM_WORLD, "mesh_quad.msh", "test", PETSC_TRUE, dm, ierr))

    plexdim = 2
    Nc = 2
    npoints = 2     ! npoints = 1 works all the time
    PetscCallA(PetscDTGaussTensorQuadrature(plexdim, Nc, npoints, -1.0d0, +1.0d0, quad, ierr))

    PetscCallA(DMPlexGetHeightStratum(dm, 0, cStart, cEnd, ierr))

    !   Allocating J, invJ before calling  DMPlexComputeCellGeometryFEM 
    !  
    !   allocate(J(4))
    !   allocate(invJ(4))
    !  
    !   sometimes works, but others does not, with a message:
    !
    !       "corrupted size vs. prev_size"  , followed by a stack trace
    !  
    do c = cStart, cEnd-1
        PetscCallA(DMPlexComputeCellGeometryFEM(dm, c, quad, vv, J, invJ, detJ, ierr))
        CHKERRA(ierr)
        print *, "Cell ", c
        print "(a, *(f12.6))", "v0 =", vv
    end do

    PetscCallA(PetscQuadratureDestroy(quad, ierr))
    PetscCallA(PetscFinalize(ierr))
end program test

!
!   EXPECTED OUTPUT
!   ---------------
!
!   npoints = 1
!
!    Cell            0
!   v0 =    2.750000    2.500000
!    Cell            1
!   v0 =    7.750000    2.750000
!    Cell            2
!   v0 =    7.750000    7.750000
!    Cell            3
!   v0 =    2.750000    7.500000
!
!   ---------------------------------
!
!   npoints = 2
!
!    Cell            0
!   v0 =    4.110042    1.178633    1.101283    0.934616    4.565384    4.398717    1.223291    3.488034
!    Cell            1
!   v0 =    8.988034    1.101283    6.223291    1.223291    9.110042    4.110042    6.678633    4.565384
!    Cell            2
!   v0 =    8.988034    8.988034    9.110042    6.223291    6.223291    9.110042    6.678633    6.678633
!    Cell            3
!   v0 =    1.101283    8.821367    4.110042    9.065384    1.223291    5.601283    4.565384    6.511966
!
!   ---------------------------------
#include <stdio.h>
#include <petscdmplex.h>
#include "petscdt.h" 

int main(int argc, char *argv[]) {

    DM dm;
    PetscInt dim, Nc, npoints;
    PetscQuadrature quad;
    PetscInt cStart, cEnd;

    PetscCall(PetscInitialize(&argc, &argv, NULL, NULL));
    PetscCall(DMPlexCreateFromFile(PETSC_COMM_WORLD, "mesh_quad.msh", "test", PETSC_TRUE, &dm));

    dim = 2;
    Nc = 2;
    npoints = 2;    // npoints = 1 works
    PetscCall(PetscDTGaussTensorQuadrature(dim, Nc, npoints, -1.0, +1.0, &quad));

    PetscCall(DMPlexGetHeightStratum(dm, 0, &cStart, &cEnd));

    for (PetscInt s = cStart; s < cEnd; s++) {
        PetscReal vv[8], J[4], invJ[4], detJ;       // vv[2] if npoints==1
        PetscCall(DMPlexComputeCellGeometryFEM(dm, s, quad, vv, J, invJ, &detJ));
        printf("Cell [%d] -- v =", s);
        for (int k = 0; k < (npoints == 1 ? 2 : 8); k++) {
            printf("%12.6f ", vv[k]);
        }
        printf("\n");
    }

    PetscCall(PetscQuadratureDestroy(&quad));
    PetscCall(PetscFinalize());
}


/*
 *  EXPECTED OUTPUT
 *  ---------------
 *
 *  npoints = 1
 *
 *   Cell [0] -- v =    2.750000    2.500000
 *   Cell [1] -- v =    7.750000    2.750000
 *   Cell [2] -- v =    7.750000    7.750000
 *   Cell [3] -- v =    2.750000    7.500000
 *
 *  ---------------------------------
 *
 *  npoints = 2
 *
 *   Cell [0] -- v =    4.110042    1.178633    1.101283    0.934616    4.565384    4.398717    1.223291    3.488034
 *   Cell [1] -- v =    8.988034    1.101283    6.223291    1.223291    9.110042    4.110042    6.678633    4.565384
 *   Cell [2] -- v =    8.988034    8.988034    9.110042    6.223291    6.223291    9.110042    6.678633    6.678633
 *   Cell [3] -- v =    1.101283    8.821367    4.110042    9.065384    1.223291    5.601283    4.565384    6.511966
 *
 *  ---------------------------------
 *
 *  Frequent output for npoints = 2 (wrong values)
 *  ----------------------------------------------
 *
 *  Cell [0] -- v =    0.394338    -2.894338     2.788675    -0.788675     0.105662    -2.894338     2.211325    -0.788675 
 *  Cell [1] -- v =    0.105662    -2.105662     2.605662     0.394338     0.394338    -2.105662     2.894338     0.394338 
 *  Cell [2] -- v =   -2.394338     0.394338     0.105662    -2.105662    -2.105662     0.394338     0.394338    -2.105662 
 *  Cell [3] -- v =    0.105662     2.894338    -2.788675     0.788675     0.394338     2.894338    -2.211325     0.788675
 *
 */

Reply via email to