Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(330)

Side by Side Diff: native_client_sdk/src/libraries/xray/xray.c

Issue 19409003: Update Xray for PNaCl (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: use TLS address for threadid Created 7 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* Copyright (c) 2013 The Chromium Authors. All rights reserved. 1 /* Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 * Use of this source code is governed by a BSD-style license that can be 2 * Use of this source code is governed by a BSD-style license that can be
3 * found in the LICENSE file. 3 * found in the LICENSE file.
4 */ 4 */
5 5
6 6
7 /* XRay -- a simple profiler for Native Client */ 7 /* XRay -- a simple profiler for Native Client */
8 8
9 #include <assert.h> 9 #include <assert.h>
10 #include <errno.h> 10 #include <errno.h>
(...skipping 22 matching lines...) Expand all
33 #define GTSC(_x) __asm__ __volatile__ ("rdtsc" : "=A" (_x)); 33 #define GTSC(_x) __asm__ __volatile__ ("rdtsc" : "=A" (_x));
34 #else 34 #else
35 FORCE_INLINE uint64_t GTOD() { 35 FORCE_INLINE uint64_t GTOD() {
36 struct timeval tv; 36 struct timeval tv;
37 gettimeofday(&tv, NULL); 37 gettimeofday(&tv, NULL);
38 return (uint64_t)tv.tv_sec * 1000000 + (uint64_t)tv.tv_usec; 38 return (uint64_t)tv.tv_sec * 1000000 + (uint64_t)tv.tv_usec;
39 } 39 }
40 #define GTSC(_x) _x = GTOD(); 40 #define GTSC(_x) _x = GTOD();
41 #endif 41 #endif
42 42
43
44 /* Use a TLS variable for cheap thread uid. */ 43 /* Use a TLS variable for cheap thread uid. */
45 __thread struct XRayTraceCapture* g_xray_capture = NULL; 44 __thread struct XRayTraceCapture* g_xray_capture = NULL;
46 45
47 46
48 struct XRayTraceStackEntry { 47 struct XRayTraceStackEntry {
49 uint32_t depth_addr; 48 uint32_t depth_addr;
50 uint64_t tsc; 49 uint64_t tsc;
51 uint32_t dest; 50 uint32_t dest;
52 uint32_t annotation_index; 51 uint32_t annotation_index;
53 }; 52 };
54 53
55 54
56 struct XRayTraceFrameEntry { 55 struct XRayTraceFrameEntry {
57 /* Indices into global tracebuffer */ 56 /* Indices into global tracebuffer */
58 int start; 57 int start;
59 int end; 58 int end;
60 uint64_t start_tsc; 59 uint64_t start_tsc;
61 uint64_t end_tsc; 60 uint64_t end_tsc;
62 uint64_t total_ticks; 61 uint64_t total_ticks;
63 int annotation_count; 62 int annotation_count;
64 bool valid; 63 bool valid;
64
65 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
66 struct XRayTimestampPair start_time;
67 struct XRayTimestampPair end_time;
68 #endif
65 }; 69 };
66 70
67 71
68 struct XRayTraceFrame { 72 struct XRayTraceFrame {
69 struct XRayTraceFrameEntry* entry; 73 struct XRayTraceFrameEntry* entry;
70 int head; 74 int head;
71 int tail; 75 int tail;
72 int count; 76 int count;
73 }; 77 };
74 78
(...skipping 11 matching lines...) Expand all
86 bool initialized; 90 bool initialized;
87 uint32_t annotation_filter; 91 uint32_t annotation_filter;
88 uint32_t guard0; 92 uint32_t guard0;
89 struct XRayTraceStackEntry stack[XRAY_TRACE_STACK_SIZE] XRAY_ALIGN64; 93 struct XRayTraceStackEntry stack[XRAY_TRACE_STACK_SIZE] XRAY_ALIGN64;
90 uint32_t guard1; 94 uint32_t guard1;
91 uint32_t guard2; 95 uint32_t guard2;
92 char annotation[XRAY_ANNOTATION_STACK_SIZE] XRAY_ALIGN64; 96 char annotation[XRAY_ANNOTATION_STACK_SIZE] XRAY_ALIGN64;
93 uint32_t guard3; 97 uint32_t guard3;
94 struct XRayTraceBufferEntry* buffer; 98 struct XRayTraceBufferEntry* buffer;
95 struct XRayTraceFrame frame; 99 struct XRayTraceFrame frame;
100
101 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
102 int32_t thread_id;
103 #endif
96 } XRAY_ALIGN64; 104 } XRAY_ALIGN64;
97 105
98 106
99 #ifdef __cplusplus 107 #ifdef __cplusplus
100 extern "C" { 108 extern "C" {
101 #endif 109 #endif
102 110
103 XRAY_NO_INSTRUMENT void __cyg_profile_func_enter(void* this_fn, 111 #if defined(__pnacl__)
104 void* call_site); 112 XRAY_NO_INSTRUMENT void __pnacl_profile_func_enter(const char* fname);
105 XRAY_NO_INSTRUMENT void __cyg_profile_func_exit(void* this_fn, 113 XRAY_NO_INSTRUMENT void __pnacl_profile_func_exit(const char* fname);
106 void* call_site); 114 #else
115 XRAY_NO_INSTRUMENT void __cyg_profile_func_enter(
116 void* this_fn, void* call_site);
117 XRAY_NO_INSTRUMENT void __cyg_profile_func_exit(void* this_fn, void* call_site);
118 #endif
119
107 XRAY_NO_INSTRUMENT void __xray_profile_append_annotation( 120 XRAY_NO_INSTRUMENT void __xray_profile_append_annotation(
108 struct XRayTraceCapture* capture, 121 struct XRayTraceCapture* capture,
109 struct XRayTraceStackEntry* se, 122 struct XRayTraceStackEntry* se,
110 struct XRayTraceBufferEntry* be); 123 struct XRayTraceBufferEntry* be);
111 124
112 #ifdef __cplusplus 125 #ifdef __cplusplus
113 } 126 }
114 #endif 127 #endif
115 128
116
117 /* Asserts that the guard values haven't changed. */ 129 /* Asserts that the guard values haven't changed. */
118 void XRayCheckGuards(struct XRayTraceCapture* capture) { 130 void XRayCheckGuards(struct XRayTraceCapture* capture) {
119 assert(capture->guard0 == XRAY_GUARD_VALUE_0x12345678); 131 assert(capture->guard0 == XRAY_GUARD_VALUE_0x12345678);
120 assert(capture->guard1 == XRAY_GUARD_VALUE_0x12345678); 132 assert(capture->guard1 == XRAY_GUARD_VALUE_0x12345678);
121 assert(capture->guard2 == XRAY_GUARD_VALUE_0x87654321); 133 assert(capture->guard2 == XRAY_GUARD_VALUE_0x87654321);
122 assert(capture->guard3 == XRAY_GUARD_VALUE_0x12345678); 134 assert(capture->guard3 == XRAY_GUARD_VALUE_0x12345678);
123 } 135 }
124 136
125 /* Decrements the trace index, wrapping around if needed. */ 137 /* Decrements the trace index, wrapping around if needed. */
126 XRAY_FORCE_INLINE int XRayTraceDecrementIndexInline( 138 XRAY_FORCE_INLINE int XRayTraceDecrementIndexInline(
(...skipping 169 matching lines...) Expand 10 before | Expand all | Expand 10 after
296 } 308 }
297 309
298 310
299 /* Generic memory free for XRay */ 311 /* Generic memory free for XRay */
300 void XRayFree(void* data) { 312 void XRayFree(void* data) {
301 assert(NULL != data); 313 assert(NULL != data);
302 free(data); 314 free(data);
303 } 315 }
304 316
305 317
306 318 #if defined(__pnacl__)
307 /* Main profile capture function that is called at the start */ 319 /* Main profile capture function that is called at the start */
308 /* of every instrumented function. This function is implicitly */ 320 /* of every instrumented function. This function is implicitly */
309 /* called when code is compilied with the -finstrument-functions option */ 321 /* called when code is compilied with the -finstrument-functions option */
322 void __pnacl_profile_func_enter(const char* fname) {
nfullagar1 2013/07/18 00:47:22 (you may have missed this one from last round) sug
323 struct XRayTraceCapture* capture = g_xray_capture;
324 if (capture && capture->recording) {
325 uint32_t depth = capture->stack_depth;
326 if (depth < capture->max_stack_depth) {
327 struct XRayTraceStackEntry* se = &capture->stack[depth];
328 uint32_t addr = (uint32_t)fname;
329 se->depth_addr = XRAY_PACK_DEPTH_ADDR(depth, addr);
330 se->dest = capture->buffer_index;
331 se->annotation_index = 0;
332 GTSC(se->tsc);
333 capture->buffer_index =
334 XRayTraceIncrementIndexInline(capture, capture->buffer_index);
335 }
336 ++capture->stack_depth;
337 }
338 }
339
340
341 /* Main profile capture function that is called at the exit of */
342 /* every instrumented function. This function is implicity called */
343 /* when the code is compiled with the -finstrument-functions option */
344 void __pnacl_profile_func_exit(const char* fname) {
345 struct XRayTraceCapture* capture = g_xray_capture;
346 if (capture && capture->recording) {
347 --capture->stack_depth;
348 if (capture->stack_depth < capture->max_stack_depth) {
349 uint32_t depth = capture->stack_depth;
350 struct XRayTraceStackEntry* se = &capture->stack[depth];
351 uint32_t buffer_index = se->dest;
352 uint64_t tsc;
353 struct XRayTraceBufferEntry* be = &capture->buffer[buffer_index];
354 GTSC(tsc);
355 be->depth_addr = se->depth_addr;
356 be->start_tick = se->tsc;
357 be->end_tick = tsc;
358 be->annotation_index = 0;
359 if (0 != se->annotation_index)
360 __xray_profile_append_annotation(capture, se, be);
361 }
362 }
363 }
364 #else
365 /* Main profile capture function that is called at the start */
366 /* of every instrumented function. This function is implicitly */
367 /* called when code is compilied with the -finstrument-functions option */
310 void __cyg_profile_func_enter(void* this_fn, void* call_site) { 368 void __cyg_profile_func_enter(void* this_fn, void* call_site) {
311 struct XRayTraceCapture* capture = g_xray_capture; 369 struct XRayTraceCapture* capture = g_xray_capture;
312 if (capture && capture->recording) { 370 if (capture && capture->recording) {
313 uint32_t depth = capture->stack_depth; 371 uint32_t depth = capture->stack_depth;
314 if (depth < capture->max_stack_depth) { 372 if (depth < capture->max_stack_depth) {
315 struct XRayTraceStackEntry* se = &capture->stack[depth]; 373 struct XRayTraceStackEntry* se = &capture->stack[depth];
316 uint32_t addr = (uint32_t)this_fn; 374 uint32_t addr = (uint32_t)this_fn;
317 se->depth_addr = XRAY_PACK_DEPTH_ADDR(depth, addr); 375 se->depth_addr = XRAY_PACK_DEPTH_ADDR(depth, addr);
318 se->dest = capture->buffer_index; 376 se->dest = capture->buffer_index;
319 se->annotation_index = 0; 377 se->annotation_index = 0;
(...skipping 22 matching lines...) Expand all
342 GTSC(tsc); 400 GTSC(tsc);
343 be->depth_addr = se->depth_addr; 401 be->depth_addr = se->depth_addr;
344 be->start_tick = se->tsc; 402 be->start_tick = se->tsc;
345 be->end_tick = tsc; 403 be->end_tick = tsc;
346 be->annotation_index = 0; 404 be->annotation_index = 0;
347 if (0 != se->annotation_index) 405 if (0 != se->annotation_index)
348 __xray_profile_append_annotation(capture, se, be); 406 __xray_profile_append_annotation(capture, se, be);
349 } 407 }
350 } 408 }
351 } 409 }
410 #endif /* __pnacl__ */
352 411
412 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
413 void XRayGetTSC(uint64_t* tsc) {GTSC(*tsc);}
nfullagar1 2013/07/18 00:47:22 above: unless it is inlined in a class, avoid putt
grosse 2013/07/18 01:26:40 Done.
414
415 int32_t XRayGetThreadID(struct XRayTraceCapture* capture) {
nfullagar1 2013/07/18 00:47:22 Need a brief comment here that ret val is the thre
grosse 2013/07/18 01:26:40 Done.
416 return capture->thread_id;
417 }
418
419 struct XRayTimestampPair* XRayGetTimestamp(
420 struct XRayTraceCapture* capture, int frame, bool end) {
421
422 struct XRayTraceFrameEntry* entry = &(capture->frame.entry[frame]);
423 return end ? &entry->end_time : &entry->start_time;
424 }
425 #endif
353 426
354 /* Special case appending annotation string to trace buffer */ 427 /* Special case appending annotation string to trace buffer */
355 /* this function should only ever be called from __cyg_profile_func_exit() */ 428 /* this function should only ever be called from __cyg_profile_func_exit() */
356 void __xray_profile_append_annotation(struct XRayTraceCapture* capture, 429 void __xray_profile_append_annotation(struct XRayTraceCapture* capture,
357 struct XRayTraceStackEntry* se, 430 struct XRayTraceStackEntry* se,
358 struct XRayTraceBufferEntry* be) { 431 struct XRayTraceBufferEntry* be) {
359 struct XRayTraceStackEntry* parent = se - 1; 432 struct XRayTraceStackEntry* parent = se - 1;
360 int start = parent->annotation_index; 433 int start = parent->annotation_index;
361 be->annotation_index = capture->buffer_index; 434 be->annotation_index = capture->buffer_index;
362 char* str = &capture->annotation[start]; 435 char* str = &capture->annotation[start];
(...skipping 203 matching lines...) Expand 10 before | Expand all | Expand 10 after
566 /* The trace stack[0] is reserved */ 639 /* The trace stack[0] is reserved */
567 memset(&capture->stack[0], 0, sizeof(capture->stack[0])); 640 memset(&capture->stack[0], 0, sizeof(capture->stack[0]));
568 /* Annotation index 0 is reserved to indicate no annotation */ 641 /* Annotation index 0 is reserved to indicate no annotation */
569 capture->stack[0].annotation_index = 1; 642 capture->stack[0].annotation_index = 1;
570 capture->annotation[0] = 0; 643 capture->annotation[0] = 0;
571 capture->annotation[1] = 0; 644 capture->annotation[1] = 0;
572 capture->annotation_count = 0; 645 capture->annotation_count = 0;
573 capture->recording = true; 646 capture->recording = true;
574 GTSC(capture->frame.entry[i].start_tsc); 647 GTSC(capture->frame.entry[i].start_tsc);
575 g_xray_capture = capture; 648 g_xray_capture = capture;
649
650 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
651 capture->frame.entry[i].start_time = XRayGenerateTimestampsNow();
652 #endif /* XRAY_DISABLE_BROWSER_INTEGRATION */
nfullagar1 2013/07/18 00:47:22 code style is to have two spaces between #endif an
grosse 2013/07/18 01:26:40 Done.
653
576 } 654 }
577 655
578 656
579 /* Ends a frame and disables capturing. Advances to the next frame. */ 657 /* Ends a frame and disables capturing. Advances to the next frame. */
580 /* Must be paired with XRayStartFrame(), and called from the same thread. */ 658 /* Must be paired with XRayStartFrame(), and called from the same thread. */
581 void XRayEndFrame(struct XRayTraceCapture* capture) { 659 void XRayEndFrame(struct XRayTraceCapture* capture) {
582 int i; 660 int i;
583 assert(capture); 661 assert(capture);
584 assert(capture->initialized); 662 assert(capture->initialized);
585 assert(capture->recording); 663 assert(capture->recording);
(...skipping 19 matching lines...) Expand all
605 if (be->depth_addr != XRAY_FRAME_MARKER) { 683 if (be->depth_addr != XRAY_FRAME_MARKER) {
606 fprintf(stderr, 684 fprintf(stderr,
607 "XRay: XRayStopFrame() detects insufficient trace buffer size!\n"); 685 "XRay: XRayStopFrame() detects insufficient trace buffer size!\n");
608 XRayReset(capture); 686 XRayReset(capture);
609 } else { 687 } else {
610 /* Replace marker with an empty annotation string. */ 688 /* Replace marker with an empty annotation string. */
611 be->depth_addr = XRAY_NULL_ANNOTATION; 689 be->depth_addr = XRAY_NULL_ANNOTATION;
612 XRayCheckGuards(capture); 690 XRayCheckGuards(capture);
613 } 691 }
614 g_xray_capture = NULL; 692 g_xray_capture = NULL;
693
694 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
695 capture->frame.entry[i].end_time = XRayGenerateTimestampsNow();
696 #endif /* XRAY_DISABLE_BROWSER_INTEGRATION */
615 } 697 }
616 698
617 699
618 /* Get the last frame captured. Do not call while capturing. */ 700 /* Get the last frame captured. Do not call while capturing. */
619 /* (ie call outside of XRayStartFrame() / XRayStopFrame() pair) */ 701 /* (ie call outside of XRayStartFrame() / XRayStopFrame() pair) */
620 int XRayGetLastFrame(struct XRayTraceCapture* capture) { 702 int XRayGetLastFrame(struct XRayTraceCapture* capture) {
621 assert(capture); 703 assert(capture);
622 assert(capture->initialized); 704 assert(capture->initialized);
623 assert(!capture->recording); 705 assert(!capture->recording);
624 assert(0 == capture->disabled); 706 assert(0 == capture->disabled);
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
692 capture->recording = false; 774 capture->recording = false;
693 XRaySetMaxStackDepth(capture, stack_depth); 775 XRaySetMaxStackDepth(capture, stack_depth);
694 XRayReset(capture); 776 XRayReset(capture);
695 777
696 /* Mapfile is optional; we don't need it for captures, only for reports. */ 778 /* Mapfile is optional; we don't need it for captures, only for reports. */
697 capture->symbols = 779 capture->symbols =
698 XRaySymbolTableCreate(XRAY_DEFAULT_SYMBOL_TABLE_SIZE); 780 XRaySymbolTableCreate(XRAY_DEFAULT_SYMBOL_TABLE_SIZE);
699 if (NULL != mapfilename) 781 if (NULL != mapfilename)
700 XRaySymbolTableParseMapfile(capture->symbols, mapfilename); 782 XRaySymbolTableParseMapfile(capture->symbols, mapfilename);
701 783
784 #ifndef XRAY_DISABLE_BROWSER_INTEGRATION
785 capture->thread_id = (int32_t)(&g_xray_capture);
nfullagar1 2013/07/18 00:47:22 Suggest having a separate '__thread int g_xray_tid
grosse 2013/07/18 01:26:40 Done.
786 #endif
787
702 return capture; 788 return capture;
703 } 789 }
704 790
705 791
706 /* Shut down and free memory used by XRay. */ 792 /* Shut down and free memory used by XRay. */
707 void XRayShutdown(struct XRayTraceCapture* capture) { 793 void XRayShutdown(struct XRayTraceCapture* capture) {
708 assert(capture); 794 assert(capture);
709 assert(capture->initialized); 795 assert(capture->initialized);
710 assert(!capture->recording); 796 assert(!capture->recording);
711 XRayCheckGuards(capture); 797 XRayCheckGuards(capture);
712 if (NULL != capture->symbols) { 798 if (NULL != capture->symbols) {
713 XRaySymbolTableFree(capture->symbols); 799 XRaySymbolTableFree(capture->symbols);
714 } 800 }
715 XRayFree(capture->frame.entry); 801 XRayFree(capture->frame.entry);
716 XRayFree(capture->buffer); 802 XRayFree(capture->buffer);
717 capture->initialized = false; 803 capture->initialized = false;
718 XRayFree(capture); 804 XRayFree(capture);
719 } 805 }
720 806
721 #endif /* XRAY */ 807 #endif /* XRAY */
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698