1 |
48 |
alirezamon |
/*
|
2 |
|
|
* Copyright (c) 2010-2011 The University of Texas at Austin
|
3 |
|
|
* All rights reserved.
|
4 |
|
|
*
|
5 |
|
|
* Redistribution and use in source and binary forms, with or without
|
6 |
|
|
* modification, are permitted provided that the following conditions are
|
7 |
|
|
* met: redistributions of source code must retain the above copyright
|
8 |
|
|
* notice, this list of conditions and the following disclaimer;
|
9 |
|
|
* redistributions in binary form must reproduce the above copyright
|
10 |
|
|
* notice, this list of conditions and the following disclaimer in the
|
11 |
|
|
* documentation and/or other materials provided with the distribution;
|
12 |
|
|
* neither the name of the copyright holders nor the names of its
|
13 |
|
|
* contributors may be used to endorse or promote products derived from
|
14 |
|
|
* this software without specific prior written permission.
|
15 |
|
|
*
|
16 |
|
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
17 |
|
|
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
18 |
|
|
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
|
19 |
|
|
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
|
20 |
|
|
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
21 |
|
|
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
22 |
|
|
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
23 |
|
|
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
24 |
|
|
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
25 |
|
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
26 |
|
|
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
27 |
|
|
*/
|
28 |
|
|
|
29 |
|
|
#include <stdio.h>
|
30 |
|
|
#include <string.h>
|
31 |
|
|
#include "../netrace.h"
|
32 |
|
|
|
33 |
|
|
#define xtod(c) ((c>='0' && c<='9') ? c-'0' : ((c>='A' && c<='F') ? \
|
34 |
|
|
c-'A'+10 : ((c>='a' && c<='f') ? c-'a'+10 : 0)))
|
35 |
|
|
|
36 |
|
|
void print_usage(void);
|
37 |
|
|
int print_packet(nt_packet_t*);
|
38 |
|
|
int xstrtoi( char *hex );
|
39 |
|
|
|
40 |
|
|
int read_flag = 0;
|
41 |
|
|
int print_flag = 0;
|
42 |
|
|
int verify_flag = 0;
|
43 |
|
|
int deps_flag = 0;
|
44 |
|
|
int node_id_to_trace = -1;
|
45 |
|
|
int node_type_to_trace = -1;
|
46 |
|
|
long long int address_to_trace = -1;
|
47 |
|
|
unsigned long long int min_cycle_to_trace = 0;
|
48 |
|
|
unsigned long long int max_cycle_to_trace = -1;
|
49 |
|
|
|
50 |
|
|
int main( int argc, char** argv ) {
|
51 |
|
|
int i;
|
52 |
|
|
unsigned long long int num_dependencies = 0;
|
53 |
|
|
unsigned long long int dep_distance = 0;
|
54 |
|
|
unsigned int verify_id = 0;
|
55 |
|
|
unsigned long long int verify_cycle = 0;
|
56 |
|
|
if( argc < 2 ) {
|
57 |
|
|
print_usage();
|
58 |
|
|
}
|
59 |
|
|
for( i = 2; i < argc; i++ ) {
|
60 |
|
|
if( strcmp(argv[i], "-h") == 0 ) {
|
61 |
|
|
print_usage();
|
62 |
|
|
} else if( strcmp(argv[i], "-d") == 0 ) {
|
63 |
|
|
read_flag = 1;
|
64 |
|
|
deps_flag = 1;
|
65 |
|
|
} else if( strcmp(argv[i], "-p") == 0 ) {
|
66 |
|
|
read_flag = 1;
|
67 |
|
|
print_flag = 1;
|
68 |
|
|
} else if( strcmp(argv[i], "-v") == 0 ) {
|
69 |
|
|
read_flag = 1;
|
70 |
|
|
verify_flag = 1;
|
71 |
|
|
} else if( strcmp(argv[i], "-n") == 0 ) {
|
72 |
|
|
if( argc > ++i ) {
|
73 |
|
|
node_id_to_trace = atoi(argv[i]);
|
74 |
|
|
read_flag = 1;
|
75 |
|
|
print_flag = 1;
|
76 |
|
|
} else {
|
77 |
|
|
fprintf( stderr, "ERROR: Must specify node number to -n\n" );
|
78 |
|
|
print_usage();
|
79 |
|
|
}
|
80 |
|
|
} else if( strcmp(argv[i], "-t") == 0 ) {
|
81 |
|
|
if( argc > ++i ) {
|
82 |
|
|
node_type_to_trace = atoi(argv[i]);
|
83 |
|
|
read_flag = 1;
|
84 |
|
|
print_flag = 1;
|
85 |
|
|
} else {
|
86 |
|
|
fprintf( stderr, "ERROR: Must specify node type to -t\n" );
|
87 |
|
|
print_usage();
|
88 |
|
|
}
|
89 |
|
|
} else if( strcmp(argv[i], "-a") == 0 ) {
|
90 |
|
|
if( argc > ++i ) {
|
91 |
|
|
address_to_trace = xstrtoi(argv[i]);
|
92 |
|
|
read_flag = 1;
|
93 |
|
|
print_flag = 1;
|
94 |
|
|
} else {
|
95 |
|
|
fprintf( stderr, "ERROR: Must specify node type to -t\n" );
|
96 |
|
|
print_usage();
|
97 |
|
|
}
|
98 |
|
|
} else if( strcmp(argv[i], "-m") == 0 ) {
|
99 |
|
|
if( argc > ++i ) {
|
100 |
|
|
min_cycle_to_trace = atol(argv[i]);
|
101 |
|
|
read_flag = 1;
|
102 |
|
|
print_flag = 1;
|
103 |
|
|
} else {
|
104 |
|
|
fprintf( stderr, "ERROR: Must specify node type to -t\n" );
|
105 |
|
|
print_usage();
|
106 |
|
|
}
|
107 |
|
|
} else if( strcmp(argv[i], "-M") == 0 ) {
|
108 |
|
|
if( argc > ++i ) {
|
109 |
|
|
max_cycle_to_trace = atol(argv[i]);
|
110 |
|
|
read_flag = 1;
|
111 |
|
|
print_flag = 1;
|
112 |
|
|
} else {
|
113 |
|
|
fprintf( stderr, "ERROR: Must specify node type to -t\n" );
|
114 |
|
|
print_usage();
|
115 |
|
|
}
|
116 |
|
|
}
|
117 |
|
|
}
|
118 |
|
|
nt_open_trfile( argv[1] );
|
119 |
|
|
nt_print_trheader();
|
120 |
|
|
// @todo on verify flag, check region info by reading all packets
|
121 |
|
|
if( read_flag ) {
|
122 |
|
|
nt_packet_t* packet = nt_read_packet();
|
123 |
|
|
verify_id = packet->id;
|
124 |
|
|
for( /*packet = nt_read_packet()*/; packet != NULL; packet = nt_read_packet() ) {
|
125 |
|
|
if( print_flag ) {
|
126 |
|
|
if( print_packet( packet ) ) {
|
127 |
|
|
nt_print_packet( packet );
|
128 |
|
|
}
|
129 |
|
|
}
|
130 |
|
|
if( verify_flag ) {
|
131 |
|
|
if( packet->id != verify_id++ ) {
|
132 |
|
|
nt_print_packet( packet );
|
133 |
|
|
nt_error( "Packet ID out of sequence" );
|
134 |
|
|
}
|
135 |
|
|
if( packet->cycle < verify_cycle ) {
|
136 |
|
|
nt_print_packet( packet );
|
137 |
|
|
nt_error( "Packet cycle out of sequence" );
|
138 |
|
|
}
|
139 |
|
|
}
|
140 |
|
|
if( deps_flag ) {
|
141 |
|
|
num_dependencies += packet->num_deps;
|
142 |
|
|
for( i = 0; i < packet->num_deps; i++ ) {
|
143 |
|
|
dep_distance += (packet->deps[i] - packet->id);
|
144 |
|
|
}
|
145 |
|
|
}
|
146 |
|
|
nt_clear_dependencies_free_packet( packet );
|
147 |
|
|
}
|
148 |
|
|
}
|
149 |
|
|
nt_close_trfile();
|
150 |
|
|
if( deps_flag ) {
|
151 |
|
|
float avg_dep_distance = (float)dep_distance / (float)num_dependencies;
|
152 |
|
|
printf( "Number of Dependencies: %llu\n", num_dependencies );
|
153 |
|
|
printf( "Average Dependency ID Distance: %f\n", avg_dep_distance );
|
154 |
|
|
}
|
155 |
|
|
return 0;
|
156 |
|
|
}
|
157 |
|
|
|
158 |
|
|
void print_usage() {
|
159 |
|
|
fprintf( stderr, "\nUtility to read and print the header of specified trace file\n" );
|
160 |
|
|
fprintf( stderr, "Usage:\n" );
|
161 |
|
|
fprintf( stderr, "\t./trace_viewer <trace_file> [options]\n" );
|
162 |
|
|
fprintf( stderr, "options:\n" );
|
163 |
|
|
fprintf( stderr, "\t-a # Only print packets accessing a specified address\n" );
|
164 |
|
|
fprintf( stderr, "\t-h Print this help message\n" );
|
165 |
|
|
fprintf( stderr, "\t-n # Only print packets to or from node specified\n" );
|
166 |
|
|
fprintf( stderr, "\t-p Print complete trace\n" );
|
167 |
|
|
fprintf( stderr, "\t-t # Only print packets to or from node type specified:\n" );
|
168 |
|
|
fprintf( stderr, "\t 0 L1 Data Cache\n" );
|
169 |
|
|
fprintf( stderr, "\t 1 L1 Instruction Cache\n" );
|
170 |
|
|
fprintf( stderr, "\t 2 L2 Cache\n" );
|
171 |
|
|
fprintf( stderr, "\t 3 Memory Controller\n" );
|
172 |
|
|
fprintf( stderr, "\t-v Verify the trace correctness\n" );
|
173 |
|
|
fprintf( stderr, "\n" );
|
174 |
|
|
exit(0);
|
175 |
|
|
}
|
176 |
|
|
|
177 |
|
|
int HextoDec( char *hex ) {
|
178 |
|
|
if( *hex == 0 ) return 0;
|
179 |
|
|
return HextoDec(hex-1) * 16 + xtod(*hex);
|
180 |
|
|
}
|
181 |
|
|
|
182 |
|
|
int xstrtoi( char *hex ) {
|
183 |
|
|
return HextoDec( hex + strlen(hex) - 1 );
|
184 |
|
|
}
|
185 |
|
|
|
186 |
|
|
int print_packet( nt_packet_t* packet ) {
|
187 |
|
|
int to_return = 1;
|
188 |
|
|
if( node_id_to_trace >= 0 ) {
|
189 |
|
|
if( node_type_to_trace >= 0 ) {
|
190 |
|
|
if( ( packet->src == node_id_to_trace && nt_get_src_type(packet) == node_type_to_trace ) ||
|
191 |
|
|
( packet->dst == node_id_to_trace && nt_get_dst_type(packet) == node_type_to_trace ) ) {
|
192 |
|
|
// return 1;
|
193 |
|
|
} else {
|
194 |
|
|
to_return = 0;
|
195 |
|
|
}
|
196 |
|
|
} else {
|
197 |
|
|
if( ( packet->src == node_id_to_trace ) || ( packet->dst == node_id_to_trace ) ) {
|
198 |
|
|
// return 1;
|
199 |
|
|
} else {
|
200 |
|
|
to_return = 0;
|
201 |
|
|
}
|
202 |
|
|
}
|
203 |
|
|
} else {
|
204 |
|
|
if( node_type_to_trace >= 0 ) {
|
205 |
|
|
if( ( nt_get_src_type(packet) == node_type_to_trace ) ||
|
206 |
|
|
( nt_get_dst_type(packet) == node_type_to_trace ) ) {
|
207 |
|
|
// return 1;
|
208 |
|
|
} else {
|
209 |
|
|
to_return = 0;
|
210 |
|
|
}
|
211 |
|
|
}
|
212 |
|
|
}
|
213 |
|
|
if( packet->cycle < min_cycle_to_trace || packet->cycle > max_cycle_to_trace ) {
|
214 |
|
|
to_return = 0;
|
215 |
|
|
}
|
216 |
|
|
if( address_to_trace >= 0 && packet->addr != address_to_trace ) {
|
217 |
|
|
to_return = 0;
|
218 |
|
|
}
|
219 |
|
|
return to_return;
|
220 |
|
|
}
|