thread-test.c 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. #include "utils.h"
  2. #ifndef HAVE_PTHREADS
  3. int main ()
  4. {
  5. printf ("Skipped thread-test - pthreads not supported\n");
  6. return 0;
  7. }
  8. #else
  9. #include <stdlib.h>
  10. #include <pthread.h>
  11. typedef struct
  12. {
  13. int thread_no;
  14. uint32_t *dst_buf;
  15. prng_t prng_state;
  16. } info_t;
  17. static const pixman_op_t operators[] =
  18. {
  19. PIXMAN_OP_SRC,
  20. PIXMAN_OP_OVER,
  21. PIXMAN_OP_ADD,
  22. PIXMAN_OP_CLEAR,
  23. PIXMAN_OP_SRC,
  24. PIXMAN_OP_DST,
  25. PIXMAN_OP_OVER,
  26. PIXMAN_OP_OVER_REVERSE,
  27. PIXMAN_OP_IN,
  28. PIXMAN_OP_IN_REVERSE,
  29. PIXMAN_OP_OUT,
  30. PIXMAN_OP_OUT_REVERSE,
  31. PIXMAN_OP_ATOP,
  32. PIXMAN_OP_ATOP_REVERSE,
  33. PIXMAN_OP_XOR,
  34. PIXMAN_OP_ADD,
  35. PIXMAN_OP_MULTIPLY,
  36. PIXMAN_OP_SCREEN,
  37. PIXMAN_OP_OVERLAY,
  38. PIXMAN_OP_DARKEN,
  39. PIXMAN_OP_LIGHTEN,
  40. PIXMAN_OP_HARD_LIGHT,
  41. PIXMAN_OP_DIFFERENCE,
  42. PIXMAN_OP_EXCLUSION,
  43. };
  44. static const pixman_format_code_t formats[] =
  45. {
  46. PIXMAN_a8r8g8b8,
  47. PIXMAN_r5g6b5,
  48. PIXMAN_a8,
  49. PIXMAN_a4,
  50. PIXMAN_a1,
  51. PIXMAN_b5g6r5,
  52. PIXMAN_r8g8b8a8,
  53. PIXMAN_a4r4g4b4
  54. };
  55. #define N_ROUNDS 8192
  56. #define RAND_ELT(arr) \
  57. arr[prng_rand_r(&info->prng_state) % ARRAY_LENGTH (arr)]
  58. #define DEST_WIDTH (7)
  59. static void *
  60. thread (void *data)
  61. {
  62. info_t *info = data;
  63. uint32_t crc32 = 0x0;
  64. uint32_t src_buf[64];
  65. pixman_image_t *dst_img, *src_img;
  66. int i;
  67. prng_srand_r (&info->prng_state, info->thread_no);
  68. for (i = 0; i < N_ROUNDS; ++i)
  69. {
  70. pixman_op_t op;
  71. int rand1, rand2;
  72. prng_randmemset_r (&info->prng_state, info->dst_buf,
  73. DEST_WIDTH * sizeof (uint32_t), 0);
  74. prng_randmemset_r (&info->prng_state, src_buf,
  75. sizeof (src_buf), 0);
  76. src_img = pixman_image_create_bits (
  77. RAND_ELT (formats), 4, 4, src_buf, 16);
  78. dst_img = pixman_image_create_bits (
  79. RAND_ELT (formats), DEST_WIDTH, 1, info->dst_buf,
  80. DEST_WIDTH * sizeof (uint32_t));
  81. image_endian_swap (src_img);
  82. image_endian_swap (dst_img);
  83. rand2 = prng_rand_r (&info->prng_state) % 4;
  84. rand1 = prng_rand_r (&info->prng_state) % 4;
  85. op = RAND_ELT (operators);
  86. pixman_image_composite32 (
  87. op,
  88. src_img, NULL, dst_img,
  89. rand1, rand2, 0, 0, 0, 0, DEST_WIDTH, 1);
  90. crc32 = compute_crc32_for_image (crc32, dst_img);
  91. pixman_image_unref (src_img);
  92. pixman_image_unref (dst_img);
  93. }
  94. return (void *)(uintptr_t)crc32;
  95. }
  96. static inline uint32_t
  97. byteswap32 (uint32_t x)
  98. {
  99. return ((x & ((uint32_t)0xFF << 24)) >> 24) |
  100. ((x & ((uint32_t)0xFF << 16)) >> 8) |
  101. ((x & ((uint32_t)0xFF << 8)) << 8) |
  102. ((x & ((uint32_t)0xFF << 0)) << 24);
  103. }
  104. int
  105. main (void)
  106. {
  107. uint32_t dest[16 * DEST_WIDTH];
  108. info_t info[16] = { { 0 } };
  109. pthread_t threads[16];
  110. void *retvals[16];
  111. uint32_t crc32s[16], crc32;
  112. int i;
  113. for (i = 0; i < 16; ++i)
  114. {
  115. info[i].thread_no = i;
  116. info[i].dst_buf = &dest[i * DEST_WIDTH];
  117. }
  118. for (i = 0; i < 16; ++i)
  119. pthread_create (&threads[i], NULL, thread, &info[i]);
  120. for (i = 0; i < 16; ++i)
  121. pthread_join (threads[i], &retvals[i]);
  122. for (i = 0; i < 16; ++i)
  123. {
  124. crc32s[i] = (uintptr_t)retvals[i];
  125. if (is_little_endian())
  126. crc32s[i] = byteswap32 (crc32s[i]);
  127. }
  128. crc32 = compute_crc32 (0, crc32s, sizeof crc32s);
  129. #define EXPECTED 0x82C4D9FB
  130. if (crc32 != EXPECTED)
  131. {
  132. printf ("thread-test failed. Got checksum 0x%08X, expected 0x%08X\n",
  133. crc32, EXPECTED);
  134. return 1;
  135. }
  136. return 0;
  137. }
  138. #endif