int main(int argc, char *argv[]) { int m, n, c, iters; float kappa; image u, u_bar; unsigned char *image_chars; char *input_jpeg_filename, *output_jpeg_filename; /* read from command line: kappa, iters, input_jpeg_filename, output_jpeg_filename */ kappa = atof(argv[1]); iters = atoi(argv[2]); input_jpeg_filename = argv[3]; output_jpeg_filename = argv[4]; import_JPEG_file(input_jpeg_filename, &image_chars, &m, &n, &c); allocate_image (&u, m, n); allocate_image (&u_bar, m, n); convert_jpeg_to_image (image_chars, &u); iso_diffusion_denoising (&u, &u_bar, kappa, iters); convert_image_to_jpeg (&u, image_chars); export_JPEG_file(output_jpeg_filename, image_chars, m, n, c, 75); deallocate_image (&u); deallocate_image (&u_bar); return 0; }
int main(int argc, char *argv[]) { int m, n, c, iters; float kappa; Image u, u_bar; unsigned char *image_chars; char *input_jpeg_filename, *output_jpeg_filename; /* read from command line: kappa, iters, input_jpeg_filename, output_jpeg_filename */ if (argc > 4) { iters = atoi(argv[1]); kappa = atof(argv[2]); input_jpeg_filename = argv[3]; output_jpeg_filename = argv[4]; } else { printf("Usage: %s iters kappa input_file output_file\n", argv[0]); exit(1); } clock_t begin; double total_time; begin = clock(); /* ... */ import_JPEG_file(input_jpeg_filename, &image_chars, &m, &n, &c); allocate_image (&u, m, n); allocate_image (&u_bar, m, n); convert_jpeg_to_image (image_chars, &u); printf("Performing %d isotropic diffusions ...\n", iters); iso_diffusion_denoising (&u, &u_bar, kappa, iters); convert_image_to_jpeg (&u_bar, image_chars); deallocate_image (&u); deallocate_image (&u_bar); export_JPEG_file(output_jpeg_filename, image_chars, m, n, c, 75); total_time = (double) (clock() - begin) / CLOCKS_PER_SEC; printf("Total execution time: %g\n", total_time); return 0; }
pixel* read_file(char** argv, int* xsize, int* ysize, int* colmax){ FILE* infile; if (!(infile = fopen(argv[2], "r"))) { fprintf(stderr, "Error when opening %s\n", argv[2]); exit(1); } int magic = ppm_readmagicnumber(infile); if (magic != 'P'*256+'6') { fprintf(stderr, "Wrong magic number\n"); exit(1); } *xsize = ppm_readint(infile); *ysize = ppm_readint(infile); *colmax = ppm_readint(infile); if (*colmax > 255) { fprintf(stderr, "Too large maximum color-component value\n"); exit(1); } pixel* image = allocate_image((*xsize)*(*ysize)); if (!fread(image, sizeof(pixel), (*xsize)*(*ysize), infile)) { fprintf(stderr, "error in fread\n"); exit(1); } return image; }
/** * @brief image_t型のクローンを作成する。 * * カラーパレットやイメージデータは内部的に別にメモリを確保しているため、 * allocateした後にmemcpyしてもクローンは作成できない。 * この関数を使ってdeepcopyを行うこと。 * * @param[in] img クローン元image_t型構造体 * @return クローンされたimage_t型構造体 */ image_t *clone_image(image_t *img) { uint32_t i; image_t *new_img = allocate_image(img->width, img->height, img->color_type); if (new_img == NULL) { return NULL; } new_img->palette_num = img->palette_num; if (img->color_type == COLOR_TYPE_INDEX) { memcpy(new_img->palette, img->palette, sizeof(color_t) * img->palette_num); } for (i = 0; i < img->height; i++) { memcpy(new_img->map[i], img->map[i], sizeof(pixcel_t) * img->width); } return new_img; }
int main(int argc, char **argv) { FILE *infile, *outfile; int magic, ok; int radius; int xsize, ysize, colmax; pixel *image; int x,y; int avg, pval, psum, sum = 0; /* Take care of the arguments */ if (argc != 3) { fprintf(stderr, "Usage: %s infile outfile\n", argv[0]); exit(2); } if (!(infile = fopen(argv[1], "r"))) { fprintf(stderr, "Error when opening %s\n", argv[1]); exit(1); } if (!(outfile = fopen(argv[2], "w"))) { fprintf(stderr, "Error when opening %s\n", argv[2]); exit(1); } /* read file */ magic = ppm_readmagicnumber(infile); if (magic != 'P'*256+'6') { fprintf(stderr, "Wrong magic number\n"); exit(1); } xsize = ppm_readint(infile); ysize = ppm_readint(infile); colmax = ppm_readint(infile); if (colmax > 255) { fprintf(stderr, "Too large maximum color-component value\n"); exit(1); } image = allocate_image(xsize*ysize); if (!fread(image, sizeof(pixel), xsize*ysize, infile)) { fprintf(stderr, "error in fread\n"); exit(1); } /* filter */ for (y=0; y<ysize; y++) { for (x=0; x<xsize; x++) { sum += PIXEL(image,x,y)->r; sum += PIXEL(image,x,y)->g; sum += PIXEL(image,x,y)->b; } } avg = sum/(xsize*ysize); for (y=0; y<ysize; y++) { for (x=0; x<xsize; x++) { psum = PIXEL(image,x,y)->r; psum += PIXEL(image,x,y)->g; psum += PIXEL(image,x,y)->b; if (psum > avg) pval = colmax; else pval = 0; PIXEL(image,x,y)->r = pval; PIXEL(image,x,y)->g = pval; PIXEL(image,x,y)->b = pval; } } /* write result */ fprintf(outfile, "P6 %d %d %d\n", xsize, ysize, colmax); if (!fwrite(image, sizeof(pixel), xsize*ysize, outfile)) { fprintf(stderr, "error in fwrite"); exit(1); } exit(0); }
int main(int argc, char **argv) { int ret; ret = MPI_Init(&argc, &argv); check(ret == MPI_SUCCESS, "Failed to init MPI"); struct prog_options o; parse_options(&o, argc, argv); /* We will save the result to a file. Try to open it right ahead so * we don't compute 5 minutes before knowing we don't haveee the rights * on it... */ FILE * outFile = fopen(o.outFileName, "w"); check_null(outFile); /* Compute the steps */ double stepX = (o.area.endX - o.area.startX) / (double)(o.width - 1); double stepY = (o.area.endY - o.area.startY) / (double)(o.height - 1); /* In a first time, check the number of lines is multiple of the number * of nodes. */ int nbNodes, rank; ret = MPI_Comm_size(MPI_COMM_WORLD, &nbNodes); check (ret == MPI_SUCCESS, "Failed to get comm size"); ret = MPI_Comm_rank(MPI_COMM_WORLD, &rank); check (ret == MPI_SUCCESS, "Failed to get comm rank"); /****** Now starts the differentiation between the master node and others *****/ debug("Node %d: handles %d lines from %d\n", rank, lines_at_node(rank, nbNodes, o.height), first_line_of_node(rank, nbNodes, o.height)); /* Only the master node allocates the whole image, others allocate smaller ones */ color_t *image = NULL; if (rank == 0) { image = allocate_image(o.width, o.height); } else { image = allocate_image(o.width, lines_at_node(rank, nbNodes, o.height)); } /* Everybody computes his part of the image */ struct complex_plan_area myArea = { o.area.startX, /* From the left... */ o.area.startY + first_line_of_node(rank, nbNodes, o.height) * stepY, /* start of my slice */ o.area.endX, /* ... to the right */ o.area.startY + (first_line_of_node(rank + 1, nbNodes, o.height) - 1) * stepY, }; ret = compute_window(image, myArea, o.width, lines_at_node(rank, nbNodes, o.height), stepX, stepY, o.threshold, o.maxIter, classic_mandelbrot); check(ret == 0, "Failed to compute the image"); /* Now, the master waits for other to send their results */ MPI_Status status; if (rank == 0) { for (int node = 1; node < nbNodes; node++) { debug("Receiving from node %d...", node); int firstPixel = first_line_of_node(node, nbNodes, o.height) * o.width; int nPixels = lines_at_node(node, nbNodes, o.height) * o.width; ret = MPI_Recv(&image[firstPixel], nPixels, MPI_BYTE, node, MPI_ANY_TAG, MPI_COMM_WORLD, &status); check(ret == MPI_SUCCESS, "Node 0: Failed to receive from node %d\n", node); } /* And save the result to the file */ ret = save_image(image, o.width, o.height, outFile); check(ret == 0, "Failed to save the image to file"); } else { int nPixels = lines_at_node(rank, nbNodes, o.height) * o.width; ret = MPI_Send(image, nPixels, MPI_BYTE, 0, 1, MPI_COMM_WORLD); check(ret == MPI_SUCCESS, "Node %d: failed to send to master", rank); } ret = MPI_Finalize(); check(ret == MPI_SUCCESS, "Failed to finalize MPI"); return 0; }
int thresmain(int argc, char *argv[]) { int thread_count; int xsize, ysize, colmax; pixel * src; pixel * dst; imagethread * imageThreads; thresfilterdata * thresdata; pthread_mutex_t thresholdsum_mutex = PTHREAD_MUTEX_INITIALIZER; unsigned int thresholdsum = 0; int i; char * inputFilepath; char * outputFilepath; struct timespec stime, etime; src = allocate_image(MAX_PIXELS); dst = allocate_image(MAX_PIXELS); /* Take care of the arguments */ if (argc != 4) { fprintf(stderr, "Usage: %s thread_count infile outfile\n", argv[0]); return 1; } thread_count = atoi(argv[1]); if(thread_count < 1){ fprintf(stderr, "Too few threads\n"); return 1; } inputFilepath = strdup(argv[2]); outputFilepath = strdup(argv[3]); /* read file */ if(read_ppm (inputFilepath, &xsize, &ysize, &colmax, (char *) src) != 0) return 1; if (colmax > 255) { fprintf(stderr, "Too large maximum color-component value\n"); return 1; } printf("Creating threads\n"); imageThreads = createThreadData(thread_count); printf("Dividing image\n"); divide(imageThreads, thread_count, src, dst, xsize, ysize); printf("\n"); printf("Setting arguments\n"); thresdata = (thresfilterdata*) malloc(sizeof(thresfilterdata) * thread_count); for(i = 0; i < thread_count; i++){ thresdata[i].xsize = xsize; thresdata[i].ysize = ysize; thresdata[i].src = src; thresdata[i].dst = dst; thresdata[i].thresholdsum = &thresholdsum; thresdata[i].imageThreads = imageThreads; thresdata[i].rank = i; thresdata[i].thresholdsum_mutex = &thresholdsum_mutex; } clock_gettime(CLOCK_REALTIME, &stime); printf("Starting threads\n"); setThreadSyncCount(thread_count); for(i = 0; i < thread_count; i++){ //printf("Starting thread %d\n", i); imageThreads[i].argument = &thresdata[i]; imageThreads[i].thread = createThread(thresfilterwrapper, imageThreads[i].argument); } printf("Threads working on average value\n"); SynchronizationPoint(); printf("Average value is %d\n", thresholdsum/(xsize*ysize)); printf("Threads working on threshold\n"); SynchronizationPoint(); printf("Threads done\n"); clock_gettime(CLOCK_REALTIME, &etime); printf("Filtering took: %g secs\n", (etime.tv_sec - stime.tv_sec) + 1e-9*(etime.tv_nsec - stime.tv_nsec)) ; /* write result */ printf("Writing output file\n"); if(write_ppm (outputFilepath, xsize, ysize, (char *)src) != 0){ return 1; } return 0; }
int main(int argc, char *argv[]) { int m,n,c,iters; int my_m, my_n, my_rank, num_procs, recv_count, my_recv_count, block_size, smallest_block_size; float kappa; image u, u_bar; unsigned char *image_chars, *my_image_chars, *new_image_chars, *my_new_image_chars; char *input_jpeg_filename, *output_jpeg_filename; my_rank = 0; char * kappa_str; MPI_Init(&argc, &argv); MPI_Comm_rank(MPI_COMM_WORLD, &my_rank); MPI_Comm_size(MPI_COMM_WORLD, &num_procs); int displs[num_procs],recvDispls[num_procs],sendCounts[num_procs], recvCounts[num_procs]; int i,my_m_rest; /* *read from command line: kappa,iters,input_jpeg_filename,output_jpeg_filename; */ input_jpeg_filename = argv[1];//riktig char output_jpeg_filename = argv[2];//riktig char kappa_str = (argv[3]);//maa konvertere til double iters = atoi(argv[4]);//maa konvertere til int //printf("iters: %d\n",iters); kappa = 0.01;//TODO:fix so that kappa can be read from the command line kappa = atof(kappa_str); if(my_rank==0){ import_JPEG_file(input_jpeg_filename, &image_chars, &m, &n, &c); } ///////////////////////////////////////////////////////////////// //Broadcasts the size from root(=0) to all the other processes.// ///////////////////////////////////////////////////////////////// MPI_Bcast(&m,1,MPI_INT,0,MPI_COMM_WORLD); MPI_Bcast(&n, 1, MPI_INT, 0, MPI_COMM_WORLD); /* *divide the m x n pixels evenly among the MPI processes */ my_n = n;//this is correct my_m = (m-2)/num_procs;//without ghost points my_m_rest = (m-2)%num_procs; smallest_block_size = my_m*my_n; if(my_rank<my_m_rest){ my_m+=1; } printf("my_m: %d\n", my_m); block_size = my_m*n; ///////////////////////////////////////////////////////////////////////// //the last process get a larger my_m if m/num_procs is a decimal number// ///////////////////////////////////////////////////////////////////////// // if(my_rank==num_procs-1){ // my_m = my_m + (m-2)%num_procs; // } my_recv_count = my_m*my_n; ///////////////////////////////////////////////////// //this is the picture divided into two processes. // n--> // ----------------------- m // | | | // | 0 | v // ----------------------- // | | // | 1 | // ----------------------- /////////////////////////////////////////////////////// allocate_image(&u, my_m, my_n); allocate_image(&u_bar, my_m, my_n); my_image_chars = malloc((block_size+2*n)*(sizeof(int))); if(my_rank==0){ int last_displ=0; int current_block_size; for(i=0;i<my_m_rest;i++){ current_block_size = smallest_block_size + n; sendCounts[i] = current_block_size + 2*n; recvCounts[i] = current_block_size; displs[i] = current_block_size*i; recvDispls[i] = 0; //printf("sendCounts: %d\n", sendCounts[i]); printf("displ: %d\n",displs[i]/n); last_displ = displs[i]; } printf("rest: %d\n", my_m_rest); for(i=my_m_rest;i<num_procs;i++){ printf("%d\n",i); current_block_size = smallest_block_size; printf("%d\n", current_block_size); sendCounts[i] = current_block_size+2*n; recvCounts[i] = current_block_size; if(i==0){ displs[i] = 0; }else{ displs[i] = displs[i-1] + current_block_size; } recvDispls[i] = 0; //printf("sendCounts: %d\n", sendCounts[i]); printf("displ: %d\n", displs[i]/n); } } /* *each process asks process 0 for partitiones region *of image_chars and copy the values into u */ //MPI_Scatterv(image_chars, sendCounts, displs, MPI_CHAR, my_image_chars, recv_count, MPI_CHAR, 0, MPI_COMM_WORLD); //MPI_Scatter(&image_chars, my_m*my_n,MPI_CHAR, &my_image_chars, my_m*my_n, MPI_CHAR, 0,MPI_COMM_WORLD);//assume first that there will be no extra rows //MPI_Scatter(image_chars, block_size, MPI_CHAR, my_image_chars, block_size, MPI_CHAR, 0, MPI_COMM_WORLD); MPI_Scatterv(image_chars, sendCounts, displs, MPI_CHAR, my_image_chars, block_size+2*n, MPI_CHAR, 0, MPI_COMM_WORLD); int start = 0; convert_char_to_float(my_image_chars, &u,my_m+2, my_n,start); //printf("%f", kappa); iso_diffusion_denoising(&u, &u_bar, kappa, iters); /* *each process sends its resulting content of u_bar to process 0 *process 0 receives from each process incoming vaules and *copy them into the designated region of image_chars */ //convert_float_to_char(&image_chars,&u,my_m, my_n,start); int x,y, pict_number,value; for(x=0;x<my_m+2;x++){ for(y=0;y<my_n;y++){ pict_number = x*n + y; value = (int)(u.image_data[x][y]); my_image_chars[pict_number] = (unsigned char) value; } } //MPI_Gather(my_image_chars, block_size, MPI_CHAR, image_chars, block_size, MPI_CHAR, 0,MPI_COMM_WORLD); //MPI_Gatherv(my_image_chars, block_size, MPI_CHAR, image_chars,recvCounts, displs, MPI_CHAR,0, MPI_COMM_WORLD); //MPI_Gatherv(my_image_chars, block_size+2*n, MPI_CHAR, image_chars, sendCounts, displs, MPI_CHAR, 0,MPI_COMM_WORLD); MPI_Send(my_image_chars,block_size+2*n, MPI_CHAR, 0,0, MPI_COMM_WORLD); int k,p; if(my_rank == 0){ //receive the computed my_image_chars from all processes my_new_image_chars = malloc(block_size*sizeof(int)); new_image_chars = malloc(n*m*sizeof(int)); for(i=0;i<n*m;i++){ new_image_chars[i] = 0; } for(i=0;i<num_procs;i++){ MPI_Recv(my_new_image_chars,sendCounts[i], MPI_CHAR,i,0,MPI_COMM_WORLD, MPI_STATUS_IGNORE); start = displs[i];//i*(sendCounts[i]-2*n); for(k=0;k<sendCounts[i];k++){ new_image_chars[start + k]= my_new_image_chars[k]; } } export_JPEG_file(output_jpeg_filename, new_image_chars,m,n,c,75); } deallocate_image(&u); deallocate_image(&u_bar); //printf("Hello World!\n"); MPI_Finalize(); return 0; }
/** * @brief Construct a new image of the given size. * * @param num_rows Number of pixel rows in image. * @param num_cols Number of pixel columns in image. * @param hist The Hist3D object that will provide data for this image. */ Image::Image(int num_rows, int num_cols) : rows(num_rows), cols(num_cols) { allocate_image(); }
/** * @brief Construct a new image of the given size. * * @param num_rows Number of pixel rows in image. * @param num_cols Number of pixel columns in image. * @param hist The Hist3D object that will provide data for this image. */ Image::Image(int num_rows, int num_cols, const Hist3D& hist) : rows(num_rows), cols(num_cols) { allocate_image(); }
int main(int argc, char *argv[]) { int m, n, c, iters, i, j; int my_m, my_n, my_rank, num_procs, size; float kappa; image u, u_bar; unsigned char *image_chars; char *input_jpeg_filename, *output_jpeg_filename; int* sendcounts, displs, recvcounts; sendcounts = (int*)malloc(num_procs*sizeof(int)); displs = (int*)malloc(num_procs*sizeof(int)); recvcounts = (int*)malloc(num_procs*sizeof(int)); printf("Now in main program\n"); MPI_Init (&argc, &argv); MPI_Comm_rank (MPI_COMM_WORLD, &my_rank); MPI_Comm_size (MPI_COMM_WORLD, &num_procs); /* read from kommand line: kappa, iters, input_jpeg filename, output_jpeg_filename */ kappa = atof(argv[1]); iters = atoi(argv[2]); input_jpeg_filename = argv[3]; output_jpeg_filename = argv[4]; /* Test that parameters are read correctly from command line: printf("kappa: %f\n", kappa); printf("iters: %d\n", iters); printf("input_jpeg_filename: %s\n", input_jpeg_filename); printf("output_jpeg_filename: %s\n", output_jpeg_filename); */ if (my_rank==0) import_JPEG_file(input_jpeg_filename, &image_chars, &m, &n, &c); printf("Successfully imported JPEG image.\n"); MPI_Bcast (&m, 1, MPI_INT, 0, MPI_COMM_WORLD); MPI_Bcast (&n, 1, MPI_INT, 0, MPI_COMM_WORLD); /* Divide the m x n pixels evenly among the MPI processes */ my_m = m/num_procs; my_n = n; /* If the pixels cannot be evenly divided, the last process picks up */ /* the remainder. */ /* Each process needs the rows above and below it. */ /* The first and last process only need 1 additional row. */ if (my_rank == num_procs - 1){ my_m += m % num_procs; allocate_image(&u, my_m+1, my_n); allocate_image(&u_bar, my_m+1, my_n); } else if (my_rank == 0){ allocate_image(&u_bar, my_m+1, my_n); } else { allocate_image (&u, my_m+2, my_n); allocate_image (&u_bar, my_m+2, my_n); } /* Each process asks process 0 for a partitioned region */ /* of image_chars and copy the values into u */ if (my_rank==0){ size = (my_m + 1)*my_n; sendcounts[my_rank] = size; displs[my_rank] = my_rank; displs[my_rank+1] = my_n*(my_rank*my_m - 1); } else if (my_rank==num_procs-1){ size = (my_m + 1)*my_n; sendcounts[my_rank] = size; } else { size = (my_m + 2)*my_n; sendcounts[my_rank] = size; displs[my_rank+1] = my_n*(my_rank*my_m - 1); } MPI_Scatterv(&image_chars, &sendcounts, &displs, MPI_UNSIGNED_CHAR, &u.image_data, size, MPI_UNSIGNED_CHAR, 0, MPI_COMM_WORLD); /* Convert data type from unsigned char to float: */ for (i=0; i<my_m; i++) { for (j=0; j<my_n; j++) { u.image_data[i][j] = (float)u.image_data[i][j]; } } iso_diffusion_denoising (&u, &u_bar, kappa, iters); /* Each process must convert the data type in u back */ /* to unsigned char. */ for (i=0; i<my_m; i++) { for (j=0; j<my_n; j++) { u.image_data[i][j] = (unsigned char)u.image_data[i][j]; } } /* Each process sends its resulting content of u to process 0 */ /* Process 0 recieves from each process incoming values and */ /* copy them into the designated region of image_chars */ /* ... */ if (my_rank==0){ displs[my_rank] = 0; displs[my_rank+1] = my_rank*my_m*my_n; size = my_m*my_n if (my_rank==0) c = 1; export_JPEG_file(output_jpeg_filename, image_chars, m, n, c, 75); printf("Successfully exported JPEG image! \n"); deallocate_image(&u); deallocate_image(&u_bar); MPI_Finalize (); printf("Finished the program!\n"); return 0; }