static void omp_force (sotl_device_t *dev) { sotl_atom_set_t *set = &dev->atom_set; tri(set); #pragma omp parallel num_threads(NB_THREAD ) #pragma omp for schedule(static) for (int current = 0; current < (int)set->natoms; current++) { calc_t force[3] = { 0.0, 0.0, 0.0 }; //atome Z supperieur for(int other = current-1;other>-1;other--){ if(abs(set->pos.z[current]-set->pos.z[other]) > LENNARD_SQUARED_CUTOFF){ break; }else{ calc_t sq_dist = squared_distance (set, current, other); if (sq_dist < LENNARD_SQUARED_CUTOFF) { calc_t intensity = lennard_jones (sq_dist); force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); force[1] += intensity * (set->pos.x[set->offset + current] - set->pos.x[set->offset + other]); force[2] += intensity * (set->pos.x[set->offset * 2 + current] - set->pos.x[set->offset * 2 + other]); } } } //atome Z inferieur for(int other = current+1;other<(int)set->natoms;other++){ if(abs(set->pos.z[current]-set->pos.z[other]) > LENNARD_SQUARED_CUTOFF){ break; }else{ calc_t sq_dist = squared_distance (set, current, other); if (sq_dist < LENNARD_SQUARED_CUTOFF) { calc_t intensity = lennard_jones (sq_dist); force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); force[1] += intensity * (set->pos.x[set->offset + current] - set->pos.x[set->offset + other]); force[2] += intensity * (set->pos.x[set->offset * 2 + current] - set->pos.x[set->offset * 2 + other]); } } } set->speed.dx[current] += force[0]; set->speed.dx[set->offset + current] += force[1]; set->speed.dx[set->offset * 2 + current] += force[2]; } }
static void omp_force (sotl_device_t *dev) { sotl_atom_set_t *set = &dev->atom_set; for (unsigned current = 0; current < set->natoms; current++) { calc_t force[3] = { 0.0, 0.0, 0.0 }; for (unsigned other = 0; other < set->natoms; other++) if (current != other) { calc_t sq_dist = squared_distance (set, current, other); if (sq_dist < LENNARD_SQUARED_CUTOFF) { calc_t intensity = lennard_jones (sq_dist); force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); force[1] += intensity * (set->pos.x[set->offset + current] - set->pos.x[set->offset + other]); force[2] += intensity * (set->pos.x[set->offset * 2 + current] - set->pos.x[set->offset * 2 + other]); } } set->speed.dx[current] += force[0]; set->speed.dx[set->offset + current] += force[1]; set->speed.dx[set->offset * 2 + current] += force[2]; } }
static void omp_force (sotl_device_t *dev) { struct timeval tv1,tv2; sotl_atom_set_t *set = &dev->atom_set; gettimeofday(&tv1,NULL); int start_ind, end_ind; #pragma omp parallel for for (unsigned current = 0; current < set->natoms; current++) { calc_t force[3] = { 0.0, 0.0, 0.0 }; // // } // /*Version naive*/ // for (unsigned other = 0; other < set->natoms; other++) // if (current != other) // { // calc_t sq_dist = squared_distance (set, current, other); // // if (sq_dist < LENNARD_SQUARED_CUTOFF) // { // calc_t intensity = lennard_jones (sq_dist); // // force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); // force[1] += intensity * (set->pos.x[set->offset + current] - // set->pos.x[set->offset + other]); // force[2] += intensity * (set->pos.x[set->offset * 2 + current] - // set->pos.x[set->offset * 2 + other]); // } // // } /* Fin version naive */ /** * Version Tri par boites : */ unsigned other; int box_id_current = atom_box_calc(dev, current); if (is_valid_box(dev, box_id_current)) { for (int i = -1; i<2; i++) { for (int j = -1; j<2; j++) { for (int k = -1; k<2; k++) { int box_id_other = get_neighbour(dev, box_id_current, i, j, k); if (is_valid_box(dev, box_id_other)) { start_ind = box_count_cummul[box_id_other]; end_ind = box_count_cummul[box_id_other-1]; int size = start_ind - end_ind; for (int l = 0; l < size; l++) { other = box_count_cummul[box_id_other]-l-1; if (other != current) { calc_t sq_dist = squared_distance (set, current, other); if (sq_dist < LENNARD_SQUARED_CUTOFF) { calc_t intensity = lennard_jones (sq_dist); force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); force[1] += intensity * (set->pos.x[set->offset + current] - set->pos.x[set->offset + other]); force[2] += intensity * (set->pos.x[set->offset * 2 + current] - set->pos.x[set->offset * 2 + other]); } } } } } } } } /*Fin version Tri par Boites */ /** Version Tri par Z : */ // for (unsigned other = current+1; other < set->natoms && ((set->pos.z[other] - set->pos.z[current]) < LENNARD_CUTOFF); other++) // { // //Now takes the atoms near from current according to the sorted array // if (current != other) // { // calc_t sq_dist = squared_distance (set, current, other); // // if (sq_dist < LENNARD_SQUARED_CUTOFF) // { // calc_t intensity = lennard_jones (sq_dist); // // force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); // force[1] += intensity * (set->pos.x[set->offset + current] - // set->pos.x[set->offset + other]); // force[2] += intensity * (set->pos.x[set->offset * 2 + current] - // set->pos.x[set->offset * 2 + other]); // } // } // } // for (unsigned other = current; other > 0 && ((set->pos.z[current] - set->pos.z[other-1]) < LENNARD_CUTOFF); other--) // { // //Now takes the atoms near from current according to the sorted array // if (current != other-1) // { // calc_t sq_dist = squared_distance (set, current, other-1); // // if (sq_dist < LENNARD_SQUARED_CUTOFF) // { // calc_t intensity = lennard_jones (sq_dist); // // force[0] += intensity * (set->pos.x[current] - set->pos.x[other-1]); // force[1] += intensity * (set->pos.x[set->offset + current] - // set->pos.x[set->offset + other-1]); // force[2] += intensity * (set->pos.x[set->offset * 2 + current] - // set->pos.x[set->offset * 2 + other-1]); // } // } // } /*Fin version Tri par Z */ set->speed.dx[current] += force[0]; set->speed.dx[set->offset + current] += force[1]; set->speed.dx[set->offset * 2 + current] += force[2]; } gettimeofday(&tv2,NULL); time_force += (float)TIME_DIFF(tv1,tv2); }
void omp_force_cube(sotl_device_t *dev){ sotl_atom_set_t *set = &dev->atom_set; sotl_domain_t *domain = &dev->domain; sotl_atom_set_t *in = malloc(sizeof(sotl_atom_set_t)); atom_set_init(in,set->natoms,set->offset); for(int i=0; i<(int)set->natoms; i++){ atom_set_add(in,set->pos.x[i],set->pos.y[i],set->pos.z[i],set->speed.dx[i],set->speed.dy[i],set->speed.dz[i]); } int NbCubes = (int) domain->total_boxes; int* boite= calloc(NbCubes,sizeof(int)); int* boiten= calloc(NbCubes,sizeof(int)); for(int i= 0; i < (int)in->natoms; i++){ int numb =atom_get_num_box(domain,in->pos.x[i],in->pos.y[i],in->pos.z[i],LENNARD_SQUARED_CUTOFF); boite[numb]++; boiten[numb]++; } for (int i = 1; i < NbCubes; i++){ boite[i] += boite[i-1]; } for(int i = 0; i < (int)in->natoms; i++){ int numb =atom_get_num_box(domain,in->pos.x[i],in->pos.y[i],in->pos.z[i],LENNARD_SQUARED_CUTOFF); int indice = boite[numb-1]+boiten[numb]-1; set->pos.x[indice]=in->pos.x[i]; set->pos.y[indice]=in->pos.y[i]; set->pos.z[indice]=in->pos.z[i]; set->speed.dx[indice]=in->speed.dx[i]; set->speed.dy[indice]=in->speed.dy[i]; set->speed.dz[indice]=in->speed.dz[i]; boiten[numb]--; } #pragma omp parallel num_threads(NB_THREAD ) #pragma omp for schedule(static) for (int current = 0; current < (int)set->natoms; current++) { calc_t force[3] = { 0.0, 0.0, 0.0 }; int bx =(int)((set->pos.x[current] - domain->min_border[0]) *LENNARD_SQUARED_CUTOFF); int by =(int)((set->pos.y[current] - domain->min_border[1]) *LENNARD_SQUARED_CUTOFF); int bz =(int)((set->pos.z[current] - domain->min_border[2]) *LENNARD_SQUARED_CUTOFF); for(int z =(bz==0)?bz:bz-1; z<= bz+1 && z<(int)domain->boxes[2]; z++){ for(int y=(by==0)?by:by-1; y<= by+1 && y<(int)domain->boxes[1]; y++){ for(int x=(bx==0)?bx:bx-1;x<=bx+1 && x<(int)domain->boxes[0];x++){ int numb = z * domain->boxes[0]* domain->boxes[1] + y * domain->boxes[0] + x; for(int other =(numb==0)?boite[0]:boite[numb-1]; other<boite[numb]; other++){ if(current != other){ calc_t sq_dist = squared_distance (set, current, other); if (sq_dist < LENNARD_SQUARED_CUTOFF) { calc_t intensity = lennard_jones (sq_dist); force[0] += intensity * (set->pos.x[current] - set->pos.x[other]); force[1] += intensity * (set->pos.x[set->offset + current] - set->pos.x[set->offset + other]); force[2] += intensity * (set->pos.x[set->offset * 2 + current] - set->pos.x[set->offset * 2 + other]); } } } } } } set->speed.dx[current] += force[0]; set->speed.dx[set->offset + current] += force[1]; set->speed.dx[set->offset * 2 + current] += force[2]; } free(boiten); atom_set_free(in); free(in); free(boite); }