1 /*************************************************************************
2 * *
3 * Vega FEM Simulation Library Version 3.1 *
4 * *
5 * "distance field" library , Copyright (C) 2007 CMU, 2016 USC *
6 * All rights reserved. *
7 * *
8 * Code authors: Jernej Barbic, Hongyi Xu, Yijing Li *
9 * http://www.jernejbarbic.com/code *
10 * *
11 * Research: Jernej Barbic, Hongyi Xu, Doug L. James *
12 * *
13 * Funding: National Science Foundation, Link Foundation, *
14 * Zumberge Research and Innovation Fund at USC *
15 * *
16 * This library is free software; you can redistribute it and/or *
17 * modify it under the terms of the BSD-style license that is *
18 * included with this library in the file LICENSE.txt *
19 * *
20 * This library is distributed in the hope that it will be useful, *
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the file *
23 * LICENSE.TXT for more details. *
24 * *
25 *************************************************************************/
26
27 /*
28 Multithreaded computation of the distance field.
29 */
30
31 #include <stdlib.h>
32 #include <stdio.h>
33 #include <string.h>
34 #include <float.h>
35
36 #include <pthread.h>
37
38 #include "distanceFieldMT.h"
39
40
DistanceFieldMT(int numThreads_)41 DistanceFieldMT::DistanceFieldMT(int numThreads_) : DistanceField(), numThreads(numThreads_)
42 {
43 }
44
DistanceFieldMT(int resolutionX_,int resolutionY_,int resolutionZ_,int numThreads_)45 DistanceFieldMT::DistanceFieldMT(int resolutionX_, int resolutionY_, int resolutionZ_, int numThreads_): DistanceField(resolutionX_, resolutionY_, resolutionZ_), numThreads(numThreads_)
46 {
47 }
48
Setup()49 void DistanceFieldMT::Setup()
50 {
51 // split the workload
52 startSlice = (int*) malloc (sizeof(int) * numThreads);
53 endSlice = (int*) malloc (sizeof(int) * numThreads);
54
55 int totalSlices = (zMax - zMin + 1);
56
57 int remainder = totalSlices % numThreads;
58 // the first 'remainder' nodes will process one element more
59 int jobSize = totalSlices / numThreads;
60
61 for(int rank=0; rank < numThreads; rank++)
62 {
63 if (rank < remainder)
64 {
65 startSlice[rank] = zMin + rank * (jobSize+1);
66 endSlice[rank] = zMin + (rank+1) * (jobSize+1);
67 }
68 else
69 {
70 startSlice[rank] = zMin + remainder * (jobSize+1) + (rank-remainder) * jobSize;
71 endSlice[rank] = zMin + remainder * (jobSize+1) + ((rank-remainder)+1) * jobSize;
72 }
73 }
74
75 printf("Total slices: %d \n", totalSlices);
76 printf("Num threads: %d \n", numThreads);
77 printf("Canonical job size: %d \n", jobSize);
78 printf("Num threads with job size augmented by one element: %d \n", remainder);
79 }
80
~DistanceFieldMT()81 DistanceFieldMT::~DistanceFieldMT()
82 {
83 }
84
GetStartSlice(int rank)85 int DistanceFieldMT::GetStartSlice(int rank)
86 {
87 return startSlice[rank];
88 }
89
GetEndSlice(int rank)90 int DistanceFieldMT::GetEndSlice(int rank)
91 {
92 return endSlice[rank];
93 }
94
95 // the routines for signed and unsigned distance field computation
96 #define COMPUTE_SIGNED_FIELD
97 #define COMPUTE_FLOOD_FIELD
98 #include "computeFieldMT.cpp"
99 #undef COMPUTE_FLOOD_FIELD
100 #include "computeFieldMT.cpp"
101 #undef COMPUTE_SIGNED_FIELD
102 #include "computeFieldMT.cpp"
103
104