367 lines · c
1// RUN: %libomp-compile-and-run2#include <stdio.h>3#include <math.h>4#include "omp_testsuite.h"5 6#define DOUBLE_DIGITS 20 /* dt^DOUBLE_DIGITS */7#define MAX_FACTOR 108#define KNOWN_PRODUCT 3628800 /* 10! */9 10int test_omp_atomic()11{12 int sum;13 int diff;14 double dsum = 0;15 double dt = 0.5; /* base of geometric row for + and - test*/16 double ddiff;17 int product;18 int x;19 int *logics;20 int bit_and = 1;21 int bit_or = 0;22 int exclusiv_bit_or = 0;23 int j;24 int known_sum;25 int known_diff;26 int known_product;27 int result = 0;28 int logic_and = 1;29 int logic_or = 0;30 double dknown_sum;31 double rounding_error = 1.E-9;32 double dpt, div;33 int logicsArray[LOOPCOUNT];34 logics = logicsArray;35 36 sum = 0;37 diff = 0;38 product = 1;39 40 // sum of integers test41 #pragma omp parallel42 {43 int i;44 #pragma omp for45 for (i = 1; i <= LOOPCOUNT; i++) {46 #pragma omp atomic47 sum += i;48 }49 50 }51 known_sum = (LOOPCOUNT * (LOOPCOUNT + 1)) / 2;52 if (known_sum != sum)53 {54 fprintf(stderr,55 "Error in sum with integers: Result was %d instead of %d.\n",56 sum, known_sum);57 result++;58 }59 60 // difference of integers test61 #pragma omp parallel62 {63 int i;64 #pragma omp for65 for (i = 0; i < LOOPCOUNT; i++) {66 #pragma omp atomic67 diff -= i;68 }69 }70 known_diff = ((LOOPCOUNT - 1) * LOOPCOUNT) / 2 * -1;71 if (diff != known_diff)72 {73 fprintf (stderr,74 "Error in difference with integers: Result was %d instead of 0.\n",75 diff);76 result++;77 }78 79 // sum of doubles test80 dsum = 0;81 dpt = 1;82 for (j = 0; j < DOUBLE_DIGITS; ++j) {83 dpt *= dt;84 }85 dknown_sum = (1 - dpt) / (1 -dt);86 #pragma omp parallel87 {88 int i;89 #pragma omp for90 for (i = 0; i < DOUBLE_DIGITS; ++i) {91 #pragma omp atomic92 dsum += pow (dt, i);93 }94 }95 if (dsum != dknown_sum && (fabs (dsum - dknown_sum) > rounding_error)) {96 fprintf (stderr, "Error in sum with doubles: Result was %f"97 " instead of: %f (Difference: %E)\n",98 dsum, dknown_sum, dsum - dknown_sum);99 result++;100 }101 102 // difference of doubles test103 dpt = 1;104 for (j = 0; j < DOUBLE_DIGITS; ++j) {105 dpt *= dt;106 }107 ddiff = (1 - dpt) / (1 - dt);108 #pragma omp parallel109 {110 int i;111 #pragma omp for112 for (i = 0; i < DOUBLE_DIGITS; ++i) {113 #pragma omp atomic114 ddiff -= pow (dt, i);115 }116 }117 if (fabs (ddiff) > rounding_error) {118 fprintf (stderr,119 "Error in difference with doubles: Result was %E instead of 0.0\n",120 ddiff);121 result++;122 }123 124 // product of integers test125 #pragma omp parallel126 {127 int i;128 #pragma omp for129 for (i = 1; i <= MAX_FACTOR; i++) {130 #pragma omp atomic131 product *= i;132 }133 }134 known_product = KNOWN_PRODUCT;135 if (known_product != product) {136 fprintf (stderr,137 "Error in product with integers: Result was %d instead of %d\n",138 product, known_product);139 result++;140 }141 142 // division of integers test143 product = KNOWN_PRODUCT;144 #pragma omp parallel145 {146 int i;147 #pragma omp for148 for (i = 1; i <= MAX_FACTOR; ++i) {149 #pragma omp atomic150 product /= i;151 }152 }153 if (product != 1) {154 fprintf (stderr,155 "Error in product division with integers: Result was %d"156 " instead of 1\n",157 product);158 result++;159 }160 161 // division of doubles test162 div = 5.0E+5;163 #pragma omp parallel164 {165 int i;166 #pragma omp for167 for (i = 1; i <= MAX_FACTOR; i++) {168 #pragma omp atomic169 div /= i;170 }171 }172 if (fabs(div-0.137787) >= 1.0E-4 ) {173 result++;174 fprintf (stderr, "Error in division with double: Result was %f"175 " instead of 0.137787\n", div);176 }177 178 // ++ test179 x = 0;180 #pragma omp parallel181 {182 int i;183 #pragma omp for184 for (i = 0; i < LOOPCOUNT; ++i) {185 #pragma omp atomic186 x++;187 }188 }189 if (x != LOOPCOUNT) {190 result++;191 fprintf (stderr, "Error in ++\n");192 }193 194 // -- test195 #pragma omp parallel196 {197 int i;198 #pragma omp for199 for (i = 0; i < LOOPCOUNT; ++i) {200 #pragma omp atomic201 x--;202 }203 }204 if (x != 0) {205 result++;206 fprintf (stderr, "Error in --\n");207 }208 209 // bit-and test part 1210 for (j = 0; j < LOOPCOUNT; ++j) {211 logics[j] = 1;212 }213 bit_and = 1;214 #pragma omp parallel215 {216 int i;217 #pragma omp for218 for (i = 0; i < LOOPCOUNT; ++i) {219 #pragma omp atomic220 bit_and &= logics[i];221 }222 }223 if (!bit_and) {224 result++;225 fprintf (stderr, "Error in BIT AND part 1\n");226 }227 228 // bit-and test part 2229 bit_and = 1;230 logics[LOOPCOUNT / 2] = 0;231 #pragma omp parallel232 {233 int i;234 #pragma omp for235 for (i = 0; i < LOOPCOUNT; ++i) {236 #pragma omp atomic237 bit_and &= logics[i];238 }239 }240 if (bit_and) {241 result++;242 fprintf (stderr, "Error in BIT AND part 2\n");243 }244 245 // bit-or test part 1246 for (j = 0; j < LOOPCOUNT; j++) {247 logics[j] = 0;248 }249 bit_or = 0;250 #pragma omp parallel251 {252 int i;253 #pragma omp for254 for (i = 0; i < LOOPCOUNT; ++i) {255 #pragma omp atomic256 bit_or |= logics[i];257 }258 }259 if (bit_or) {260 result++;261 fprintf (stderr, "Error in BIT OR part 1\n");262 }263 264 // bit-or test part 2265 bit_or = 0;266 logics[LOOPCOUNT / 2] = 1;267 #pragma omp parallel268 {269 270 int i;271 #pragma omp for272 for (i = 0; i < LOOPCOUNT; ++i) {273 #pragma omp atomic274 bit_or |= logics[i];275 }276 }277 if (!bit_or) {278 result++;279 fprintf (stderr, "Error in BIT OR part 2\n");280 }281 282 // bit-xor test part 1283 for (j = 0; j < LOOPCOUNT; j++) {284 logics[j] = 0;285 }286 exclusiv_bit_or = 0;287 #pragma omp parallel288 {289 int i;290 #pragma omp for291 for (i = 0; i < LOOPCOUNT; ++i) {292 #pragma omp atomic293 exclusiv_bit_or ^= logics[i];294 }295 }296 if (exclusiv_bit_or) {297 result++;298 fprintf (stderr, "Error in EXCLUSIV BIT OR part 1\n");299 }300 301 // bit-xor test part 2302 exclusiv_bit_or = 0;303 logics[LOOPCOUNT / 2] = 1;304 #pragma omp parallel305 {306 int i;307 #pragma omp for308 for (i = 0; i < LOOPCOUNT; ++i) {309 #pragma omp atomic310 exclusiv_bit_or ^= logics[i];311 }312 313 }314 if (!exclusiv_bit_or) {315 result++;316 fprintf (stderr, "Error in EXCLUSIV BIT OR part 2\n");317 }318 319 // left shift test320 x = 1;321 #pragma omp parallel322 {323 int i;324 #pragma omp for325 for (i = 0; i < 10; ++i) {326 #pragma omp atomic327 x <<= 1;328 }329 330 }331 if ( x != 1024) {332 result++;333 fprintf (stderr, "Error in <<\n");334 x = 1024;335 }336 337 // right shift test338 #pragma omp parallel339 {340 int i;341 #pragma omp for342 for (i = 0; i < 10; ++i) {343 #pragma omp atomic344 x >>= 1;345 }346 }347 if (x != 1) {348 result++;349 fprintf (stderr, "Error in >>\n");350 }351 352 return (result == 0);353} // test_omp_atomic()354 355int main()356{357 int i;358 int num_failed=0;359 360 for(i = 0; i < REPETITIONS; i++) {361 if(!test_omp_atomic()) {362 num_failed++;363 }364 }365 return num_failed;366}367