priotest.c 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203
  1. /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
  2. /* This Source Code Form is subject to the terms of the Mozilla Public
  3. * License, v. 2.0. If a copy of the MPL was not distributed with this
  4. * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  5. /*
  6. * File: priotest.c
  7. * Purpose: testing priorities
  8. */
  9. #include "prcmon.h"
  10. #include "prinit.h"
  11. #include "prinrval.h"
  12. #include "prlock.h"
  13. #include "prlog.h"
  14. #include "prmon.h"
  15. #include "prprf.h"
  16. #include "prthread.h"
  17. #include "prtypes.h"
  18. #include "plerror.h"
  19. #include "plgetopt.h"
  20. #include <stdio.h>
  21. #include <stdlib.h>
  22. #define DEFAULT_DURATION 5
  23. static PRBool failed = PR_FALSE;
  24. static PRIntervalTime oneSecond;
  25. static PRFileDesc *debug_out = NULL;
  26. static PRBool debug_mode = PR_FALSE;
  27. static PRUint32 PerSecond(PRIntervalTime timein)
  28. {
  29. PRUint32 loop = 0;
  30. while (((PRIntervalTime)(PR_IntervalNow()) - timein) < oneSecond) {
  31. loop += 1;
  32. }
  33. return loop;
  34. } /* PerSecond */
  35. static void PR_CALLBACK Low(void *arg)
  36. {
  37. PRUint32 t3 = 0, t2 = 0, t1 = 0, t0, *tn = (PRUint32*)arg;
  38. while (1)
  39. {
  40. t0 = PerSecond(PR_IntervalNow());
  41. *tn = (t3 + 3 * t2 + 3 * t1 + t0) / 8;
  42. t3 = t2; t2 = t1; t1 = t0;
  43. }
  44. } /* Low */
  45. static void PR_CALLBACK High(void *arg)
  46. {
  47. PRUint32 t3 = 0, t2 = 0, t1 = 0, t0, *tn = (PRUint32*)arg;
  48. while (1)
  49. {
  50. PRIntervalTime timein = PR_IntervalNow();
  51. PR_Sleep(oneSecond >> 2); /* 0.25 seconds */
  52. t0 = PerSecond(timein);
  53. *tn = (t3 + 3 * t2 + 3 * t1 + t0) / 8;
  54. t3 = t2; t2 = t1; t1 = t0;
  55. }
  56. } /* High */
  57. static void Help(void)
  58. {
  59. PR_fprintf(
  60. debug_out, "Usage: priotest [-d] [-c n]\n");
  61. PR_fprintf(
  62. debug_out, "-c n\tduration of test in seconds (default: %d)\n", DEFAULT_DURATION);
  63. PR_fprintf(
  64. debug_out, "-d\tturn on debugging output (default: FALSE)\n");
  65. } /* Help */
  66. static void RudimentaryTests(void)
  67. {
  68. /*
  69. ** Try some rudimentary tests like setting valid priority and
  70. ** getting it back, or setting invalid priorities and getting
  71. ** back a valid answer.
  72. */
  73. PRThreadPriority priority;
  74. PR_SetThreadPriority(PR_GetCurrentThread(), PR_PRIORITY_URGENT);
  75. priority = PR_GetThreadPriority(PR_GetCurrentThread());
  76. failed = ((PR_TRUE == failed) || (PR_PRIORITY_URGENT != priority))
  77. ? PR_TRUE : PR_FALSE;
  78. if (debug_mode && (PR_PRIORITY_URGENT != priority))
  79. {
  80. PR_fprintf(debug_out, "PR_[S/G]etThreadPriority() failed\n");
  81. }
  82. PR_SetThreadPriority(
  83. PR_GetCurrentThread(), (PRThreadPriority)(PR_PRIORITY_FIRST - 1));
  84. priority = PR_GetThreadPriority(PR_GetCurrentThread());
  85. failed = ((PR_TRUE == failed) || (PR_PRIORITY_FIRST != priority))
  86. ? PR_TRUE : PR_FALSE;
  87. if (debug_mode && (PR_PRIORITY_FIRST != priority))
  88. {
  89. PR_fprintf(debug_out, "PR_SetThreadPriority(-1) failed\n");
  90. }
  91. PR_SetThreadPriority(
  92. PR_GetCurrentThread(), (PRThreadPriority)(PR_PRIORITY_LAST + 1));
  93. priority = PR_GetThreadPriority(PR_GetCurrentThread());
  94. failed = ((PR_TRUE == failed) || (PR_PRIORITY_LAST != priority))
  95. ? PR_TRUE : PR_FALSE;
  96. if (debug_mode && (PR_PRIORITY_LAST != priority))
  97. {
  98. PR_fprintf(debug_out, "PR_SetThreadPriority(+1) failed\n");
  99. }
  100. } /* RudimentataryTests */
  101. static void CreateThreads(PRUint32 *lowCount, PRUint32 *highCount)
  102. {
  103. (void)PR_CreateThread(
  104. PR_USER_THREAD, Low, lowCount, PR_PRIORITY_LOW,
  105. PR_LOCAL_THREAD, PR_JOINABLE_THREAD, 0);
  106. (void)PR_CreateThread(
  107. PR_USER_THREAD, High, highCount, PR_PRIORITY_HIGH,
  108. PR_LOCAL_THREAD, PR_JOINABLE_THREAD, 0);
  109. } /* CreateThreads */
  110. int main(int argc, char **argv)
  111. {
  112. PLOptStatus os;
  113. PRIntn duration = DEFAULT_DURATION;
  114. PRUint32 totalCount, highCount = 0, lowCount = 0;
  115. PLOptState *opt = PL_CreateOptState(argc, argv, "hdc:");
  116. debug_out = PR_STDOUT;
  117. oneSecond = PR_SecondsToInterval(1);
  118. while (PL_OPT_EOL != (os = PL_GetNextOpt(opt)))
  119. {
  120. if (PL_OPT_BAD == os) {
  121. continue;
  122. }
  123. switch (opt->option)
  124. {
  125. case 'd': /* debug mode */
  126. debug_mode = PR_TRUE;
  127. break;
  128. case 'c': /* test duration */
  129. duration = atoi(opt->value);
  130. break;
  131. case 'h': /* help message */
  132. default:
  133. Help();
  134. return 2;
  135. }
  136. }
  137. PL_DestroyOptState(opt);
  138. PR_STDIO_INIT();
  139. if (duration == 0) {
  140. duration = DEFAULT_DURATION;
  141. }
  142. RudimentaryTests();
  143. printf("Priority test: running for %d seconds\n\n", duration);
  144. (void)PerSecond(PR_IntervalNow());
  145. totalCount = PerSecond(PR_IntervalNow());
  146. PR_SetThreadPriority(PR_GetCurrentThread(), PR_PRIORITY_URGENT);
  147. if (debug_mode)
  148. {
  149. PR_fprintf(debug_out,
  150. "The high priority thread should get approximately three\n");
  151. PR_fprintf( debug_out,
  152. "times what the low priority thread manages. A maximum of \n");
  153. PR_fprintf( debug_out, "%d cycles are available.\n\n", totalCount);
  154. }
  155. duration = (duration + 4) / 5;
  156. CreateThreads(&lowCount, &highCount);
  157. while (duration--)
  158. {
  159. PRIntn loop = 5;
  160. while (loop--) {
  161. PR_Sleep(oneSecond);
  162. }
  163. if (debug_mode) {
  164. PR_fprintf(debug_out, "high : low :: %d : %d\n", highCount, lowCount);
  165. }
  166. }
  167. PR_ProcessExit((failed) ? 1 : 0);
  168. PR_NOT_REACHED("You can't get here -- but you did!");
  169. return 1; /* or here */
  170. } /* main */
  171. /* priotest.c */