00001 
00002 
00003 
00004 
00005 
00006 #include "mpi.h"
00007 #include <stdio.h>
00008 #include <string.h>
00009 #include <stdlib.h>
00010 
00011 
00012 
00013 #define SIZE 5000
00014 
00015 #define VERBOSE 0
00016 int main(int argc, char **argv)
00017 {
00018     int *buf, i, mynod, nprocs, len, b[3];
00019     int errs=0, toterrs;
00020     MPI_Aint d[3];
00021     MPI_File fh;
00022     MPI_Status status;
00023     char *filename;
00024     MPI_Datatype typevec, newtype, t[3];
00025 
00026     MPI_Init(&argc,&argv);
00027     MPI_Comm_size(MPI_COMM_WORLD, &nprocs);
00028     MPI_Comm_rank(MPI_COMM_WORLD, &mynod);
00029 
00030     if (nprocs != 2) {
00031         fprintf(stderr, "Run this program on two processes\n");
00032         MPI_Abort(MPI_COMM_WORLD, 1);
00033     }
00034 
00035 
00036 
00037     if (!mynod) {
00038     i = 1;
00039     while ((i < argc) && strcmp("-fname", *argv)) {
00040         i++;
00041         argv++;
00042     }
00043     if (i >= argc) {
00044         fprintf(stderr, "\n*#  Usage: noncontig_coll -fname filename\n\n");
00045         MPI_Abort(MPI_COMM_WORLD, 1);
00046     }
00047     argv++;
00048     len = strlen(*argv);
00049     filename = (char *) malloc(len+1);
00050     strcpy(filename, *argv);
00051     MPI_Bcast(&len, 1, MPI_INT, 0, MPI_COMM_WORLD);
00052     MPI_Bcast(filename, len+1, MPI_CHAR, 0, MPI_COMM_WORLD);
00053     }
00054     else {
00055     MPI_Bcast(&len, 1, MPI_INT, 0, MPI_COMM_WORLD);
00056     filename = (char *) malloc(len+1);
00057     MPI_Bcast(filename, len+1, MPI_CHAR, 0, MPI_COMM_WORLD);
00058     }
00059 
00060     buf = (int *) malloc(SIZE*sizeof(int));
00061 
00062     MPI_Type_vector(SIZE/2, 1, 2, MPI_INT, &typevec);
00063 
00064     b[0] = b[1] = b[2] = 1;
00065     d[0] = 0;
00066     d[1] = mynod*sizeof(int);
00067     d[2] = SIZE*sizeof(int);
00068     t[0] = MPI_LB;
00069     t[1] = typevec;
00070     t[2] = MPI_UB;
00071 
00072     MPI_Type_struct(3, b, d, t, &newtype);
00073     MPI_Type_commit(&newtype);
00074     MPI_Type_free(&typevec);
00075 
00076     if (!mynod) {
00077 #if VERBOSE
00078     fprintf(stderr, "\ntesting noncontiguous in memory, noncontiguous in file using collective I/O\n");
00079 #endif
00080     MPI_File_delete(filename, MPI_INFO_NULL);
00081     }
00082     MPI_Barrier(MPI_COMM_WORLD);
00083 
00084     MPI_File_open(MPI_COMM_WORLD, filename, MPI_MODE_CREATE | MPI_MODE_RDWR,
00085                   MPI_INFO_NULL, &fh);
00086 
00087     MPI_File_set_view(fh, 0, MPI_INT, newtype, "native", MPI_INFO_NULL);
00088 
00089     for (i=0; i<SIZE; i++) buf[i] = i + mynod*SIZE;
00090     MPI_File_write_all(fh, buf, 1, newtype, &status);
00091 
00092     MPI_Barrier(MPI_COMM_WORLD);
00093 
00094     for (i=0; i<SIZE; i++) buf[i] = -1;
00095 
00096     MPI_File_read_at_all(fh, 0, buf, 1, newtype, &status);
00097 
00098     for (i=0; i<SIZE; i++) {
00099     if (!mynod) {
00100         if ((i%2) && (buf[i] != -1)) {
00101         errs++;
00102         fprintf(stderr, "Process %d: buf %d is %d, should be -1\n", 
00103             mynod, i, buf[i]);
00104         }
00105         if (!(i%2) && (buf[i] != i)) {
00106         errs++;
00107         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00108             mynod, i, buf[i], i);
00109         }
00110     }
00111     else {
00112         if ((i%2) && (buf[i] != i + mynod*SIZE)) {
00113         errs++;
00114         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00115             mynod, i, buf[i], i + mynod*SIZE);
00116         }
00117         if (!(i%2) && (buf[i] != -1)) {
00118         errs++;
00119         fprintf(stderr, "Process %d: buf %d is %d, should be -1\n", 
00120             mynod, i, buf[i]);
00121         }
00122     }
00123     }
00124 
00125     MPI_File_close(&fh);
00126 
00127     MPI_Barrier(MPI_COMM_WORLD);
00128 
00129     if (!mynod) {
00130 #if VERBOSE
00131     fprintf(stderr, "\ntesting noncontiguous in memory, contiguous in file using collective I/O\n");
00132 #endif
00133     MPI_File_delete(filename, MPI_INFO_NULL);
00134     }
00135     MPI_Barrier(MPI_COMM_WORLD);
00136 
00137     MPI_File_open(MPI_COMM_WORLD, filename, MPI_MODE_CREATE | MPI_MODE_RDWR,
00138                   MPI_INFO_NULL, &fh);
00139 
00140     for (i=0; i<SIZE; i++) buf[i] = i + mynod*SIZE;
00141     MPI_File_write_at_all(fh, mynod*(SIZE/2)*sizeof(int), buf, 1, newtype, &status);
00142 
00143     MPI_Barrier(MPI_COMM_WORLD);
00144 
00145     for (i=0; i<SIZE; i++) buf[i] = -1;
00146 
00147     MPI_File_read_at_all(fh, mynod*(SIZE/2)*sizeof(int), buf, 1, newtype, &status);
00148 
00149     for (i=0; i<SIZE; i++) {
00150     if (!mynod) {
00151         if ((i%2) && (buf[i] != -1)) {
00152         errs++;
00153         fprintf(stderr, "Process %d: buf %d is %d, should be -1\n", 
00154             mynod, i, buf[i]);
00155         }
00156         if (!(i%2) && (buf[i] != i)) {
00157         errs++;
00158         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00159             mynod, i, buf[i], i);
00160         }
00161     }
00162     else {
00163         if ((i%2) && (buf[i] != i + mynod*SIZE)) {
00164         errs++;
00165         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00166             mynod, i, buf[i], i + mynod*SIZE);
00167         }
00168         if (!(i%2) && (buf[i] != -1)) {
00169         errs++;
00170         fprintf(stderr, "Process %d: buf %d is %d, should be -1\n", 
00171             mynod, i, buf[i]);
00172         }
00173     }
00174     }
00175 
00176     MPI_File_close(&fh);
00177 
00178     MPI_Barrier(MPI_COMM_WORLD);
00179 
00180     if (!mynod) {
00181 #if VERBOSE
00182     fprintf(stderr, "\ntesting contiguous in memory, noncontiguous in file using collective I/O\n");
00183 #endif
00184     MPI_File_delete(filename, MPI_INFO_NULL);
00185     }
00186     MPI_Barrier(MPI_COMM_WORLD);
00187 
00188     MPI_File_open(MPI_COMM_WORLD, filename, MPI_MODE_CREATE | MPI_MODE_RDWR,
00189                   MPI_INFO_NULL, &fh);
00190 
00191     MPI_File_set_view(fh, 0, MPI_INT, newtype, "native", MPI_INFO_NULL);
00192 
00193     for (i=0; i<SIZE; i++) buf[i] = i + mynod*SIZE;
00194     MPI_File_write_all(fh, buf, SIZE, MPI_INT, &status);
00195 
00196     MPI_Barrier(MPI_COMM_WORLD);
00197 
00198     for (i=0; i<SIZE; i++) buf[i] = -1;
00199 
00200     MPI_File_read_at_all(fh, 0, buf, SIZE, MPI_INT, &status);
00201 
00202     for (i=0; i<SIZE; i++) {
00203     if (!mynod) {
00204         if (buf[i] != i) {
00205         errs++;
00206         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00207             mynod, i, buf[i], i);
00208         }
00209     }
00210     else {
00211         if (buf[i] != i + mynod*SIZE) {
00212         errs++;
00213         fprintf(stderr, "Process %d: buf %d is %d, should be %d\n", 
00214             mynod, i, buf[i], i + mynod*SIZE);
00215         }
00216     }
00217     }
00218 
00219     MPI_File_close(&fh);
00220 
00221     MPI_Allreduce( &errs, &toterrs, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD );
00222     if (mynod == 0) {
00223     if( toterrs > 0) {
00224         fprintf( stderr, "Found %d errors\n", toterrs );
00225     }
00226     else {
00227         fprintf( stdout, " No Errors\n" );
00228     }
00229     }
00230 
00231     MPI_Type_free(&newtype);
00232     free(buf);
00233     free(filename);
00234     MPI_Finalize();
00235     return 0;
00236 }