Actual source code: ex218.c
1: static char help[] = "Tests MatShellTestMult()\n\n";
3: #include <petscmat.h>
5: typedef struct _n_User *User;
6: struct _n_User {
7: Mat B;
8: };
10: static PetscErrorCode MatMult_User(Mat A, Vec X, Vec Y)
11: {
12: User user;
14: PetscFunctionBegin;
15: PetscCall(MatShellGetContext(A, &user));
16: PetscCall(MatMult(user->B, X, Y));
17: PetscFunctionReturn(PETSC_SUCCESS);
18: }
20: static PetscErrorCode MatMultTranspose_User(Mat A, Vec X, Vec Y)
21: {
22: User user;
24: PetscFunctionBegin;
25: PetscCall(MatShellGetContext(A, &user));
26: PetscCall(MatMultTranspose(user->B, X, Y));
27: PetscFunctionReturn(PETSC_SUCCESS);
28: }
30: static PetscErrorCode MyFunction(void *ctx, Vec x, Vec y)
31: {
32: User user = (User)ctx;
34: PetscFunctionBegin;
35: PetscCall(MatMult(user->B, x, y));
36: PetscFunctionReturn(PETSC_SUCCESS);
37: }
39: int main(int argc, char **args)
40: {
41: const PetscInt inds[] = {0, 1};
42: PetscScalar avals[] = {2, 3, 5, 7};
43: Mat S;
44: User user;
45: Vec base;
47: PetscFunctionBeginUser;
48: PetscCall(PetscInitialize(&argc, &args, NULL, help));
49: PetscCall(PetscNew(&user));
50: PetscCall(MatCreateSeqAIJ(PETSC_COMM_WORLD, 2, 2, 2, NULL, &user->B));
51: PetscCall(MatSetUp(user->B));
52: PetscCall(MatSetValues(user->B, 2, inds, 2, inds, avals, INSERT_VALUES));
53: PetscCall(MatAssemblyBegin(user->B, MAT_FINAL_ASSEMBLY));
54: PetscCall(MatAssemblyEnd(user->B, MAT_FINAL_ASSEMBLY));
55: PetscCall(MatCreateVecs(user->B, &base, NULL));
56: PetscCall(MatCreateShell(PETSC_COMM_WORLD, 2, 2, 2, 2, user, &S));
57: PetscCall(MatSetUp(S));
58: PetscCall(MatShellSetOperation(S, MATOP_MULT, (void (*)(void))MatMult_User));
59: PetscCall(MatShellSetOperation(S, MATOP_MULT_TRANSPOSE, (void (*)(void))MatMultTranspose_User));
61: PetscCall(MatShellTestMult(S, MyFunction, base, user, NULL));
62: PetscCall(MatShellTestMultTranspose(S, MyFunction, base, user, NULL));
64: PetscCall(VecDestroy(&base));
65: PetscCall(MatDestroy(&user->B));
66: PetscCall(MatDestroy(&S));
67: PetscCall(PetscFree(user));
68: PetscCall(PetscFinalize());
69: return 0;
70: }
72: /*TEST
74: test:
75: args: -mat_shell_test_mult_view -mat_shell_test_mult_transpose_view
77: TEST*/