profile.c 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include <unistd.h>
  5. #include <sys/types.h>
  6. #include <fcntl.h>
  7. #include "sys9.h"
  8. extern long* _clock;
  9. extern long _callpc(void**);
  10. extern long _savearg(void);
  11. extern void* sbrk(unsigned long);
  12. typedef unsigned long ulong;
  13. typedef struct Plink Plink;
  14. struct Plink
  15. {
  16. Plink *old; /* known to be 0(ptr) */
  17. Plink *down;
  18. Plink *link;
  19. long pc;
  20. long count;
  21. long time; /* known to be 20(ptr) */
  22. };
  23. struct
  24. {
  25. Plink *pp; /* known to be 0(ptr) */
  26. Plink *next; /* known to be 4(ptr) */
  27. Plink *last;
  28. Plink *first;
  29. } __prof;
  30. ulong
  31. _profin(void)
  32. {
  33. void *dummy;
  34. long pc;
  35. Plink *pp, *p;
  36. ulong arg;
  37. arg = _savearg();
  38. pc = _callpc(&dummy);
  39. pp = __prof.pp;
  40. if(pp == 0)
  41. return arg;
  42. for(p=pp->down; p; p=p->link)
  43. if(p->pc == pc)
  44. goto out;
  45. p = __prof.next + 1;
  46. if(p >= __prof.last) {
  47. __prof.pp = 0;
  48. return arg;
  49. }
  50. __prof.next = p;
  51. p->link = pp->down;
  52. pp->down = p;
  53. p->pc = pc;
  54. p->old = pp;
  55. p->down = 0;
  56. p->count = 0;
  57. out:
  58. __prof.pp = p;
  59. p->count++;
  60. p->time += *_clock;
  61. return arg; /* disgusting linkage */
  62. }
  63. ulong
  64. _profout(void)
  65. {
  66. Plink *p;
  67. ulong arg;
  68. arg = _savearg();
  69. p = __prof.pp;
  70. if(p) {
  71. p->time -= *_clock;
  72. __prof.pp = p->old;
  73. }
  74. return arg;
  75. }
  76. void
  77. _profdump(void)
  78. {
  79. int f;
  80. long n;
  81. Plink *p;
  82. char *vp;
  83. __prof.pp = 0;
  84. f = creat("prof.out", 0666);
  85. if(f < 0) {
  86. perror("create prof.out");
  87. return;
  88. }
  89. __prof.first->time = -*_clock;
  90. vp = (char*)__prof.first;
  91. for(p = __prof.first; p <= __prof.next; p++) {
  92. /*
  93. * short down
  94. */
  95. n = 0xffff;
  96. if(p->down)
  97. n = p->down - __prof.first;
  98. vp[0] = n>>8;
  99. vp[1] = n;
  100. /*
  101. * short right
  102. */
  103. n = 0xffff;
  104. if(p->link)
  105. n = p->link - __prof.first;
  106. vp[2] = n>>8;
  107. vp[3] = n;
  108. vp += 4;
  109. /*
  110. * long pc
  111. */
  112. n = p->pc;
  113. vp[0] = n>>24;
  114. vp[1] = n>>16;
  115. vp[2] = n>>8;
  116. vp[3] = n;
  117. vp += 4;
  118. /*
  119. * long count
  120. */
  121. n = p->count;
  122. vp[0] = n>>24;
  123. vp[1] = n>>16;
  124. vp[2] = n>>8;
  125. vp[3] = n;
  126. vp += 4;
  127. /*
  128. * long time
  129. */
  130. n = -p->time;
  131. vp[0] = n>>24;
  132. vp[1] = n>>16;
  133. vp[2] = n>>8;
  134. vp[3] = n;
  135. vp += 4;
  136. }
  137. write(f, (char*)__prof.first, vp - (char*)__prof.first);
  138. close(f);
  139. }
  140. void
  141. _profmain(void)
  142. {
  143. char ename[50];
  144. int n, f;
  145. n = 1000;
  146. f = _OPEN("/env/profsize", 0);
  147. if(f >= 0) {
  148. memset(ename, 0, sizeof(ename));
  149. _READ(f, ename, sizeof(ename)-1);
  150. _CLOSE(f);
  151. n = atol(ename);
  152. }
  153. __prof.first = sbrk(n*sizeof(Plink));
  154. __prof.last = sbrk(0);
  155. __prof.next = __prof.first;
  156. atexit(_profdump);
  157. *_clock = 1;
  158. }