J'ai une version sérielle de BML et j'essaye d'en écrire une parallèle avec OpenMP. Fondamentalement, mon code fonctionne avec un main
dans une boucle appelant deux fonctions pour les mouvements horizontaux et verticaux. Comme ceci:OpenMP dans le modèle BML de Biham-Middleton-Levine
for (s = 0; s < nmovss; s++) {
horizontal_movs(grid, N);
copy_sides(grid, N);
cur = 1-cur;
vertical_movs(grid, N);
copy_sides(grid, N);
cur = 1-cur;
}
Où cur
est la grille actuelle. Ensuite, les fonctions horizontales et verticales sont similaires et ont une boucle imbriquée:
for(i = 1; i <= n; i++) {
for(j = 1; j <= n+1; j++) {
if(grid[cur][i][j-1] == LR && grid[cur][i][j] == EMPTY) {
grid[1-cur][i][j-1] = EMPTY;
grid[1-cur][i][j] = LR;
}
else {
grid[1-cur][i][j] = grid[cur][i][j];
}
}
}
Le code produit une image de ppm à chaque étape, et petit morceau une certaine entrée de la version de série produire une sortie que l'on peut supposer bien. Mais en utilisant #pragma omp parallel for
à l'intérieur des deux fonctions H et V, les résultats de fichier ppm dédoublées dans ces zones que le nombre de threads (par exemple 4):
Je suppose que le problème est que chaque thread devrait faire les deux fonctionne en séquence avant termit parce que les movememnts sont strictement connectés. Je ne sais pas comment faire ça. Si je place le pragma à un niveau plus élevé comme avant la boucle principale, il n'y a pas d'accélération. Évidemment, le fichier ppm ne doit pas être découpé comme l'image.
Juste une conjecture super sauvage car le niveau de détails que vous donnez est limité (montrez simplement le code parallélisé actuel, ce serait beaucoup plus utile), vous avez oublié de déclarer 'private (j)' dans votre '#pragma omp parallèle pour la ligne. Essayez simplement de l'ajouter et de voir ce qui se passe. – Gilles
@Gilles 'default (none), shared et private' sont omis dans la question mais il y en a dans mon code. – Caramelleamare