private void EventSourceOnMessageRaised(object sender, BuildMessageEventArgs e)
        {
            if (e is TaskCommandLineEventArgs commandLine)
            {
                // We are only interested in CSharp and VisualBasic tasks
                string language;
                string extractedArguments;
                string error;
                bool   success;

                switch (commandLine.TaskName)
                {
                case CscTaskName:
                    language = LanguageNames.CSharp;
                    success  = TryGetArgumentsFromCommandLine(CscToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                case VbcTaskName:
                    language = LanguageNames.VisualBasic;
                    success  = TryGetArgumentsFromCommandLine(VbcToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                default:
                    return;
                }

                // We were able to split the compiler invocation from its arguments. This is the indicator
                // that something didn't go as expected. Since failing to parse the command line means we
                // are not catching all inputs/outputs properly, we have no option but to fail the corresponding pip
                if (!success)
                {
                    throw new ArgumentException(error);
                }

                var parsedCommandLine = CompilerUtilities.GetParsedCommandLineArguments(language, extractedArguments, commandLine.ProjectFile);

                // In general we don't care about errors in the command line, since any error there will eventually fail the compiler call.
                // However, we do care about new switches that may represent file accesses that are introduced to the compiler and this logger
                // is not aware of.
                // This means that if the command line comes back with a bad switch error, but the compiler doesn't fail, we need to fail the call.
                // Error 2007 represents a bad switch. Unfortunately there doesn't seem to be any public enumeration that defines it properly.
                var badSwitchErrors = parsedCommandLine.Errors.Where(diagnostic => diagnostic.Id.Contains("2007")).ToList();
                foreach (var badSwitch in badSwitchErrors)
                {
                    // If we find a bad switch error, delay making a decision until we know if the compiler failed or not.
                    m_badSwitchErrors.Add(badSwitch);
                }

                RegisterAccesses(parsedCommandLine);
            }
        }
Beispiel #2
0
        private void EventSourceOnMessageRaised(object sender, BuildMessageEventArgs e)
        {
            if (e is TaskCommandLineEventArgs commandLine)
            {
                // We are only interested in CSharp and VisualBasic tasks
                string language;
                string extractedArguments;
                string error;
                bool   success;

                switch (commandLine.TaskName)
                {
                case CscTaskName:
                    language = LanguageNames.CSharp;
                    success  = TryGetArgumentsFromCommandLine(CscToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                case VbcTaskName:
                    language = LanguageNames.VisualBasic;
                    success  = TryGetArgumentsFromCommandLine(VbcToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                default:
                    return;
                }

                // We were able to split the compiler invocation from its arguments. This is the indicator
                // that something didn't go as expected. Since failing to parse the command line means we
                // are not catching all inputs/outputs properly, we have no option but to fail the corresponding pip
                if (!success)
                {
                    throw new ArgumentException(error);
                }

                var parsedCommandLine = CompilerUtilities.GetParsedCommandLineArguments(language, extractedArguments, commandLine.ProjectFile);
                RegisterAccesses(parsedCommandLine);
            }
        }
        private void EventSourceOnMessageRaised(object sender, BuildMessageEventArgs e)
        {
            if (e is TaskCommandLineEventArgs commandLine)
            {
                // We are only interested in CSharp and VisualBasic tasks
                string language;
                string extractedArguments;
                string error;
                bool   success;

                switch (commandLine.TaskName)
                {
                case CscTaskName:
                    language = LanguageNames.CSharp;
                    success  = TryGetArgumentsFromCommandLine(CscToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                case VbcTaskName:
                    language = LanguageNames.VisualBasic;
                    success  = TryGetArgumentsFromCommandLine(VbcToolName, commandLine.CommandLine, out extractedArguments, out error);
                    break;

                default:
                    return;
                }

                // We were able to split the compiler invocation from its arguments. This is the indicator
                // that something didn't go as expected. Since failing to parse the command line means we
                // are not catching all inputs/outputs properly, we have no option but to fail the corresponding pip
                if (!success)
                {
                    throw new ArgumentException(error);
                }

                var parsedCommandLine = CompilerUtilities.GetParsedCommandLineArguments(language, extractedArguments, commandLine.ProjectFile, out string[] args);

                // In general we don't care about errors in the command line, since any error there will eventually fail the compiler call.
                // However, we do care about new switches that may represent file accesses that are introduced to the compiler and this logger
                // is not aware of.
                // This means that if the command line comes back with a bad switch error, but the compiler doesn't fail, we need to fail the call.
                // Error 2007 represents a bad switch. Unfortunately there doesn't seem to be any public enumeration that defines it properly.
                var badSwitchErrors = parsedCommandLine.Errors.Where(diagnostic => diagnostic.Id.Contains("2007")).ToList();
                foreach (var badSwitch in badSwitchErrors)
                {
                    // If we find a bad switch error, delay making a decision until we know if the compiler failed or not.
                    m_badSwitchErrors.Add(badSwitch);
                }

                string[] embeddedResourceFilePaths = Array.Empty <string>();

                // Determine the paths to the embedded resources. /resource: parameters end up in CommandLineArguments.ManifestResources,
                // but the returned class drops the file path (and is currently internal anyway).
                // We should be able to remove this if/when this gets resolved: https://github.com/dotnet/roslyn/issues/41372.
                if (parsedCommandLine.ManifestResources.Length > 0)
                {
                    IEnumerable <string> embeddedResourcesArgs = args.Where(
                        a =>
                        a.StartsWith("/resource:", StringComparison.OrdinalIgnoreCase) ||
                        a.StartsWith("/res:", StringComparison.Ordinal) ||
                        a.StartsWith("/linkresource:", StringComparison.Ordinal) ||
                        a.StartsWith("/linkres:", StringComparison.Ordinal));

                    embeddedResourceFilePaths = CompilerUtilities.GetEmbeddedResourceFilePaths(
                        embeddedResourcesArgs,
                        parsedCommandLine.BaseDirectory);
                }

                var result = new ParseResult()
                {
                    ParsedArguments       = parsedCommandLine,
                    EmbeddedResourcePaths = embeddedResourceFilePaths
                };

                RegisterAccesses(result);
            }
        }