-
Notifications
You must be signed in to change notification settings - Fork 4.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improve coreclr test infra #77929
Improve coreclr test infra #77929
Changes from 1 commit
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
|
@@ -118,14 +118,50 @@ public override string ToString() | |||||
// issues.targets file as a split model would be very confusing for developers | ||||||
// and test monitors. | ||||||
private readonly HashSet<string>? _testExclusionList; | ||||||
private readonly int _stripe = 0; | ||||||
private readonly int _stripeCount = 1; | ||||||
private int _shouldRunQuery = -1; | ||||||
|
||||||
public TestFilter(string? filterString, HashSet<string>? testExclusionList) | ||||||
public TestFilter(string? filterString, HashSet<string>? testExclusionList) : | ||||||
this(filterString == null ? Array.Empty<string>() : new string[]{filterString}, testExclusionList) | ||||||
{ | ||||||
} | ||||||
|
||||||
public TestFilter(string[] filterArgs, HashSet<string>? testExclusionList) | ||||||
{ | ||||||
string? filterString = null; | ||||||
|
||||||
for (int i = 0; i < filterArgs.Length; i++) | ||||||
{ | ||||||
if (filterArgs[i].StartsWith("-stripe")) | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think it's worth starting a markdown file or something for us to start documenting the command line options the merged runners support, especially as we continue to add more options. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Agreed, actually it would be probably also useful to have an md on the overall concepts of merged tests like the stuff we presented a couple of times in the past; I can try to put some basics together but I'll probably need your additional commits for more detailed explanation of stuff I'm not that familiar with; I'd expect the documentation of command-line options to the merged runners can be easily included in the doc. |
||||||
{ | ||||||
_stripe = Int32.Parse(filterArgs[++i]); | ||||||
_stripeCount = Int32.Parse(filterArgs[++i]); | ||||||
} | ||||||
else | ||||||
{ | ||||||
if (filterString == null) | ||||||
filterString = filterArgs[0]; | ||||||
} | ||||||
} | ||||||
|
||||||
var stripeEnvironment = Environment.GetEnvironmentVariable("TEST_HARNESS_STRIPE_TO_EXECUTE"); | ||||||
if (!String.IsNullOrEmpty(stripeEnvironment) && stripeEnvironment != ".0.1") | ||||||
{ | ||||||
var stripes = stripeEnvironment.Split('.'); | ||||||
if (stripes.Length == 3) | ||||||
{ | ||||||
Console.WriteLine($"Test striping enabled via TEST_HARNESS_STRIPE_TO_EXECUTE environment variable set to '{stripeEnvironment}'"); | ||||||
_stripe = Int32.Parse(stripes[1]); | ||||||
_stripeCount = Int32.Parse(stripes[2]); | ||||||
} | ||||||
} | ||||||
|
||||||
if (filterString is not null) | ||||||
{ | ||||||
if (filterString.IndexOfAny(new[] { '!', '(', ')', '~', '=' }) != -1) | ||||||
{ | ||||||
throw new ArgumentException("Complex test filter expressions are not supported today. The only filters supported today are the simple form supported in 'dotnet test --filter' (substrings of the test's fully qualified name). If further filtering options are desired, file an issue on dotnet/runtime for support.", nameof(filterString)); | ||||||
throw new ArgumentException("Complex test filter expressions ar e not supported today. The only filters supported today are the simple form supported in 'dotnet test --filter' (substrings of the test's fully qualified name). If further filtering options are desired, file an issue on dotnet/runtime for support.", nameof(filterString)); | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nit - this looks like a typo There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||
} | ||||||
_filter = new NameClause(TermKind.FullyQualifiedName, filterString, substring: true); | ||||||
} | ||||||
|
@@ -140,15 +176,26 @@ public TestFilter(ISearchClause? filter, HashSet<string>? testExclusionList) | |||||
|
||||||
public bool ShouldRunTest(string fullyQualifiedName, string displayName, string[]? traits = null) | ||||||
{ | ||||||
bool shouldRun = false; | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nit - it might be a bit cleaner to define the local variable as uninitialized, if would let the Roslyn compiler verify that it does get initialized in each of the code branches. |
||||||
if (_testExclusionList is not null && _testExclusionList.Contains(displayName.Replace("\\", "/"))) | ||||||
{ | ||||||
return false; | ||||||
shouldRun = false; | ||||||
} | ||||||
if (_filter is null) | ||||||
else if (_filter is null) | ||||||
{ | ||||||
shouldRun = true; | ||||||
} | ||||||
else | ||||||
{ | ||||||
shouldRun = _filter.IsMatch(fullyQualifiedName, displayName, traits ?? Array.Empty<string>()); | ||||||
} | ||||||
|
||||||
if (shouldRun) | ||||||
{ | ||||||
return true; | ||||||
// Test stripe, if true, then report success | ||||||
return ((System.Threading.Interlocked.Increment(ref _shouldRunQuery)) % _stripeCount) == _stripe; | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This is a very clever and cheap way to handle striping. I like it! |
||||||
} | ||||||
return _filter.IsMatch(fullyQualifiedName, displayName, traits ?? Array.Empty<string>()); | ||||||
return false; | ||||||
} | ||||||
|
||||||
public static HashSet<string> LoadTestExclusionList() | ||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a bit challenging as we long-term envision we should emit something like a watchdog app that would run itself as a child process and execute the tests starting at a given index; this is needed especially for GCStress tests where a hard crash or timeout in a particular test basically drops all coverage on the floor; it would be great to collect the XUnit summaries and allow restarting the run at the next test by the parent process. I think this is good for now, I can imagine how to adapt this to the described scenario.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Mmm, yes. We should possibly consider adding yet another parameter with the test index to start with, and we can tie that into the test striping logic. That should be workable, but we have enough changes put together here in this PR that I don't want to add that right now.