xref: /libCEED/tests/t414-qfunction.c (revision b473a06276daa8a28b9126dca2fc365f20267013)
1 /// @file
2 /// Test creation, evaluation, and destruction for vector mass QFunction by name
3 /// \test Test creation, evaluation, and destruction for vector mass QFunction by name
4 #include <ceed.h>
5 #include <math.h>
6 #include <stdio.h>
7 #include <string.h>
8 
9 int main(int argc, char **argv) {
10   Ceed          ceed;
11   CeedVector    in[16], out[16];
12   CeedVector    q_data, dx, w, u, v;
13   CeedQFunction qf_setup, qf_mass;
14   CeedInt       q        = 8;
15   const CeedInt num_comp = 3;
16 
17   CeedInit(argv[1], &ceed);
18 
19   for (CeedInt dim = 2; dim <= 3; dim++) {
20     CeedInt num_qpts = CeedIntPow(q, dim);
21 
22     CeedVectorCreate(ceed, num_qpts * dim * dim, &dx);
23     CeedVectorCreate(ceed, num_qpts, &w);
24     CeedVectorCreate(ceed, num_qpts * num_comp, &u);
25     {
26       CeedScalar dx_array[num_qpts * dim * dim], w_array[num_qpts], u_array[num_qpts * num_comp];
27 
28       for (CeedInt i = 0; i < num_qpts; i++) {
29         w_array[i] = 1.0 / num_qpts;
30       }
31       for (CeedInt d = 0; d < dim; d++) {
32         for (CeedInt g = 0; g < dim; g++) {
33           for (CeedInt i = 0; i < num_qpts; i++) {
34             dx_array[i + (g * dim + d) * num_qpts] = d == g;
35           }
36         }
37       }
38       for (CeedInt c = 0; c < num_comp; c++) {
39         for (CeedInt i = 0; i < num_qpts; i++) {
40           u_array[i + c * num_qpts] = c + 1;
41         }
42       }
43       CeedVectorSetArray(dx, CEED_MEM_HOST, CEED_COPY_VALUES, dx_array);
44       CeedVectorSetArray(w, CEED_MEM_HOST, CEED_COPY_VALUES, w_array);
45       CeedVectorSetArray(u, CEED_MEM_HOST, CEED_COPY_VALUES, u_array);
46     }
47     CeedVectorCreate(ceed, num_qpts, &q_data);
48     CeedVectorSetValue(q_data, 0.0);
49     CeedVectorCreate(ceed, num_qpts * num_comp, &v);
50     CeedVectorSetValue(v, 0.0);
51 
52     char name[13] = "";
53     snprintf(name, sizeof name, "Mass%" CeedInt_FMT "DBuild", dim);
54     CeedQFunctionCreateInteriorByName(ceed, name, &qf_setup);
55     {
56       in[0]  = dx;
57       in[1]  = w;
58       out[0] = q_data;
59       CeedQFunctionApply(qf_setup, num_qpts, in, out);
60     }
61 
62     CeedQFunctionCreateInteriorByName(ceed, "Vector3MassApply", &qf_mass);
63     {
64       in[0]  = u;
65       in[1]  = q_data;
66       out[0] = v;
67       CeedQFunctionApply(qf_mass, num_qpts, in, out);
68     }
69 
70     // Verify results
71     {
72       const CeedScalar *v_array;
73 
74       CeedVectorGetArrayRead(v, CEED_MEM_HOST, &v_array);
75       for (CeedInt c = 0; c < num_comp; c++) {
76         CeedScalar sum = 0;
77         for (CeedInt i = 0; i < num_qpts; i++) sum += v_array[i + c * num_qpts];
78         if (fabs(sum - (c + 1)) > 10 * CEED_EPSILON) {
79           // LCOV_EXCL_START
80           printf("%" CeedInt_FMT "D volume error in component %" CeedInt_FMT ": %f != %f\n", dim, c, sum, (c + 1.0));
81           // LCOV_EXCL_STOP
82         }
83       }
84       CeedVectorRestoreArrayRead(v, &v_array);
85     }
86 
87     CeedVectorDestroy(&dx);
88     CeedVectorDestroy(&w);
89     CeedVectorDestroy(&u);
90     CeedVectorDestroy(&v);
91     CeedVectorDestroy(&q_data);
92     CeedQFunctionDestroy(&qf_setup);
93     CeedQFunctionDestroy(&qf_mass);
94   }
95 
96   CeedDestroy(&ceed);
97   return 0;
98 }
99