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

Side by Side Diff: tools/foozzie/v8_suppressions.py

Issue 2635923002: [foozzie] Refactoring - move source hashing to main script (Closed)
Patch Set: Created 3 years, 11 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
« no previous file with comments | « tools/foozzie/v8_foozzie_test.py ('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 2016 the V8 project authors. All rights reserved. 1 # Copyright 2016 the V8 project 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 Suppressions for V8 correctness fuzzer failures. 6 Suppressions for V8 correctness fuzzer failures.
7 7
8 We support three types of suppressions: 8 We support three types of suppressions:
9 1. Ignore test case by pattern. 9 1. Ignore test case by pattern.
10 Map a regular expression to a bug entry. A new failure will be reported 10 Map a regular expression to a bug entry. A new failure will be reported
11 when the pattern matches a JS test case. 11 when the pattern matches a JS test case.
12 Subsequent matches will be recoreded under the first failure. 12 Subsequent matches will be recoreded under the first failure.
13 13
14 2. Ignore test run by output pattern: 14 2. Ignore test run by output pattern:
15 Map a regular expression to a bug entry. A new failure will be reported 15 Map a regular expression to a bug entry. A new failure will be reported
16 when the pattern matches the output of a particular run. 16 when the pattern matches the output of a particular run.
17 Subsequent matches will be recoreded under the first failure. 17 Subsequent matches will be recoreded under the first failure.
18 18
19 3. Relax line-to-line comparisons with expressions of lines to ignore and 19 3. Relax line-to-line comparisons with expressions of lines to ignore and
20 lines to be normalized (i.e. ignore only portions of lines). 20 lines to be normalized (i.e. ignore only portions of lines).
21 These are not tied to bugs, be careful to not silently switch off this tool! 21 These are not tied to bugs, be careful to not silently switch off this tool!
22 22
23 Alternatively, think about adding a behavior change to v8_suppressions.js 23 Alternatively, think about adding a behavior change to v8_suppressions.js
24 to silence a particular class of problems. 24 to silence a particular class of problems.
25 """ 25 """
26 26
27 import hashlib
28 import itertools 27 import itertools
29 import re 28 import re
30 29
31 # Max line length for regular experessions checking for lines to ignore. 30 # Max line length for regular experessions checking for lines to ignore.
32 MAX_LINE_LENGTH = 512 31 MAX_LINE_LENGTH = 512
33 32
34 # For ignoring lines before carets and to ignore caret positions. 33 # For ignoring lines before carets and to ignore caret positions.
35 CARET_RE = re.compile(r'^\s*\^\s*$') 34 CARET_RE = re.compile(r'^\s*\^\s*$')
36 35
37 # Ignore by original source files. Map from bug->relative file paths in V8, 36 # Ignore by original source files. Map from bug->relative file paths in V8,
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
133 ] 132 ]
134 133
135 134
136 ############################################################################### 135 ###############################################################################
137 # Implementation - you should not need to change anything below this point. 136 # Implementation - you should not need to change anything below this point.
138 137
139 # Compile regular expressions. 138 # Compile regular expressions.
140 ALLOWED_LINE_DIFFS = [re.compile(exp) for exp in ALLOWED_LINE_DIFFS] 139 ALLOWED_LINE_DIFFS = [re.compile(exp) for exp in ALLOWED_LINE_DIFFS]
141 IGNORE_LINES = [re.compile(exp) for exp in IGNORE_LINES] 140 IGNORE_LINES = [re.compile(exp) for exp in IGNORE_LINES]
142 141
143 # The number of hex digits used from the hash of the original source file path.
144 # Keep the number small to avoid duplicate explosion.
145 SOURCE_HASH_LENGTH = 3
146
147 ORIGINAL_SOURCE_PREFIX = 'v8-foozzie source: ' 142 ORIGINAL_SOURCE_PREFIX = 'v8-foozzie source: '
148 ORIGINAL_SOURCE_DEFAULT = 'none'
149 143
150 def line_pairs(lines): 144 def line_pairs(lines):
151 return itertools.izip_longest( 145 return itertools.izip_longest(
152 lines, itertools.islice(lines, 1, None), fillvalue=None) 146 lines, itertools.islice(lines, 1, None), fillvalue=None)
153 147
154 148
155 def caret_match(line1, line2): 149 def caret_match(line1, line2):
156 if (not line1 or 150 if (not line1 or
157 not line2 or 151 not line2 or
158 len(line1) > MAX_LINE_LENGTH or 152 len(line1) > MAX_LINE_LENGTH or
(...skipping 17 matching lines...) Expand all
176 match2 = exp.match(line2) 170 match2 = exp.match(line2)
177 if match1 and match2: 171 if match1 and match2:
178 # If there are groups in the regexp, ensure the groups matched the same 172 # If there are groups in the regexp, ensure the groups matched the same
179 # things. 173 # things.
180 if match1.groups() == match2.groups(): # tuple comparison 174 if match1.groups() == match2.groups(): # tuple comparison
181 return True 175 return True
182 return False 176 return False
183 177
184 178
185 def diff_output(output1, output2, allowed, ignore1, ignore2): 179 def diff_output(output1, output2, allowed, ignore1, ignore2):
186 """Returns a tuple (difference, source, source_key). 180 """Returns a tuple (difference, source).
187 181
188 The difference is None if there's no difference, otherwise a string 182 The difference is None if there's no difference, otherwise a string
189 with a readable diff. 183 with a readable diff.
190 184
191 The source is the last source output within the test case. It is the string 185 The source is the last source output within the test case, or None if no
192 'none' if no such output existed. 186 such output existed.
193
194 The source_key is a short hash of source or 'none'.
195 """ 187 """
196 def useful_line(ignore): 188 def useful_line(ignore):
197 def fun(line): 189 def fun(line):
198 return all(not e.match(line) for e in ignore) 190 return all(not e.match(line) for e in ignore)
199 return fun 191 return fun
200 192
201 lines1 = filter(useful_line(ignore1), output1) 193 lines1 = filter(useful_line(ignore1), output1)
202 lines2 = filter(useful_line(ignore2), output2) 194 lines2 = filter(useful_line(ignore2), output2)
203 195
204 # This keeps track where we are in the original source file of the fuzz 196 # This keeps track where we are in the original source file of the fuzz
205 # test case. 197 # test case.
206 source = ORIGINAL_SOURCE_DEFAULT 198 source = None
207 source_key = ORIGINAL_SOURCE_DEFAULT
208 199
209 for ((line1, lookahead1), (line2, lookahead2)) in itertools.izip_longest( 200 for ((line1, lookahead1), (line2, lookahead2)) in itertools.izip_longest(
210 line_pairs(lines1), line_pairs(lines2), fillvalue=(None, None)): 201 line_pairs(lines1), line_pairs(lines2), fillvalue=(None, None)):
211 202
212 # Only one of the two iterators should run out. 203 # Only one of the two iterators should run out.
213 assert not (line1 is None and line2 is None) 204 assert not (line1 is None and line2 is None)
214 205
215 # One iterator ends earlier. 206 # One iterator ends earlier.
216 if line1 is None: 207 if line1 is None:
217 return '+ %s' % short_line_output(line2), source, source_key 208 return '+ %s' % short_line_output(line2), source
218 if line2 is None: 209 if line2 is None:
219 return '- %s' % short_line_output(line1), source, source_key 210 return '- %s' % short_line_output(line1), source
220 211
221 # If lines are equal, no further checks are necessary. 212 # If lines are equal, no further checks are necessary.
222 if line1 == line2: 213 if line1 == line2:
223 # Instrumented original-source-file output must be equal in both 214 # Instrumented original-source-file output must be equal in both
224 # versions. It only makes sense to update it here when both lines 215 # versions. It only makes sense to update it here when both lines
225 # are equal. 216 # are equal.
226 if line1.startswith(ORIGINAL_SOURCE_PREFIX): 217 if line1.startswith(ORIGINAL_SOURCE_PREFIX):
227 source = line1[len(ORIGINAL_SOURCE_PREFIX):] 218 source = line1[len(ORIGINAL_SOURCE_PREFIX):]
228 source_key = hashlib.sha1(source).hexdigest()[:SOURCE_HASH_LENGTH]
229 continue 219 continue
230 220
231 # Look ahead. If next line is a caret, ignore this line. 221 # Look ahead. If next line is a caret, ignore this line.
232 if caret_match(lookahead1, lookahead2): 222 if caret_match(lookahead1, lookahead2):
233 continue 223 continue
234 224
235 # Check if a regexp allows these lines to be different. 225 # Check if a regexp allows these lines to be different.
236 if ignore_by_regexp(line1, line2, allowed): 226 if ignore_by_regexp(line1, line2, allowed):
237 continue 227 continue
238 228
239 # Lines are different. 229 # Lines are different.
240 return ( 230 return (
241 '- %s\n+ %s' % (short_line_output(line1), short_line_output(line2)), 231 '- %s\n+ %s' % (short_line_output(line1), short_line_output(line2)),
242 source, 232 source,
243 source_key,
244 ) 233 )
245 234
246 # No difference found. 235 # No difference found.
247 return None, source, source_key 236 return None, source
248 237
249 238
250 def get_suppression(arch1, config1, arch2, config2): 239 def get_suppression(arch1, config1, arch2, config2):
251 return V8Suppression(arch1, config1, arch2, config2) 240 return V8Suppression(arch1, config1, arch2, config2)
252 241
253 242
254 class Suppression(object): 243 class Suppression(object):
255 def diff(self, output1, output2): 244 def diff(self, output1, output2):
256 return None 245 return None
257 246
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
314 bug = check(IGNORE_OUTPUT.get(arch, {})) 303 bug = check(IGNORE_OUTPUT.get(arch, {}))
315 if bug: 304 if bug:
316 return bug 305 return bug
317 bug = check(IGNORE_OUTPUT.get(config, {})) 306 bug = check(IGNORE_OUTPUT.get(config, {}))
318 if bug: 307 if bug:
319 return bug 308 return bug
320 bug = check(IGNORE_OUTPUT.get('%s,%s' % (arch, config), {})) 309 bug = check(IGNORE_OUTPUT.get('%s,%s' % (arch, config), {}))
321 if bug: 310 if bug:
322 return bug 311 return bug
323 return None 312 return None
OLDNEW
« no previous file with comments | « tools/foozzie/v8_foozzie_test.py ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698