예제 #1
0
        private void CreateCommutativityChecker(Program program, AtomicActionInfo first, AtomicActionInfo second)
        {
            if (first == second && first.thatInParams.Count == 0 && first.thatOutParams.Count == 0)
                return;
            if (first.CommutesWith(second))
                return;
            if (!commutativityCheckerCache.Add(new Tuple<AtomicActionInfo, AtomicActionInfo>(first, second)))
                return;

            List<Variable> inputs  = Enumerable.Union(first.thatInParams, second.thisInParams).ToList();
            List<Variable> outputs = Enumerable.Union(first.thatOutParams, second.thisOutParams).ToList();
            List<Variable> locals  = Enumerable.Union(first.thatAction.LocVars, second.thisAction.LocVars).ToList();
            List<Block> firstBlocks = CloneBlocks(first.thatAction.Blocks);
            List<Block> secondBlocks = CloneBlocks(second.thisAction.Blocks);
            foreach (Block b in firstBlocks.Where(b => b.TransferCmd is ReturnCmd))
            {
                List<Block>  bs = new List<Block>  { secondBlocks[0] };
                List<string> ls = new List<string> { secondBlocks[0].Label };
                b.TransferCmd = new GotoCmd(Token.NoToken, ls, bs);
            }
            List<Block> blocks = Enumerable.Union(firstBlocks, secondBlocks).ToList();
            HashSet<Variable> frame = new HashSet<Variable>();
            frame.UnionWith(first.gateUsedGlobalVars);
            frame.UnionWith(first.actionUsedGlobalVars);
            frame.UnionWith(second.gateUsedGlobalVars);
            frame.UnionWith(second.actionUsedGlobalVars);
            
            List<Requires> requires = new List<Requires>();
            requires.Add(DisjointnessRequires(program, first.thatInParams.Union(second.thisInParams), frame));
            foreach (AssertCmd assertCmd in Enumerable.Union(first.thatGate, second.thisGate))
                requires.Add(new Requires(false, assertCmd.Expr));

            var transitionRelationComputation = new TransitionRelationComputation(program, first, second, frame, new HashSet<Variable>());
            Expr transitionRelation = transitionRelationComputation.TransitionRelationCompute();
            {
                List<Block> bs = new List<Block> { blocks[0] };
                List<string> ls = new List<string> { blocks[0].Label };
                var initBlock = new Block(Token.NoToken, string.Format("{0}_{1}_init", first.proc.Name, second.proc.Name), transitionRelationComputation.TriggerAssumes(), new GotoCmd(Token.NoToken, ls, bs));
                blocks.Insert(0, initBlock);
            }
            IEnumerable<Expr> linearityAssumes = DisjointnessExpr(program, first.thatOutParams.Union(second.thisInParams), frame).Union(DisjointnessExpr(program, first.thatOutParams.Union(second.thisOutParams), frame));
            Ensures ensureCheck = new Ensures(false, Expr.Imp(Expr.And(linearityAssumes), transitionRelation));
            ensureCheck.ErrorData = string.Format("Commutativity check between {0} and {1} failed", first.proc.Name, second.proc.Name);
            List<Ensures> ensures = new List<Ensures> { ensureCheck };
            
            string checkerName = string.Format("CommutativityChecker_{0}_{1}", first.proc.Name, second.proc.Name);
            List<IdentifierExpr> globalVars = civlTypeChecker.SharedVariables.Select(x => Expr.Ident(x)).ToList();

            Procedure proc = new Procedure(Token.NoToken, checkerName, new List<TypeVariable>(), inputs, outputs, requires, globalVars, ensures);
            Implementation impl = new Implementation(Token.NoToken, checkerName, new List<TypeVariable>(), inputs, outputs, locals, blocks);
            impl.Proc = proc;
            this.decls.Add(impl);
            this.decls.Add(proc);
        }
예제 #2
0
        private void CreateCommutativityChecker(Program program, AtomicActionInfo first, AtomicActionInfo second)
        {
            if (first == second && first.thatInParams.Count == 0 && first.thatOutParams.Count == 0)
            {
                return;
            }
            if (first.CommutesWith(second))
            {
                return;
            }
            if (!commutativityCheckerCache.Add(new Tuple <AtomicActionInfo, AtomicActionInfo>(first, second)))
            {
                return;
            }

            List <Variable> inputs       = Enumerable.Union(first.thatInParams, second.thisInParams).ToList();
            List <Variable> outputs      = Enumerable.Union(first.thatOutParams, second.thisOutParams).ToList();
            List <Variable> locals       = Enumerable.Union(first.thatAction.LocVars, second.thisAction.LocVars).ToList();
            List <Block>    firstBlocks  = CloneBlocks(first.thatAction.Blocks);
            List <Block>    secondBlocks = CloneBlocks(second.thisAction.Blocks);

            foreach (Block b in firstBlocks.Where(b => b.TransferCmd is ReturnCmd))
            {
                List <Block> bs = new List <Block>  {
                    secondBlocks[0]
                };
                List <string> ls = new List <string> {
                    secondBlocks[0].Label
                };
                b.TransferCmd = new GotoCmd(Token.NoToken, ls, bs);
            }
            List <Block>       blocks = Enumerable.Union(firstBlocks, secondBlocks).ToList();
            HashSet <Variable> frame  = new HashSet <Variable>();

            frame.UnionWith(first.gateUsedGlobalVars);
            frame.UnionWith(first.actionUsedGlobalVars);
            frame.UnionWith(second.gateUsedGlobalVars);
            frame.UnionWith(second.actionUsedGlobalVars);

            List <Requires> requires = new List <Requires>();

            requires.Add(DisjointnessRequires(program, first.thatInParams.Union(second.thisInParams), frame));
            foreach (AssertCmd assertCmd in Enumerable.Union(first.thatGate, second.thisGate))
            {
                requires.Add(new Requires(false, assertCmd.Expr));
            }

            var  transitionRelationComputation = new TransitionRelationComputation(program, first, second, frame, new HashSet <Variable>());
            Expr transitionRelation            = transitionRelationComputation.TransitionRelationCompute();
            {
                List <Block> bs = new List <Block> {
                    blocks[0]
                };
                List <string> ls = new List <string> {
                    blocks[0].Label
                };
                var initBlock = new Block(Token.NoToken, string.Format("{0}_{1}_init", first.proc.Name, second.proc.Name), transitionRelationComputation.TriggerAssumes(), new GotoCmd(Token.NoToken, ls, bs));
                blocks.Insert(0, initBlock);
            }

            var thisInParamsFiltered            = second.thisInParams.Where(v => linearTypeChecker.FindLinearKind(v) != LinearKind.LINEAR_IN);
            IEnumerable <Expr> linearityAssumes = Enumerable.Union(
                DisjointnessExpr(program, first.thatOutParams.Union(thisInParamsFiltered), frame),
                DisjointnessExpr(program, first.thatOutParams.Union(second.thisOutParams), frame));
            // TODO: add further disjointness expressions?
            Ensures ensureCheck = new Ensures(false, Expr.Imp(Expr.And(linearityAssumes), transitionRelation));

            ensureCheck.ErrorData = string.Format("Commutativity check between {0} and {1} failed", first.proc.Name, second.proc.Name);
            List <Ensures> ensures = new List <Ensures> {
                ensureCheck
            };

            string checkerName = string.Format("CommutativityChecker_{0}_{1}", first.proc.Name, second.proc.Name);
            List <IdentifierExpr> globalVars = civlTypeChecker.SharedVariables.Select(x => Expr.Ident(x)).ToList();

            Procedure      proc = new Procedure(Token.NoToken, checkerName, new List <TypeVariable>(), inputs, outputs, requires, globalVars, ensures);
            Implementation impl = new Implementation(Token.NoToken, checkerName, new List <TypeVariable>(), inputs, outputs, locals, blocks);

            impl.Proc = proc;
            this.decls.Add(impl);
            this.decls.Add(proc);
        }
예제 #3
0
        private void CreateCommutativityChecker(AtomicActionCopy first, AtomicActionCopy second)
        {
            if (first == second && first.firstInParams.Count == 0 && first.firstOutParams.Count == 0)
            {
                return;
            }
            if (first.TriviallyCommutesWith(second))
            {
                return;
            }
            if (!commutativityCheckerCache.Add(Tuple.Create(first, second)))
            {
                return;
            }

            List <Variable>    inputs  = Enumerable.Union(first.firstInParams, second.secondInParams).ToList();
            List <Variable>    outputs = Enumerable.Union(first.firstOutParams, second.secondOutParams).ToList();
            List <Variable>    locals  = Enumerable.Union(first.firstAction.LocVars, second.secondAction.LocVars).ToList();
            List <Block>       blocks  = ComposeBlocks(first, second);
            HashSet <Variable> frame   = new HashSet <Variable>();

            frame.UnionWith(first.gateUsedGlobalVars);
            frame.UnionWith(first.actionUsedGlobalVars);
            frame.UnionWith(second.gateUsedGlobalVars);
            frame.UnionWith(second.actionUsedGlobalVars);

            List <Requires> requires = new List <Requires>();

            requires.Add(DisjointnessRequires(first.firstInParams.Union(second.secondInParams).Where(v => linearTypeChecker.FindLinearKind(v) != LinearKind.LINEAR_OUT), frame));
            foreach (AssertCmd assertCmd in Enumerable.Union(first.firstGate, second.secondGate))
            {
                requires.Add(new Requires(false, assertCmd.Expr));
            }

            var  transitionRelationComputation = new TransitionRelationComputation(first, second, frame, new HashSet <Variable>());
            Expr transitionRelation            = transitionRelationComputation.TransitionRelationCompute();
            {
                List <Block> bs = new List <Block> {
                    blocks[0]
                };
                List <string> ls = new List <string> {
                    blocks[0].Label
                };
                var initBlock = new Block(Token.NoToken, string.Format("{0}_{1}_init", first.proc.Name, second.proc.Name), transitionRelationComputation.TriggerAssumes(), new GotoCmd(Token.NoToken, ls, bs));
                blocks.Insert(0, initBlock);
            }

            var secondInParamsFiltered          = second.secondInParams.Where(v => linearTypeChecker.FindLinearKind(v) != LinearKind.LINEAR_IN);
            IEnumerable <Expr> linearityAssumes = Enumerable.Union(
                DisjointnessExpr(first.firstOutParams.Union(secondInParamsFiltered), frame),
                DisjointnessExpr(first.firstOutParams.Union(second.secondOutParams), frame));
            // TODO: add further disjointness expressions?
            Ensures ensureCheck = new Ensures(first.proc.tok, false, Expr.Imp(Expr.And(linearityAssumes), transitionRelation), null);

            ensureCheck.ErrorData = string.Format("Commutativity check between {0} and {1} failed", first.proc.Name, second.proc.Name);
            List <Ensures> ensures = new List <Ensures> {
                ensureCheck
            };

            string checkerName = string.Format("CommutativityChecker_{0}_{1}", first.proc.Name, second.proc.Name);

            AddChecker(checkerName, inputs, outputs, locals, requires, ensures, blocks);
        }