@@ -57,11 +57,9 @@ PetscErrorCode SetupLibceedByDegree(DM dm, Ceed ceed, CeedInt degree,
5757 P = degree + 1 ;
5858 Q = P + q_extra ;
5959 CeedBasisCreateTensorH1Lagrange (ceed , topo_dim , num_comp_u , P , Q ,
60- bp_data .q_mode ,
61- & basis_u );
60+ bp_data .q_mode , & basis_u );
6261 CeedBasisCreateTensorH1Lagrange (ceed , topo_dim , num_comp_x , 2 , Q ,
63- bp_data .q_mode ,
64- & basis_x );
62+ bp_data .q_mode , & basis_x );
6563 CeedBasisGetNumQuadraturePoints (basis_u , & num_qpts );
6664
6765 // CEED restrictions
@@ -155,8 +153,7 @@ PetscErrorCode SetupLibceedByDegree(DM dm, Ceed ceed, CeedInt degree,
155153 CeedOperatorSetField (op_setup_rhs , "x" , elem_restr_x , basis_x ,
156154 CEED_VECTOR_ACTIVE );
157155 CeedOperatorSetField (op_setup_rhs , "q_data" , elem_restr_qd_i ,
158- CEED_BASIS_COLLOCATED ,
159- q_data );
156+ CEED_BASIS_COLLOCATED , q_data );
160157 CeedOperatorSetField (op_setup_rhs , "true_soln" , elem_restr_u_i ,
161158 CEED_BASIS_COLLOCATED , * target );
162159 CeedOperatorSetField (op_setup_rhs , "rhs" , elem_restr_u , basis_u ,
@@ -254,4 +251,115 @@ PetscErrorCode CeedLevelTransferSetup(Ceed ceed, CeedInt num_levels,
254251 PetscFunctionReturn (0 );
255252};
256253
254+ // -----------------------------------------------------------------------------
255+ // Set up libCEED for BDDC interface vertices
256+ // -----------------------------------------------------------------------------
257+ PetscErrorCode SetupLibceedBDDC (DM dm_vertex , CeedData data_fine ,
258+ CeedDataBDDC data_vertex ,
259+ PetscInt g_vertex_size , PetscInt xl_vertex_size ,
260+ BPData bp_data {
261+ int ierr ;
262+ Ceed ceed = data_fine -> ceed ;
263+ CeedBasis basis_Pi , basis_u = data_fine -> basis_u ;
264+ CeedElemRestriction elem_restr_Pi , elem_restr_r ;
265+ CeedOperator op_Pi_r , op_r_Pi , op_Pi_Pi , op_r_r , op_r_r_inv , ;
266+ CeedVector x_Pi_ceed , y_Pi_ceed , x_r_ceed , y_r_ceed , mask_r_ceed , mask_Gamma_ceed , mask_I_ceed ;
267+ CeedInt topo_dim , num_comp_u , P , Q , num_qpts , num_elem , elem_size ,
268+ q_data_size = bp_data .q_data_size ;
269+
270+ // CEED basis
271+ CeedBasisGetDimension (basis_u , & topo_dim );
272+ CeedBasisGetNumComponents (basis_u , & num_comp_u );
273+ CeedBasisGetNumNodes1D (basis_u , & P );
274+ elem_size = CeedIntPow (P , topo_dim );
275+ CeedBasisGetNumQuadraturePoints1D (basis_u , & Q );
276+ CeedBasisGetNumQuadraturePoints (basis_u , & num_qpts );
277+ CeedScalar * interp_1d , * grad_1d , * q_ref_1d , * q_weight_1d ;
278+ interp_1d = calloc (2 * Q * sizeof (CeedScalar ));
279+ CeedScalar * temp ;
280+ CeedBasisGetInterp1D (basis_u , & temp );
281+ memcpy (interp_1d , temp , Q * sizeof (CeedScalar ));
282+ memcpy (& interp_1d [1 * Q ], temp [(P - 1 )* Q ], Q * sizeof (CeedScalar ));
283+ grad_1d = calloc (2 * Q * sizeof (CeedScalar ));
284+ CeedBasisGetGrad1D (basis_u , & temp );
285+ memcpy (grad_1d , temp , Q * sizeof (CeedScalar ));
286+ memcpy (& grad_1d [1 * Q ], temp [(P - 1 )* Q ], Q * sizeof (CeedScalar ));
287+ q_ref_1d = calloc (Q * sizeof (CeedScalar ));
288+ CeedBasisGetQRef (basis_u , & temp );
289+ memcpy (q_ref_1d , temp , Q * sizeof (CeedScalar ));
290+ q_weight_1d = calloc (Q * sizeof (CeedScalar ));
291+ CeedBasisGetQWeights (basis_u , & temp );
292+ memcpy (q_weight_1d , temp , Q * sizeof (CeedScalar ));
293+ CeedBasisCreateTensorH1 (ceed , topo_dim , num_comp_u , 1 , Q ,
294+ interp_1d , grad_1d , q_ref_1d ,
295+ q_weight_1d , & basis_Pi );
296+
297+ // CEED restrictions
298+ // -- Interface vertex restriction
299+ ierr = CreateRestrictionFromPlex (ceed , dm_vertex , P , topo_dim , 0 , 0 , 0 , & elem_restr_Pi );
300+ CHKERRQ (ierr );
301+
302+ // -- Subdomain restriction
303+ ierr = DMPlexGetHeightStratum (dm_vertex , 0 , & c_start , & c_end ); CHKERRQ (ierr );
304+ num_elem = c_end - c_start ;
305+ CeedInt strides = [num_comp_u , 1 , num_comp_u * elem_size ];
306+ CeedElemRestrictionCreateStrided (ceed , num_elem , elem_size , num_comp_u ,
307+ num_comp_u * num_elem * elem_size ,
308+ strides , & elem_restr_r );
309+
310+ // Create the persistent vectors that will be needed
311+ CeedVectorCreate (ceed , xl_vertex_size , & x_Pi_ceed );
312+ CeedVectorCreate (ceed , xl_vertex_size , & y_Pi_ceed );
313+ CeedVectorCreate (ceed , num_comp_u * elem_size * num_elem , & x_r_ceed );
314+ CeedVectorCreate (ceed , num_comp_u * elem_size * num_elem , & y_r_ceed );
315+
316+ // Create the mass or diff operator
317+ CeedQFunction qf_apply = data_fine -> qf_apply ;
318+ // -- Interface nodes
319+ CeedOperatorSetField (op_Pi_Pi , "u" , elem_restr_Pi , basis_u , CEED_VECTOR_ACTIVE );
320+ CeedOperatorSetField (op_Pi_Pi , "q_data" , data_fine -> elem_restr_qd_i ,
321+ CEED_BASIS_COLLOCATED , data_fine -> q_data );
322+ CeedOperatorSetField (op_Pi_Pi , "v" , elem_restr_Pi , basis_u , CEED_VECTOR_ACTIVE );
323+ // -- Interface vertices to subdomain
324+ CeedOperatorSetField (op_Pi_r , "u" , elem_restr_r , basis_u , CEED_VECTOR_ACTIVE );
325+ CeedOperatorSetField (op_Pi_r , "q_data" , data_fine -> elem_restr_qd_i ,
326+ CEED_BASIS_COLLOCATED , data_fine -> q_data );
327+ CeedOperatorSetField (op_Pi_r , "v" , elem_restr_Pi , basis_u , CEED_VECTOR_ACTIVE );
328+ // -- Subdomain to interface vertices
329+ CeedOperatorSetField (op_r_Pi , "u" , elem_restr_Pi , basis_u , CEED_VECTOR_ACTIVE );
330+ CeedOperatorSetField (op_r_Pi , "q_data" , data_fine -> elem_restr_qd_i ,
331+ CEED_BASIS_COLLOCATED , data_fine -> q_data );
332+ CeedOperatorSetField (op_r_Pi , "v" , elem_restr_r , basis_u , CEED_VECTOR_ACTIVE );
333+ // -- Subdomain to subdomain
334+ CeedOperatorSetField (op_r_r , "u" , elem_restr_r , basis_u , CEED_VECTOR_ACTIVE );
335+ CeedOperatorSetField (op_r_r , "q_data" , data_fine -> elem_restr_qd_i ,
336+ CEED_BASIS_COLLOCATED , data_fine -> q_data );
337+ CeedOperatorSetField (op_r_r , "v" , elem_restr_r , basis_u , CEED_VECTOR_ACTIVE );
338+ // -- Subdomain FDM inverse
339+ CeedOperatorCreateFDMElementInverse (op_r_r , & op_r_r_inv , CEED_REQUEST_IMMEDIATE );
340+
341+ // Injection and restriction operators
342+ CeedQFunctionCreateIdentity (ceed , num_comp_u , CEED_EVAL_NONE , CEED_EVAL_NONE ,
343+ & qf_inject );
344+ CeedQFunctionCreateIdentity (ceed , num_comp_u , CEED_EVAL_NONE , CEED_EVAL_NONE ,
345+ & qf_restrict );
346+
347+ // Save libCEED data required for level
348+ data_vertex -> basis_Pi = basis_Pi ;
349+ data_vertex -> elem_restr_Pi = elem_restr_Pi ;
350+ data_vertex -> elem_restr_r = elem_restr_r ;
351+ data_vertex -> op_Pi_r = op_Pi_r ;
352+ data_vertex -> op_r_Pi = op_r_Pi ;
353+ data_vertex -> op_Pi_Pi = op_Pi_Pi ;
354+ data_vertex -> op_r_r = op_r_r ;
355+ data_vertex -> op_r_r_inv = op_r_r_inv ;
356+ data_vertex -> x_Pi_ceed = x_Pi_ceed ;
357+ data_vertex -> y_Pi_ceed = y_Pi_ceed ;
358+ data_vertex -> x_r_ceed = x_r_ceed ;
359+ data_vertex -> y_r_ceed = y_r_ceed ;
360+
361+ PetscFunctionReturn (0 );
362+ };
363+
364+
257365// -----------------------------------------------------------------------------
0 commit comments