public void Analyze(SemanticModelAnalysisContext context)
        {
            var semanticModel     = context.SemanticModel;
            var syntaxTree        = semanticModel.SyntaxTree;
            var cancellationToken = context.CancellationToken;

            var option = context.Options.GetIdeOptions().ReportInvalidRegexPatterns;

            if (!option)
            {
                return;
            }

            var detector = RegexLanguageDetector.GetOrCreate(semanticModel.Compilation, _info);

            // Use an actual stack object so that we don't blow the actual stack through recursion.
            var root  = syntaxTree.GetRoot(cancellationToken);
            var stack = new Stack <SyntaxNode>();

            stack.Push(root);

            while (stack.Count != 0)
            {
                cancellationToken.ThrowIfCancellationRequested();
                var current = stack.Pop();

                foreach (var child in current.ChildNodesAndTokens())
                {
                    if (child.IsNode)
                    {
                        stack.Push(child.AsNode());
                    }
                    else
                    {
                        AnalyzeToken(context, detector, child.AsToken(), cancellationToken);
                    }
                }
            }
        }
        public void RegisterClassifications(EmbeddedLanguageClassificationContext context)
        {
            var token = context.SyntaxToken;

            if (!_info.IsAnyStringLiteral(token.RawKind))
            {
                return;
            }

            if (!context.Options.ColorizeRegexPatterns)
            {
                return;
            }

            var semanticModel     = context.SemanticModel;
            var cancellationToken = context.CancellationToken;

            var detector = RegexLanguageDetector.GetOrCreate(semanticModel.Compilation, _info);
            var tree     = detector.TryParseString(token, semanticModel, cancellationToken);

            if (tree == null)
            {
                return;
            }

            var visitor = s_visitorPool.Allocate();

            try
            {
                visitor.Context = context;
                AddClassifications(tree.Root, visitor, context);
            }
            finally
            {
                visitor.Context = default;
                s_visitorPool.Free(visitor);
            }
        }
 private void AnalyzeToken(
     SemanticModelAnalysisContext context,
     RegexLanguageDetector detector,
     SyntaxToken token,
     CancellationToken cancellationToken)
 {
     if (_info.IsAnyStringLiteral(token.RawKind))
     {
         var tree = detector.TryParseString(token, context.SemanticModel, cancellationToken);
         if (tree != null)
         {
             foreach (var diag in tree.Diagnostics)
             {
                 context.ReportDiagnostic(DiagnosticHelper.Create(
                                              Descriptor,
                                              Location.Create(context.SemanticModel.SyntaxTree, diag.Span),
                                              ReportDiagnostic.Warn,
                                              additionalLocations: null,
                                              properties: null,
                                              diag.Message));
             }
         }
     }
 }