1 #include "pargrid.h"
2
3 /*+ main - the main routine for this grid program
4
5 Input Parameters:
6 argc, argv - the usual
7 argv[1] - the number of processors in the x direction
8 argv[2] - the number of processors in the y direction
9 argv[3] - the number of processors in the z direction
10 argv[4] - the number of points in the x direction on each processor
11 do not use less than 3 points
12 argv[5] - the number of points in the y direction on each processor
13 do not use less than 3 points
14 argv[6] - the number of points in the z direction on each processor
15 do not use less than 3 points
16 argv[7] - symmetric = 0, nonsymmetric = 1
17 argv[8] - 0 = do not use, 1 = use inode/clique stuff
18 argv[9] - number of components per grid point
19 argv[10] - 0 = use identity for shift, 1 = use positive of A
20 argv[11] - shift
21
22 To Run, use mpirun
23
24 Notes: The grid program solves a linear system associated with
25 a 3-D grid distributed across the processors. The 3-D
26 grid is partitioned in all three dimensions among the
27 processors. A 7pt stencil is used.
28
29 +*/
30
main(int argc,char ** argv)31 int main(int argc, char **argv)
32 {
33 par_grid grid;
34 BSprocinfo *procinfo;
35 int inode, nonsymmetric;
36
37 /* Call BSinit() to initialize BlocklSolve and MPI */
38 BSinit(&argc,&argv);
39
40 /* set up the context for BlockSolve */
41 procinfo = BScreate_ctx(); CHKERRN(0);
42 /* tell it to print out some information on the reordering */
43 BSctx_set_pr(procinfo,TRUE); CHKERRN(0);
44
45 if(procinfo->my_id==0) {
46 printf("\n");
47 printf("************** Blocksolve Example Grid7 *******************\n");
48 }
49
50 /* read in grid parameters */
51 if (argc < 12) {
52 SETERRC(ARG_ERR,"Argument list too small\n");
53 if(procinfo->my_id==0) {
54 printf("Example: mpirun -np P grid7.ARCH PX PY PZ NX NY NZ SYM IN NC BMAT SHIFT\n");
55 printf("ARCH = Machine architecture\n");
56 printf("P = number of processors\n");
57 printf("PX = the number of processors in the x direction\n");
58 printf("PY = the number of processors in the y direction\n");
59 printf("PZ = the number of processors in the z direction\n");
60 printf("NX = number of points in the x direction on each processor\n");
61 printf("NY = number of points in the y direction on each processor\n");
62 printf("NZ = number of points in the z direction on each processor\n");
63 printf("SYM = 0, use symmetric data structure, = 1, use nonsymmetric\n");
64 printf("IN = 0, do not use, = 1, use inode/clique stuff\n");
65 printf("NC = number of components per grid point\n");
66 printf("BMAT = 0, use I, = 1, use positive(A)\n");
67 printf("SHIFT = shift in (A - shift*B) \n");
68 }
69 return(-1);
70 }
71 sscanf(argv[1],"%d",&grid.worker_x);
72 sscanf(argv[2],"%d",&grid.worker_y);
73 sscanf(argv[3],"%d",&grid.worker_z);
74 if (procinfo->my_id == 0) {
75 printf("o Number of workers (x,y,z): %d %d %d\n",
76 grid.worker_x,grid.worker_y,grid.worker_z);
77 }
78 if (procinfo->nprocs != grid.worker_x*grid.worker_y*grid.worker_z) {
79 SETERRC(ARG_ERR,"Number of processors is not correct\n");
80 return(-1);
81 }
82 sscanf(argv[4],"%d",&grid.l_num_x);
83 sscanf(argv[5],"%d",&grid.l_num_y);
84 sscanf(argv[6],"%d",&grid.l_num_z);
85 sscanf(argv[7],"%d",&nonsymmetric);
86 sscanf(argv[8],"%d",&inode);
87 sscanf(argv[9],"%d",&grid.ncomp);
88 sscanf(argv[10],"%d",&grid.bmatrix);
89 sscanf(argv[11],"%lf",&grid.shift);
90 if(grid.ncomp<1) grid.ncomp = 1;
91 if(grid.ncomp>20) grid.ncomp = 20;
92 grid.symmetric = TRUE;
93 grid.icc_storage = (!nonsymmetric);
94 grid.positive = FALSE;
95 BSctx_set_method(procinfo,SYMMLQ);
96
97 /* tell it to use the nonsymmetric matrix data structure */
98 if(nonsymmetric) {
99 if (procinfo->my_id == 0)
100 printf("o Using nonsymmetric data structure\n");
101 BSctx_set_pre(procinfo,PRE_ILU);
102 } else {
103 if (procinfo->my_id == 0)
104 printf("o Using symmetric data structure\n");
105 BSctx_set_pre(procinfo,PRE_ICC);
106 }
107
108 /* decide whether to look for i-nodes or cliques */
109 if(inode) {
110 if (procinfo->my_id == 0)
111 printf("o Using inode/clique information\n");
112 BSctx_set_si(procinfo,FALSE); CHKERRN(0);
113 } else {
114 if (procinfo->my_id == 0)
115 printf("o Not using inode/clique information\n");
116 BSctx_set_si(procinfo,TRUE); CHKERRN(0);
117 }
118
119 if (procinfo->my_id == 0)
120 printf("o Multi component grid, %d components per point\n",grid.ncomp);
121
122 if (procinfo->my_id == 0) {
123 if(grid.bmatrix) printf("o B = positive(A)\n");
124 else printf("o B = I\n");
125 printf("o Shift = %e\n",grid.shift);
126 }
127
128 /* local grid size and type */
129 grid.type = 7;
130 if (procinfo->my_id == 0) {
131 printf("o Local discretizations (x,y,z): %d %d %d\n",
132 grid.l_num_x,grid.l_num_y,grid.l_num_z);
133 }
134
135 /* call the worker */
136 worker(&grid,procinfo);
137
138 if(procinfo->my_id==0) {
139 printf("************ End Blocksolve Example Grid7 *****************\n");
140 printf("\n");
141 }
142
143 /* print logging if enabled */
144 BSprint_log(procinfo); CHKERRN(0);
145
146 /* free the context */
147 BSfree_ctx(procinfo); CHKERRN(0);
148
149 /* finalize BlockSolve and MPI */
150 BSfinalize();
151
152 exit(0);
153 }
154