Exemple #1
0
        static int Main(string[] args)
        {
            int exitCode = StatusTestErrorBadInput;

            ArgumentSyntax syntax = ParseCommandLine(args);

            if (_help)
            {
                ShowUsage();
                return(0);
            }

            if (!File.Exists(_coreRunExePath))
            {
                Console.WriteLine($"Error: {_coreRunExePath} is an invalid path.");
                ShowUsage();
                return(exitCode);
            }

            if (!File.Exists(_testExe))
            {
                Console.WriteLine($"Error: {_testExe} is an invalid path.");
                ShowUsage();
                return(exitCode);
            }

            string passThroughArguments = "";

            if (_testargs.Count > 0)
            {
                passThroughArguments = string.Join(' ', _testargs);
            }

            var testModules = new HashSet <string>();
            var testFolders = new HashSet <string>();

            testModules.Add(_testExe.ToLower());
            foreach (string reference in _referenceFilenames)
            {
                // CoreCLR generates ETW events with all lower case native image files that break our string comparison.
                testModules.Add(reference.ToLower());
            }

            foreach (string reference in _referenceFolders)
            {
                string absolutePath = reference.ToAbsoluteDirectoryPath();

                if (!Directory.Exists(reference))
                {
                    Console.WriteLine($"Error: {reference} does not exist.");
                    ShowUsage();
                    return(exitCode);
                }
                testFolders.Add(reference.ToLower());
            }

            if (_noEtl)
            {
                RunTest(null, null, passThroughArguments, out exitCode);
            }
            else
            {
                using (var session = new TraceEventSession("ReadyToRunTestSession"))
                {
                    var r2rMethodFilter = new ReadyToRunJittedMethods(session, testModules, testFolders);
                    session.EnableProvider(ClrTraceEventParser.ProviderGuid, TraceEventLevel.Verbose, (ulong)(ClrTraceEventParser.Keywords.Jit | ClrTraceEventParser.Keywords.Loader));

                    Task.Run(() => RunTest(session, r2rMethodFilter, passThroughArguments, out exitCode));

                    // Block, processing callbacks for events we subscribed to
                    session.Source.Process();

                    Console.WriteLine("Test execution " + (exitCode == StatusTestPassed ? "PASSED" : "FAILED"));
                    int analysisResult = AnalyzeResults(r2rMethodFilter, _whitelistFilename);

                    Console.WriteLine("Test jitted method analysis " + (analysisResult == StatusTestPassed ? "PASSED" : "FAILED"));

                    // If the test passed, return the Jitted method analysis result
                    // If the test failed, return its execution exit code
                    exitCode = exitCode == StatusTestPassed ? analysisResult : exitCode;
                }
            }


            Console.WriteLine($"Final test result: {exitCode}");
            return(exitCode);
        }
Exemple #2
0
        private static int AnalyzeResults(ReadyToRunJittedMethods jittedMethods, string whiteListFilePath = null)
        {
            var whiteListedMethods = new HashSet <string>();

            if (!string.IsNullOrEmpty(whiteListFilePath))
            {
                using (TextReader tr = File.OpenText(whiteListFilePath))
                {
                    string line = "";
                    while ((line = tr.ReadLine()) != null)
                    {
                        whiteListedMethods.Add(line);
                    }
                }
            }

            if (jittedMethods.AssembliesWithEventsCount == 0)
            {
                Console.WriteLine($"Error: No test assemblies were loaded by the runtime. This is likely a test harness bug / ETW issue");
                return(StatusTestErrorNoAssemblyLoadEvents);
            }

            Console.WriteLine("");
            Console.WriteLine("*** Jitted method analysis ***");

            Console.WriteLine("");
            Console.WriteLine("White listed methods that were jitted (these don't count as test failures):");
            int whiteListedJittedMethodCount = 0;

            foreach (var jittedMethod in jittedMethods.JittedMethods)
            {
                if (whiteListedMethods.Contains(jittedMethod.MethodName))
                {
                    Console.WriteLine(jittedMethod.MethodName);
                    ++whiteListedJittedMethodCount;
                }
            }
            if (whiteListedJittedMethodCount == 0)
            {
                Console.WriteLine("-None-");
            }

            Console.WriteLine("");
            Console.WriteLine("Methods that were jitted without a whitelist entry (test failure):");
            int jittedMethodCount = 0;

            foreach (var jittedMethod in jittedMethods.JittedMethods)
            {
                string fullName = GetFullModuleName(jittedMethod.assemblyName, jittedMethod.MethodName);
                if (!whiteListedMethods.Contains(jittedMethod.MethodName) && !whiteListedMethods.Contains(fullName))
                {
                    Console.WriteLine(fullName);
                    ++jittedMethodCount;
                }
            }
            if (jittedMethodCount == 0)
            {
                Console.WriteLine("-None-");
            }

            if (jittedMethodCount > 0)
            {
                Console.WriteLine($"Error: {jittedMethodCount} methods were jitted.");
                return(StatusTestErrorMethodsJitted);
            }

            return(StatusTestPassed);
        }
Exemple #3
0
        private static void RunTest(TraceEventSession session, ReadyToRunJittedMethods r2rMethodFilter, string testArguments, out int exitCode)
        {
            exitCode = -100;

            try
            {
                using (var process = new Process())
                {
                    process.StartInfo.FileName        = _coreRunExePath;
                    process.StartInfo.Arguments       = _testExe + " " + testArguments;
                    process.StartInfo.UseShellExecute = false;

                    process.Start();

                    if (r2rMethodFilter != null)
                    {
                        r2rMethodFilter.SetProcessId(process.Id);
                    }

                    process.OutputDataReceived += delegate(object sender, DataReceivedEventArgs args)
                    {
                        Console.WriteLine(args.Data);
                    };

                    process.ErrorDataReceived += delegate(object sender, DataReceivedEventArgs args)
                    {
                        Console.WriteLine(args.Data);
                    };

                    if (process.WaitForExit(DefaultTestTimeOut))
                    {
                        exitCode = process.ExitCode;
                    }
                    else
                    {
                        // Do our best to kill it if there's a timeout, but if it fails, not much we can do
                        try
                        {
                            process.Kill();
                        }
                        catch
                        {
                        }

                        Console.WriteLine("Test execution timed out.");
                        exitCode = StatusTestErrorTimeOut;
                    }

                    Console.WriteLine($"Test exited with code {process.ExitCode}");

                    if (session != null && session.EventsLost > 0)
                    {
                        exitCode = StatusTestErrorEventsLost;
                        Console.WriteLine($"Error - {session.EventsLost} got lost in the nether.");
                        return;
                    }
                }
            }
            finally
            {
                // Stop ETL collection on the main thread
                session?.Stop();
            }
        }
Exemple #4
0
        private static int AnalyzeResults(ReadyToRunJittedMethods jittedMethods, string whiteListFilePath = null)
        {
            var whiteListedMethods = new HashSet <string>();

            if (!string.IsNullOrEmpty(whiteListFilePath))
            {
                using (TextReader tr = File.OpenText(whiteListFilePath))
                {
                    string line = "";
                    while ((line = tr.ReadLine()) != null)
                    {
                        whiteListedMethods.Add(line);
                    }
                }
            }

            if (jittedMethods.AssembliesWithEventsCount == 0)
            {
                Console.WriteLine($"Error: No test assemblies were loaded by the runtime. This is likely a test harness bug / ETW issue");
                return(StatusTestErrorNoAssemblyLoadEvents);
            }

            Console.WriteLine("");
            Console.WriteLine("*** Jitted method analysis ***");

            Console.WriteLine("");
            Console.WriteLine("White listed methods that were jitted (these don't count as test failures):");
            int whiteListedJittedMethodCount = 0;

            List <string> jittedMethodNames = new List <string>();

            foreach (KeyValuePair <string, HashSet <string> > jittedMethod in jittedMethods.JittedMethods.OrderBy(kvp => kvp.Key))
            {
                bool wasWhiteListed = whiteListedMethods.Contains(jittedMethod.Key);
                if (!wasWhiteListed)
                {
                    // Check assembly-qualified whitelist clauses
                    wasWhiteListed = true;
                    foreach (string assemblyName in jittedMethod.Value)
                    {
                        string fullName = GetFullModuleName(assemblyName, jittedMethod.Key);
                        if (!whiteListedMethods.Contains(fullName))
                        {
                            jittedMethodNames.Add(fullName);
                            wasWhiteListed = false;
                        }
                    }
                }
                if (wasWhiteListed)
                {
                    Console.WriteLine(jittedMethod.Key);
                    whiteListedJittedMethodCount++;
                }
            }

            if (whiteListedJittedMethodCount == 0)
            {
                Console.WriteLine("-None-");
            }

            Console.WriteLine("");
            Console.WriteLine("Methods that were jitted without a whitelist entry (test failure):");
            foreach (string jittedMethod in jittedMethodNames)
            {
                Console.WriteLine(jittedMethod);
            }
            if (jittedMethodNames.Count == 0)
            {
                Console.WriteLine("-None-");
            }
            else
            {
                Console.WriteLine($"Error: {jittedMethodNames.Count} methods were jitted.");
                return(StatusTestErrorMethodsJitted);
            }

            return(StatusTestPassed);
        }