OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [tags/] [nog_patch_40/] [or1ksim/] [profiler.c] - Blame information for rev 533

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 173 markom
/* Command line utility, that displays profiling information, generated
2
   by or1ksim. (use -profile option at command line, when running or1ksim.
3
   GNU License (C) Marko Mlinar 2001.  */
4
 
5
#include <stdio.h>
6
 
7
#define MAX_STACK 1024
8
#define MAX_FUNCS 1024
9
 
10
struct stack_struct {
11 533 markom
  /* Function address */
12
  unsigned int addr;
13
 
14
  /* Cycles of function start; cycles of subfunctions are added later */
15 173 markom
  unsigned int cycles;
16 533 markom
 
17
  /* Return address */
18 173 markom
  unsigned int raddr;
19 533 markom
 
20
  /* Name of the function */
21 173 markom
  char name[33];
22
} stack[MAX_STACK];
23
 
24
struct func_struct {
25 533 markom
  /* Start address of function */
26 173 markom
  unsigned int addr;
27 533 markom
 
28
  /* Name of the function */
29 173 markom
  char name[33];
30 533 markom
 
31
  /* Total cycles spent in function */
32 173 markom
  long cum_cycles;
33 533 markom
 
34
  /* Calls to this function */
35 173 markom
  long calls;
36
} func[MAX_FUNCS];
37
 
38 533 markom
/* Total number of functions */
39 173 markom
int nfuncs = 0;
40 533 markom
 
41
/* Current depth */
42 173 markom
int nstack = 0;
43
 
44 533 markom
/* Max depth */
45
int maxstack = 0;
46 173 markom
 
47 533 markom
/* Number of total calls */
48
int ntotcalls = 0;
49
 
50
/* Number of covered calls */
51
int nfunccalls = 0;
52
 
53
/* Current cycles */
54
static int cycles = 0;
55
 
56
/* Whether we are in cumulative mode */
57
static int cumulative = 0;
58
 
59
/* Whether we should not report warnings */
60
static int quiet = 0;
61
 
62
/* File to read from */
63
static FILE *fprof = 0;
64
 
65 173 markom
int main (int argc, char *argv[]) {
66 264 markom
  char fprofname[50] = "sim.profile";
67 173 markom
  int line = 0;
68
  if (argc > 4 || argc < 2) {
69 533 markom
    fprintf (stderr, "USAGE: profiler [--cumulative|-c] [--quiet|-q] --generate|-g [profile_file_name]\n");
70 173 markom
    exit(1);
71
  }
72
  argv++; argc--;
73
  while (argc > 0) {
74 533 markom
    if (!strcmp(argv[0], "-q") || !strcmp(argv[0], "--quiet")) {
75
      quiet = 1;
76
      argv++; argc--;
77
    } else if (!strcmp(argv[0], "-c") || !strcmp(argv[0], "--cumulative")) {
78 173 markom
      cumulative = 1;
79
      argv++; argc--;
80
    } else if (strcmp(argv[0], "-g") && strcmp(argv[0], "--generate")) {
81
      fprintf (stderr, "USAGE: profiler [--cumulative|-c] [--generate|-g] [profile_file_name]\n");
82
      exit(1);
83
    } else {
84
      argv++; argc--;
85
      if (argv[0] && argv[0][0] != '-') {
86
        strcpy (&fprofname[0], argv[0]);
87 239 markom
        argv++; argc--;
88 173 markom
      }
89
    }
90
  }
91
 
92
  fprof = fopen (&fprofname[0], "rt");
93
 
94
  if (!fprof) {
95
    fprintf (stderr, "Cannot open profile file: %s\n", &fprofname[0]);
96
    exit(1);
97
  }
98
 
99
  while (1) {
100
    char dir = fgetc (fprof);
101
    line++;
102
    if (dir == '+') {
103
      if (fscanf (fprof, "%08X %08X %08X %s\n", &stack[nstack].cycles, &stack[nstack].raddr,
104 239 markom
                  &stack[nstack].addr, &stack[nstack].name[0]) != 4)
105
        fprintf (stderr, "Error reading line #%i\n", line);
106 173 markom
      else {
107 533 markom
        cycles = stack[nstack].cycles;
108
        nstack++;
109
        if (nstack > maxstack)
110
          maxstack = nstack;
111
      }
112
      ntotcalls++;
113
    } else if (dir == '-') {
114 173 markom
      struct stack_struct s;
115
      if (fscanf (fprof, "%08X %08X\n", &s.cycles, &s.raddr) != 2)
116 239 markom
        fprintf (stderr, "Error reading line #%i\n", line);
117 173 markom
      else {
118 239 markom
        int i;
119
        cycles = s.cycles;
120
        for (i = nstack - 1; i >= 0; i--)
121
          if (stack[i].raddr == s.raddr) break;
122
        if (i >= 0) {
123 533 markom
          /* pop everything above current from stack,
124 239 markom
             if more than one, something went wrong */
125 533 markom
          while (nstack > i) {
126
            int j;
127
            long time;
128 239 markom
            nstack--;
129 533 markom
            time = s.cycles - stack[nstack].cycles;
130
            if (!quiet && time < 0) {
131
              fprintf (stderr, "WARNING: Negative time at %s (return addr = %08X).\n", stack[i].name, stack[i].raddr);
132
              time = 0;
133
            }
134
 
135
            /* Whether in normal mode, we must substract called function from execution time.  */
136
            if (!cumulative)
137
              for (j = 0; j < nstack; j++)
138
                stack[j].cycles += time;
139
 
140
            if (!quiet && i != nstack)
141 239 markom
              fprintf (stderr, "WARNING: Missaligned return call for %s (%08X) (found %s @ %08X), closing.\n", stack[nstack].name, stack[nstack].raddr, stack[i].name, stack[i].raddr);
142 533 markom
 
143 239 markom
            for (j = 0; j < nfuncs; j++)
144
              if (stack[nstack].addr == func[j].addr) { /* function exists, append. */
145 533 markom
                func[j].cum_cycles += time;
146 239 markom
                func[j].calls++;
147 533 markom
                nfunccalls++;
148 239 markom
                break;
149
              }
150
            if (j >= nfuncs) { /* function does not yet exist, create new. */
151 533 markom
              func[nfuncs].cum_cycles = time;
152 239 markom
              func[nfuncs].calls = 1;
153 533 markom
              nfunccalls++;
154 239 markom
              func[nfuncs].addr = stack[nstack].addr;
155
              strcpy (func[nfuncs].name, stack[nstack].name);
156
              nfuncs++;
157
            }
158
          }
159 533 markom
        } else if (!quiet) fprintf (stderr, "WARNING: Cannot find return call for (%08X), ignoring.\n", s.raddr);
160 173 markom
      }
161
    } else
162
      break;
163
  }
164
  fclose(fprof);
165
 
166
  /* Now we have all data acquired. Print out. */
167
  {
168
    int i, j;
169
    if (cumulative)
170
      printf ("CUMULATIVE TIMES\n");
171
    printf ("---------------------------------------------------------------------------\n");
172
    printf ("|function name            |addr    |# calls |avg cycles  |total cyles     |\n");
173
    printf ("|-------------------------+--------+--------+------------+----------------|\n");
174
    for (j = 0; j < nfuncs; j++) {
175
      int bestcyc = 0, besti = 0;
176
      for (i = 0; i < nfuncs; i++)
177 239 markom
        if (func[i].cum_cycles > bestcyc) {
178
          bestcyc = func[i].cum_cycles;
179
          besti = i;
180
        }
181 173 markom
      i = besti;
182
      printf ("| %-24s|%08X|%8i|%12.1f|%11i,%3.0f%%|\n",
183 239 markom
              func[i].name, func[i].addr, func[i].calls, ((double)func[i].cum_cycles / func[i].calls), func[i].cum_cycles, (100. * func[i].cum_cycles / cycles));
184 173 markom
      func[i].cum_cycles = -1;
185
    }
186
    printf ("---------------------------------------------------------------------------\n");
187
  }
188 533 markom
  printf ("Total %i functions, %i cycles.\n", nfuncs, cycles);
189
  printf ("Total function calls %i/%i (max depth %i).\n", nfunccalls, ntotcalls, maxstack);
190
  return 0;
191 173 markom
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.