<commit_before>﻿using Microsoft.Boogie;
using System;
using System.Collections.Generic;
using System.Linq;

namespace Symbooglix
{
    namespace Transform
    {
        public class PassManager
        {
            protected List<Tuple<IPass,PassInfo>> Passes;
            public Program TheProgram
            {
                get;
                private set;
            }


            public class PassManagerEventArgs : EventArgs
            {
                public readonly IPass ThePass;
                public readonly Program TheProgram;
                public PassManagerEventArgs(IPass pass, Program program) { ThePass = pass; TheProgram = program; }
            }
            public delegate void PassRunEvent(Object sender, PassManagerEventArgs args);
            public event PassRunEvent BeforePassRun;
            public event PassRunEvent AfterPassRun;


            public PassManager(Program prog)
            {
                Passes = new List<Tuple<IPass,PassInfo>>();
                TheProgram = prog;
            }

            public void Add(IPass pass)
            {
                var passInfo = new PassInfo();

                // Get the dependencies
                pass.SetPassInfo(ref passInfo);
                var tuple = Tuple.Create(pass, passInfo);

                if (passInfo.Dependencies != null)
                {
                    // We could be more sophisticatd here and try to optimise
                    // the list of passes so we don't run redundant analyses
                    // Leave this for now

                    // The pass has Dependencies so Add them

                    // It is not safe to iterate over a dictionary and modify it
                    // at the same time so do it in two stages.
                    // 1. Collect all the KeyValue Pairs in the dictionary
                    // 2. Iterate over the collected KeyValue pairs and modify the dictionary
                    var depList = new List<KeyValuePair<System.Type,IPass>>();
                    foreach (var keyValuePair in passInfo.Dependencies)
                    {
                        depList.Add(keyValuePair);
                    }

                    foreach (var keyValuePair in depList)
                    {
                        // Create dependency. This requires that the pass has a default constructor
                        IPass dependencyOfPass = Activator.CreateInstance(keyValuePair.Key) as IPass;

                        passInfo.Dependencies[keyValuePair.Key] = dependencyOfPass;

                        // Do this recursively so we handle any dependencies of the dependencies (of the...)*
                        Add(dependencyOfPass);
                    }

                }

                Passes.Add(tuple);
            }
                
            public void Run()
            {
                foreach (var pass in Passes.Select( p => p.Item1))
                {
                    // Passes may implement multiple IPass interfaces
                    // so we can't use Handle(pass as dynmaic) or double
                    // dispatch here because may need to call Handle multiple
                    // times. So we must do this manually
                    bool handled = false;

                    if (BeforePassRun != null)
                        BeforePassRun(this, new PassManagerEventArgs(pass, TheProgram));

                    // Eurgh: Macros would be handy here!

                    if (pass is IProgramPass)
                    {
                        Handle(pass as IProgramPass);
                        handled = true;
                    }

                    if (pass is IFunctionPass)
                    {
                        Handle(pass as IFunctionPass);
                        handled = true;
                    }

                    if (pass is IProcedurePass)
                    {
                        Handle(pass as IProcedurePass);
                        handled = true;
                    }

                    if (pass is IImplementationPass)
                    {
                        Handle(pass as IImplementationPass);
                        handled = true;
                    }

                    if (pass is IAxiomPass)
                    {
                        Handle(pass as IAxiomPass);
                        handled = true;
                    }

                    if (pass is IGlobalVariablePass)
                    {
                        Handle(pass as IGlobalVariablePass);
                        handled = true;
                    }

                    if (pass is IConstantVariablePass)
                    {
                        Handle(pass as IConstantVariablePass);
                        handled = true;
                    }

                    if (!handled)
                        throw new InvalidCastException("Pass type not handled!");

                    if (AfterPassRun != null)
                        AfterPassRun(this, new PassManagerEventArgs(pass, TheProgram));
                }
            }

            private void Handle(IProgramPass pass)
            {
                pass.RunOn(TheProgram);
            }

            private void Handle(IFunctionPass pass)
            {
                var functions = TheProgram.TopLevelDeclarations.OfType<Function>();
                foreach (var function in functions)
                {
                    pass.RunOn(function);<commit_msg>Added Finished event to PassManager so observers can get access to the Program after all passes have been run.<commit_after>﻿using Microsoft.Boogie;
using System;
using System.Collections.Generic;
using System.Linq;

namespace Symbooglix
{
    namespace Transform
    {
        public class PassManager
        {
            protected List<Tuple<IPass,PassInfo>> Passes;
            public Program TheProgram
            {
                get;
                private set;
            }


            public class PassManagerEventArgs : EventArgs
            {
                public readonly IPass ThePass;
                public readonly Program TheProgram;
                public PassManagerEventArgs(IPass pass, Program program) { ThePass = pass; TheProgram = program; }
            }
            public delegate void PassRunEvent(Object sender, PassManagerEventArgs args);
            public event PassRunEvent BeforePassRun;
            public event PassRunEvent AfterPassRun;
            public event PassRunEvent Finished;


            public PassManager(Program prog)
            {
                Passes = new List<Tuple<IPass,PassInfo>>();
                TheProgram = prog;
            }

            public void Add(IPass pass)
            {
                var passInfo = new PassInfo();

                // Get the dependencies
                pass.SetPassInfo(ref passInfo);
                var tuple = Tuple.Create(pass, passInfo);

                if (passInfo.Dependencies != null)
                {
                    // We could be more sophisticatd here and try to optimise
                    // the list of passes so we don't run redundant analyses
                    // Leave this for now

                    // The pass has Dependencies so Add them

                    // It is not safe to iterate over a dictionary and modify it
                    // at the same time so do it in two stages.
                    // 1. Collect all the KeyValue Pairs in the dictionary
                    // 2. Iterate over the collected KeyValue pairs and modify the dictionary
                    var depList = new List<KeyValuePair<System.Type,IPass>>();
                    foreach (var keyValuePair in passInfo.Dependencies)
                    {
                        depList.Add(keyValuePair);
                    }

                    foreach (var keyValuePair in depList)
                    {
                        // Create dependency. This requires that the pass has a default constructor
                        IPass dependencyOfPass = Activator.CreateInstance(keyValuePair.Key) as IPass;

                        passInfo.Dependencies[keyValuePair.Key] = dependencyOfPass;

                        // Do this recursively so we handle any dependencies of the dependencies (of the...)*
                        Add(dependencyOfPass);
                    }

                }

                Passes.Add(tuple);
            }
                
            public void Run()
            {
                foreach (var pass in Passes.Select( p => p.Item1))
                {
                    // Passes may implement multiple IPass interfaces
                    // so we can't use Handle(pass as dynmaic) or double
                    // dispatch here because may need to call Handle multiple
                    // times. So we must do this manually
                    bool handled = false;

                    if (BeforePassRun != null)
                        BeforePassRun(this, new PassManagerEventArgs(pass, TheProgram));

                    // Eurgh: Macros would be handy here!

                    if (pass is IProgramPass)
                    {
                        Handle(pass as IProgramPass);
                        handled = true;
                    }

                    if (pass is IFunctionPass)
                    {
                        Handle(pass as IFunctionPass);
                        handled = true;
                    }

                    if (pass is IProcedurePass)
                    {
                        Handle(pass as IProcedurePass);
                        handled = true;
                    }

                    if (pass is IImplementationPass)
                    {
                        Handle(pass as IImplementationPass);
                        handled = true;
                    }

                    if (pass is IAxiomPass)
                    {
                        Handle(pass as IAxiomPass);
                        handled = true;
                    }

                    if (pass is IGlobalVariablePass)
                    {
                        Handle(pass as IGlobalVariablePass);
                        handled = true;
                    }

                    if (pass is IConstantVariablePass)
                    {
                        Handle(pass as IConstantVariablePass);
                        handled = true;
                    }

                    if (!handled)
                        throw new InvalidCastException("Pass type not handled!");

                    if (AfterPassRun != null)
                        AfterPassRun(this, new PassManagerEventArgs(pass, TheProgram));
                }

                if (Finished != null)
                    Finished(this, new PassManagerEventArgs(null, TheProgram));
            }

            private void Handle(IProgramPass pass)
            {
                pass.RunOn(TheProgram);
            }

            private void Handle(IFunctionPass pass)
            {
                var functions = TheProgram.TopLevelDeclarations.OfType<Function>();
                foreach (var function in functions)
                {
                    pass.RunOn(function);
{'fraction_non_alphanumeric': 0.056712962962962965, 'fraction_numerical': 0.0005341880341880342, 'mean_word_length': 1.0622360932623462, 'pattern_counts': {'":': 0, '<': 17, '<?xml version=': 0, '>': 19, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3298772', 'n_tokens_mistral': 2507, 'n_tokens_neox': 2242, 'n_words': 752}