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

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

Issue 18120003: Update XRay to support x86-64 (RDTSC), use dladdr() as an optional way to (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: 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 | Annotate | Revision Log
« no previous file with comments | « native_client_sdk/src/libraries/xray/xray.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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 <alloca.h> 9 #include <alloca.h>
10 #include <assert.h> 10 #include <assert.h>
11 #include <errno.h> 11 #include <errno.h>
12 #include <stdarg.h> 12 #include <stdarg.h>
13 #include <stdint.h> 13 #include <stdint.h>
14 #include <stdio.h> 14 #include <stdio.h>
15 #include <stdlib.h> 15 #include <stdlib.h>
16 #include <string.h> 16 #include <string.h>
17 #include <unistd.h> 17 #include <unistd.h>
18 #include "xray/xray_priv.h" 18 #include "xray/xray_priv.h"
19 19
20 #if defined(XRAY) 20 #if defined(XRAY)
21 21
22 #define FORCE_INLINE __attribute__((always_inline))
23
24 #if defined(__amd64__)
25 FORCE_INLINE uint64_t RDTSC64() {
26 uint64_t a, d;
27 __asm__ __volatile__("rdtsc" : "=a" (a), "=d" (d));
28 return ((uint64_t)a) | (((uint64_t)d) << 32);
29 }
30 #define RDTSC(_x) _x = RDTSC64()
31 #else
22 #define RDTSC(_x) __asm__ __volatile__ ("rdtsc" : "=A" (_x)); 32 #define RDTSC(_x) __asm__ __volatile__ ("rdtsc" : "=A" (_x));
23 #define FORCE_INLINE __attribute__((always_inline)) 33 #endif
34
24 35
25 /* Use a TLS variable for cheap thread uid. */ 36 /* Use a TLS variable for cheap thread uid. */
26 volatile __thread int g_xray_thread_id; 37 volatile __thread int g_xray_thread_id;
27 38
28 39
29 struct XRayTraceStackEntry { 40 struct XRayTraceStackEntry {
30 uint32_t depth_addr; 41 uint32_t depth_addr;
31 uint64_t tsc; 42 uint64_t tsc;
32 uint32_t dest; 43 uint32_t dest;
33 uint32_t annotation_index; 44 uint32_t annotation_index;
(...skipping 550 matching lines...) Expand 10 before | Expand all | Expand 10 after
584 int XRayTraceBufferNextEntry(int index) { 595 int XRayTraceBufferNextEntry(int index) {
585 if (XRayTraceBufferIsAnnotation(index)) 596 if (XRayTraceBufferIsAnnotation(index))
586 index = XRayTraceBufferSkipAnnotation(index); 597 index = XRayTraceBufferSkipAnnotation(index);
587 else 598 else
588 index = XRayTraceBufferIncrementIndex(index); 599 index = XRayTraceBufferIncrementIndex(index);
589 return index; 600 return index;
590 } 601 }
591 602
592 603
593 /* Dumps the trace report for a given frame. */ 604 /* Dumps the trace report for a given frame. */
594 void XRayTraceReport(FILE* f, int frame, char* label, float cutoff) { 605 void XRayTraceReport(FILE* f, int frame, char* label,
606 float percent_cutoff, int ticks_cutoff) {
595 int index; 607 int index;
596 int start; 608 int start;
597 int end; 609 int end;
598 float total; 610 float total;
599 int bad_depth = 0;
600 char space[257]; 611 char space[257];
601 memset(space, ' ', 256); 612 memset(space, ' ', 256);
602 space[256] = 0; 613 space[256] = 0;
603 if (NULL == f) { 614 if (NULL == f) {
604 f = stdout; 615 f = stdout;
605 } 616 }
606 fprintf(f, 617 fprintf(f,
607 "======================================================================\n"); 618 "======================================================================\n");
608 if (NULL != label) 619 if (NULL != label)
609 fprintf(f, "label %s\n", label); 620 fprintf(f, "label %s\n", label);
610 fprintf(f, "\n"); 621 fprintf(f, "\n");
611 fprintf(f, 622 fprintf(f,
612 " Address Ticks Percent Function <optional annotation>\n"); 623 " Address Ticks Percent Function <optional annotation>\n");
613 fprintf(f, 624 fprintf(f,
614 "----------------------------------------------------------------------\n"); 625 "----------------------------------------------------------------------\n");
615 start = g_xray.frame.entry[frame].start; 626 start = g_xray.frame.entry[frame].start;
616 end = g_xray.frame.entry[frame].end; 627 end = g_xray.frame.entry[frame].end;
617 total = (float)g_xray.frame.entry[frame].total_ticks; 628 total = (float)g_xray.frame.entry[frame].total_ticks;
618 index = start; 629 index = start;
619 while (index != end) { 630 while (index != end) {
620 if (!XRayTraceBufferIsAnnotation(index)) { 631 if (!XRayTraceBufferIsAnnotation(index)) {
621 const char* symbol_name; 632 const char* symbol_name;
622 char annotation[1024]; 633 char annotation[1024];
623 struct XRayTraceBufferEntry* e = &g_xray.buffer[index]; 634 struct XRayTraceBufferEntry* e = &g_xray.buffer[index];
624 uint32_t depth = XRAY_EXTRACT_DEPTH(e->depth_addr); 635 uint32_t depth = XRAY_EXTRACT_DEPTH(e->depth_addr);
625 uint32_t addr = XRAY_EXTRACT_ADDR(e->depth_addr); 636 uint32_t addr = XRAY_EXTRACT_ADDR(e->depth_addr);
626 uint32_t ticks = (e->ticks); 637 uint32_t ticks = (e->ticks);
627 uint32_t annotation_index = (e->annotation_index); 638 uint32_t annotation_index = (e->annotation_index);
628 float percent = 100.0f * (float)ticks / total; 639 float percent = 100.0f * (float)ticks / total;
629 if (percent >= cutoff) { 640 if (percent >= percent_cutoff && ticks >= ticks_cutoff) {
630 if (depth > 250) bad_depth++;
631 struct XRaySymbol* symbol; 641 struct XRaySymbol* symbol;
632 symbol = XRaySymbolTableLookup(g_xray.symbols, addr); 642 symbol = XRaySymbolTableLookup(g_xray.symbols, addr);
633 symbol_name = XRaySymbolGetName(symbol); 643 symbol_name = XRaySymbolGetName(symbol);
634 if (0 != annotation_index) { 644 if (0 != annotation_index) {
635 XRayTraceBufferCopyToString(annotation_index, annotation); 645 XRayTraceBufferCopyToString(annotation_index, annotation);
636 } else { 646 } else {
637 strcpy(annotation, ""); 647 strcpy(annotation, "");
638 } 648 }
639 fprintf(f, "0x%08X %10ld %5.1f %s%s %s\n", 649 fprintf(f, "0x%08X %10ld %5.1f %s%s %s\n",
640 (unsigned int)addr, (int64_t)ticks, percent, 650 (unsigned int)addr, (int64_t)ticks, percent,
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after
717 index, 727 index,
718 (int64_t)total_ticks, 728 (int64_t)total_ticks,
719 capture_size, 729 capture_size,
720 annotation_count, 730 annotation_count,
721 label); 731 label);
722 } 732 }
723 } 733 }
724 734
725 735
726 /* Dump a frame report followed by trace report(s) for each frame. */ 736 /* Dump a frame report followed by trace report(s) for each frame. */
727 void XRayReport(FILE* f, float cutoff) { 737 void XRayReport(FILE* f, float percent_cutoff, int ticks_cutoff) {
728 int head; 738 int head;
729 int index; 739 int index;
730 int counter = 0; 740 int counter = 0;
731 fprintf(f, "Number of symbols: %d\n", XRaySymbolCount(g_xray.symbols)); 741 if (g_xray.symbols)
742 fprintf(f, "Number of symbols: %d\n", XRaySymbolCount(g_xray.symbols));
732 XRayFrameReport(f); 743 XRayFrameReport(f);
733 fprintf(f, "\n"); 744 fprintf(f, "\n");
734 head = g_xray.frame.head; 745 head = g_xray.frame.head;
735 index = g_xray.frame.tail; 746 index = g_xray.frame.tail;
736 while (index != head) { 747 while (index != head) {
737 char label[XRAY_MAX_LABEL]; 748 char label[XRAY_MAX_LABEL];
738 fprintf(f, "\n"); 749 fprintf(f, "\n");
739 XRayFrameMakeLabel(counter, label); 750 XRayFrameMakeLabel(counter, label);
740 XRayTraceReport(f, index, label, cutoff); 751 XRayTraceReport(f, index, label, percent_cutoff, ticks_cutoff);
741 index = XRayFrameNext(index); 752 index = XRayFrameNext(index);
753
742 ++counter; 754 ++counter;
743 } 755 }
744 fprintf(f, 756 fprintf(f,
745 "======================================================================\n"); 757 "======================================================================\n");
746 #if defined(XRAY_OUTPUT_HASH_COLLISIONS) 758 #if defined(XRAY_OUTPUT_HASH_COLLISIONS)
747 XRayHashTableHisto(f); 759 XRayHashTableHisto(f);
748 #endif 760 #endif
761 fflush(f);
749 } 762 }
750 763
751 764
752 /* Write a profile report to text file. */ 765 /* Write a profile report to text file. */
753 void XRaySaveReport(const char* filename, float cutoff) { 766 void XRaySaveReport(const char* filename,
767 float percent_cutoff,
768 int ticks_cutoff) {
754 FILE* f; 769 FILE* f;
755 f = fopen(filename, "wt"); 770 f = fopen(filename, "wt");
756 if (NULL != f) { 771 if (NULL != f) {
757 XRayReport(f, cutoff); 772 XRayReport(f, percent_cutoff, ticks_cutoff);
758 fclose(f); 773 fclose(f);
759 } 774 }
760 } 775 }
761 776
762 777
763 /* Initialize XRay */ 778 /* Initialize XRay */
764 void XRayInit(int stack_depth, int buffer_size, int frame_count, 779 void XRayInit(int stack_depth, int buffer_size, int frame_count,
765 const char* mapfilename) { 780 const char* mapfilename) {
766 int adj_frame_count = frame_count + 1; 781 int adj_frame_count = frame_count + 1;
767 assert(false == g_xray.initialized); 782 assert(false == g_xray.initialized);
(...skipping 13 matching lines...) Expand all
781 g_xray.disabled = 0; 796 g_xray.disabled = 0;
782 g_xray.annotation_filter = 0xFFFFFFFF; 797 g_xray.annotation_filter = 0xFFFFFFFF;
783 g_xray.guard0 = XRAY_GUARD_VALUE; 798 g_xray.guard0 = XRAY_GUARD_VALUE;
784 g_xray.guard1 = XRAY_GUARD_VALUE; 799 g_xray.guard1 = XRAY_GUARD_VALUE;
785 g_xray.guard2 = XRAY_GUARD_VALUE; 800 g_xray.guard2 = XRAY_GUARD_VALUE;
786 g_xray.initialized = true; 801 g_xray.initialized = true;
787 XRaySetMaxStackDepth(stack_depth); 802 XRaySetMaxStackDepth(stack_depth);
788 XRayReset(); 803 XRayReset();
789 804
790 /* Mapfile is optional; we don't need it for captures, only for reports. */ 805 /* Mapfile is optional; we don't need it for captures, only for reports. */
791 if (NULL != mapfilename) { 806 g_xray.symbols = XRaySymbolTableCreate(XRAY_DEFAULT_SYMBOL_TABLE_SIZE);
792 g_xray.symbols = XRaySymbolTableCreate(XRAY_DEFAULT_SYMBOL_TABLE_SIZE); 807 if (NULL != mapfilename)
793 XRaySymbolTableParseMapfile(g_xray.symbols, mapfilename); 808 XRaySymbolTableParseMapfile(g_xray.symbols, mapfilename);
794 }
795 } 809 }
796 810
797 811
798 /* Shut down and free memory used by XRay. */ 812 /* Shut down and free memory used by XRay. */
799 void XRayShutdown() { 813 void XRayShutdown() {
800 assert(true == g_xray.initialized); 814 assert(true == g_xray.initialized);
801 assert(NULL == g_xray.recording); 815 assert(NULL == g_xray.recording);
802 XRayCheckGuards(); 816 XRayCheckGuards();
803 if (NULL != g_xray.symbols) { 817 if (NULL != g_xray.symbols) {
804 XRaySymbolTableFree(g_xray.symbols); 818 XRaySymbolTableFree(g_xray.symbols);
805 } 819 }
806 XRayFree(g_xray.frame.entry); 820 XRayFree(g_xray.frame.entry);
807 XRayFree(g_xray.buffer); 821 XRayFree(g_xray.buffer);
808 g_xray.initialized = false; 822 g_xray.initialized = false;
809 } 823 }
810 824
811 #endif /* XRAY */ 825 #endif /* XRAY */
812 826
OLDNEW
« no previous file with comments | « native_client_sdk/src/libraries/xray/xray.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698