コード例 #1
0
        public override Procedure VisitProcedure(Procedure node)
        {
            Debug.Assert(civlTypeChecker.procToYieldingProc.ContainsKey(node));
            if (!procToDuplicate.ContainsKey(node))
            {
                YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[node];
                Debug.Assert(layerNum <= yieldingProc.upperLayer);

                Procedure proc = (Procedure)node.Clone();
                proc.Name      = $"{node.Name}_{layerNum}";
                proc.InParams  = this.VisitVariableSeq(node.InParams);
                proc.OutParams = this.VisitVariableSeq(node.OutParams);
                proc.Requires  = this.VisitRequiresSeq(node.Requires);
                proc.Ensures   = this.VisitEnsuresSeq(node.Ensures);
                if (yieldingProc is MoverProc moverProc && yieldingProc.upperLayer == layerNum)
                {
                    proc.Modifies = moverProc.modifiedGlobalVars.Select(g => Expr.Ident(g)).ToList();
                }
                else
                {
                    proc.Modifies = civlTypeChecker.GlobalVariables.Select(v => Expr.Ident(v)).ToList();
                    yieldingProcs.Add(proc);
                }

                procToDuplicate[node] = proc;
                absyMap[proc]         = node;
            }
コード例 #2
0
ファイル: YieldTypeChecker.cs プロジェクト: rospoly/boogie
            private int CallCmdLabel(CallCmd callCmd)
            {
                if (@base.civlTypeChecker.procToIntroductionProc.ContainsKey(callCmd.Proc))
                {
                    return(I);
                }

                YieldingProc callee = @base.civlTypeChecker.procToYieldingProc[callCmd.Proc];

                if (callCmd.IsAsync)
                {
                    if (callee is ActionProc && !callCmd.HasAttribute(CivlAttributes.SYNC))
                    {
                        return(L);
                    }
                    if (callee.upperLayer < currLayerNum || (callee.upperLayer == currLayerNum && callee is MoverProc))
                    {
                        return(MoverTypeToLabel(callee.moverType));
                    }
                    return(L);
                }
                else
                {
                    if (callee.upperLayer < currLayerNum || (callee.upperLayer == currLayerNum && callee is MoverProc))
                    {
                        return(MoverTypeToLabel(callee.moverType));
                    }
                    return(Y);
                }
            }
コード例 #3
0
ファイル: YieldTypeChecker.cs プロジェクト: omaragb/tlp182
            private int CallCmdLabel(CallCmd callCmd)
            {
                if ([email protected](callCmd.Proc))
                {
                    return(P);
                }

                YieldingProc callee = @base.civlTypeChecker.procToYieldingProc[callCmd.Proc];

                if (callCmd.IsAsync)
                {
                    if ((currLayerNum < yieldingProc.upperLayer && currLayerNum > callee.upperLayer) ||
                        (currLayerNum == yieldingProc.upperLayer && callee.upperLayer < yieldingProc.upperLayer))
                    {
                        return(MoverTypeToLabel(callee.moverType));
                    }
                    return(L);
                }
                else
                {
                    if (callee.upperLayer < currLayerNum || (callee.upperLayer == currLayerNum && callee is MoverProc))
                    {
                        return(MoverTypeToLabel(callee.moverType));
                    }
                    return(Y);
                }
            }
コード例 #4
0
            private string CallCmdLabel(CallCmd callCmd)
            {
                if (@base.civlTypeChecker.procToIntroductionAction.ContainsKey(callCmd.Proc) ||
                    @base.civlTypeChecker.procToLemmaProc.ContainsKey(callCmd.Proc))
                {
                    return(I);
                }

                if (@base.civlTypeChecker.procToYieldInvariant.ContainsKey(callCmd.Proc))
                {
                    return(@base.civlTypeChecker.procToYieldInvariant[callCmd.Proc].LayerNum == currLayerNum ? Y : P);
                }

                YieldingProc callee = @base.civlTypeChecker.procToYieldingProc[callCmd.Proc];

                if (callCmd.IsAsync)
                {
                    return(L);
                }

                if (callee is MoverProc && callee.upperLayer == currLayerNum)
                {
                    return(MoverTypeToLabel(callee.moverType));
                }

                if (callee is ActionProc actionProc && callee.upperLayer < currLayerNum)
                {
                    return(MoverTypeToLabel(actionProc.RefinedActionAtLayer(currLayerNum).moverType));
                }

                return(Y);
            }
コード例 #5
0
        private void TransformImpl(Implementation originalImpl, Implementation impl)
        {
            // initialize globalSnapshotInstrumentation
            globalSnapshotInstrumentation = new GlobalSnapshotInstrumentation(civlTypeChecker);

            // initialize refinementInstrumentation
            YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[originalImpl.Proc];

            if (yieldingProc.upperLayer == this.layerNum)
            {
                if (yieldingProc is ActionProc)
                {
                    refinementInstrumentation = new ActionRefinementInstrumentation(
                        civlTypeChecker,
                        impl,
                        originalImpl,
                        globalSnapshotInstrumentation.OldGlobalMap);
                }
                else
                {
                    refinementInstrumentation = new SkipRefinementInstrumentation(
                        civlTypeChecker,
                        yieldingProc,
                        globalSnapshotInstrumentation.OldGlobalMap);
                }
            }
            else
            {
                refinementInstrumentation = new RefinementInstrumentation();
            }

            var allYieldPredicates = CollectYields(impl);

            // initialize noninterferenceInstrumentation
            if (CommandLineOptions.Clo.TrustNonInterference)
            {
                noninterferenceInstrumentation = new NoneNoninterferenceInstrumentation();
            }
            else
            {
                noninterferenceCheckerDecls.AddRange(
                    NoninterferenceChecker.CreateNoninterferenceCheckers(civlTypeChecker, linearTypeChecker, layerNum, absyMap, impl, allYieldPredicates));
                noninterferenceInstrumentation = new SomeNoninterferenceInstrumentation(
                    civlTypeChecker,
                    linearTypeChecker,
                    linearPermissionInstrumentation,
                    globalSnapshotInstrumentation.OldGlobalMap,
                    wrapperNoninterferenceCheckerProc);
            }

            DesugarConcurrency(impl, allYieldPredicates);

            impl.LocVars.AddRange(globalSnapshotInstrumentation.NewLocalVars);
            impl.LocVars.AddRange(refinementInstrumentation.NewLocalVars);
            impl.LocVars.AddRange(noninterferenceInstrumentation.NewLocalVars);
        }
コード例 #6
0
 public PerLayerYieldSufficiencyTypeChecker(CivlTypeChecker civlTypeChecker, YieldingProc yieldingProc,
                                            Implementation impl, int currLayerNum, Graph <Block> implGraph, Graph <MoverProc> moverProcedureCallGraph)
 {
     this.civlTypeChecker         = civlTypeChecker;
     this.yieldingProc            = yieldingProc;
     this.impl                    = impl;
     this.currLayerNum            = currLayerNum;
     this.implGraph               = implGraph;
     this.moverProcedureCallGraph = moverProcedureCallGraph;
 }
コード例 #7
0
        public override Procedure VisitProcedure(Procedure node)
        {
            if (!civlTypeChecker.procToYieldingProc.ContainsKey(node))
            {
                return(node);
            }
            if (!procMap.ContainsKey(node))
            {
                YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[node];

                if (layerNum > yieldingProc.upperLayer)
                {
                    if (yieldingProc is ActionProc actionProc)
                    {
                        // yielding procedure already transformed to atomic action
                        var action = actionProc.refinedAction;
                        if (action.layerRange.Contains(layerNum))
                        {
                            return(action.layerToActionCopy[layerNum].proc);
                        }
                        else
                        {
                            return(node);
                        }
                    }
                    else if (yieldingProc is SkipProc)
                    {
                        // (calls to) skip procedures do not completely disappear because of output variables
                        return(procToSkipProcDummy[yieldingProc.proc]);
                    }
                    else if (yieldingProc is MoverProc)
                    {
                        // mover procedure does not exist on this layer any more
                        return(node);
                    }
                }

                Procedure proc = (Procedure)node.Clone();
                proc.Name      = $"{node.Name}_{layerNum}";
                proc.InParams  = this.VisitVariableSeq(node.InParams);
                proc.OutParams = this.VisitVariableSeq(node.OutParams);
                proc.Requires  = this.VisitRequiresSeq(node.Requires);
                proc.Ensures   = this.VisitEnsuresSeq(node.Ensures);
                if (yieldingProc is MoverProc moverProc && yieldingProc.upperLayer == layerNum)
                {
                    proc.Modifies = moverProc.modifiedGlobalVars.Select(g => Expr.Ident(g)).ToList();
                }
                else
                {
                    proc.Modifies = civlTypeChecker.sharedVariableIdentifiers;
                    yieldingProcs.Add(proc);
                }

                procMap[node] = proc;
            }
コード例 #8
0
ファイル: YieldTypeChecker.cs プロジェクト: omaragb/tlp182
 public PerLayerYieldTypeChecker(YieldTypeChecker @base, YieldingProc yieldingProc, Implementation impl, int currLayerNum, Graph <Block> implGraph)
 {
     this.@base        = @base;
     this.yieldingProc = yieldingProc;
     this.impl         = impl;
     this.currLayerNum = currLayerNum;
     this.implGraph    = implGraph;
     this.initialState = impl.Blocks[0];
     this.finalStates  = new HashSet <Absy>();
     this.implEdges    = new List <Tuple <Absy, int, Absy> >();
 }
コード例 #9
0
        public override Procedure VisitProcedure(Procedure node)
        {
            if (!civlTypeChecker.procToYieldingProc.ContainsKey(node))
            {
                return(node);
            }
            if (!procMap.ContainsKey(node))
            {
                YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[node];

                if (layerNum > yieldingProc.upperLayer)
                {
                    if (yieldingProc is ActionProc actionProc)
                    {
                        // yielding procedure already transformed to atomic action
                        var refinedAction = actionProc.RefinedActionAtLayer(layerNum);
                        if (refinedAction == null)
                        {
                            // TODO: This can only happen because YieldingProcChecker.AddCheckers calls
                            // VisitProcedure on every layer. Do this "call redirection" somewhere else?
                            return(node);
                        }
                        return(refinedAction.proc);
                    }
                    else if (yieldingProc is SkipProc)
                    {
                        // calls to skip procedures are erased
                        return(node);
                    }
                    else if (yieldingProc is MoverProc)
                    {
                        // mover procedure does not exist on this layer any more
                        return(node);
                    }
                }

                Procedure proc = (Procedure)node.Clone();
                proc.Name      = $"{node.Name}_{layerNum}";
                proc.InParams  = this.VisitVariableSeq(node.InParams);
                proc.OutParams = this.VisitVariableSeq(node.OutParams);
                proc.Requires  = this.VisitRequiresSeq(node.Requires);
                proc.Ensures   = this.VisitEnsuresSeq(node.Ensures);
                if (yieldingProc is MoverProc moverProc && yieldingProc.upperLayer == layerNum)
                {
                    proc.Modifies = moverProc.modifiedGlobalVars.Select(g => Expr.Ident(g)).ToList();
                }
                else
                {
                    proc.Modifies = civlTypeChecker.sharedVariableIdentifiers;
                    yieldingProcs.Add(proc);
                }

                procMap[node] = proc;
            }
コード例 #10
0
            private string CallCmdLabelAsync(CallCmd callCmd)
            {
                if (civlTypeChecker.procToIntroductionAction.ContainsKey(callCmd.Proc) ||
                    civlTypeChecker.procToLemmaProc.ContainsKey(callCmd.Proc))
                {
                    return(P);
                }

                if (civlTypeChecker.procToYieldInvariant.ContainsKey(callCmd.Proc))
                {
                    return(civlTypeChecker.procToYieldInvariant[callCmd.Proc].LayerNum == currLayerNum ? Y : P);
                }

                YieldingProc callee = civlTypeChecker.procToYieldingProc[callCmd.Proc];

                if (callCmd.IsAsync)
                {
                    if (callee is MoverProc && callee.upperLayer == currLayerNum)
                    {
                        return(ModifiesGlobalLabel(callee.proc.Modifies));
                    }

                    if (callee is ActionProc actionProc && callee.upperLayer < currLayerNum)
                    {
                        if (callCmd.HasAttribute(CivlAttributes.SYNC))
                        {
                            return(ModifiesGlobalLabel(actionProc.RefinedActionAtLayer(currLayerNum).modifiedGlobalVars));
                        }
                        else
                        {
                            return(P);
                        }
                    }

                    return(A);
                }
                else
                {
                    if (callee is MoverProc && callee.upperLayer == currLayerNum)
                    {
                        return(ModifiesGlobalLabel(callee.proc.Modifies));
                    }

                    if (callee is ActionProc actionProc && callee.upperLayer < currLayerNum)
                    {
                        return(ModifiesGlobalLabel(actionProc.RefinedActionAtLayer(currLayerNum).modifiedGlobalVars));
                    }

                    return(Y);
                }
            }
コード例 #11
0
 public SkipRefinementInstrumentation(
     CivlTypeChecker civlTypeChecker,
     YieldingProc yieldingProc,
     Dictionary <Variable, Variable> oldGlobalMap)
 {
     this.oldGlobalMap = new Dictionary <Variable, Variable>();
     foreach (Variable v in civlTypeChecker.sharedVariables)
     {
         var layerRange = civlTypeChecker.GlobalVariableLayerRange(v);
         if (layerRange.lowerLayerNum <= yieldingProc.upperLayer && yieldingProc.upperLayer < layerRange.upperLayerNum)
         {
             this.oldGlobalMap[v] = oldGlobalMap[v];
         }
     }
 }
コード例 #12
0
        private void TransformImpl(Implementation impl)
        {
            HashSet <Block> yieldingLoopHeaders;
            Graph <Block>   graph = ComputeYieldingLoopHeaders(impl, out yieldingLoopHeaders);

            // initialize globalSnapshotInstrumentation
            globalSnapshotInstrumentation = new GlobalSnapshotInstrumentation(civlTypeChecker);

            // initialize refinementInstrumentation
            Procedure    originalProc = implMap[impl].Proc;
            YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[originalProc];

            if (yieldingProc.upperLayer == this.layerNum)
            {
                refinementInstrumentation = new SomeRefinementInstrumentation(
                    civlTypeChecker,
                    impl,
                    originalProc,
                    globalSnapshotInstrumentation.OldGlobalMap,
                    yieldingLoopHeaders);
            }
            else
            {
                refinementInstrumentation = new NoneRefinementInstrumentation();
            }

            // initialize noninterferenceInstrumentation
            if (CommandLineOptions.Clo.TrustNonInterference)
            {
                noninterferenceInstrumentation = new NoneNoninterferenceInstrumentation();
            }
            else
            {
                noninterferenceInstrumentation = new SomeNoninterferenceInstrumentation(civlTypeChecker,
                                                                                        linearTypeChecker,
                                                                                        layerNum, absyMap, globalSnapshotInstrumentation.OldGlobalMap, yieldProc);
            }

            DesugarConcurrency(impl, graph, yieldingLoopHeaders);

            impl.LocVars.AddRange(globalSnapshotInstrumentation.NewLocalVars);
            impl.LocVars.AddRange(refinementInstrumentation.NewLocalVars);
            impl.LocVars.AddRange(noninterferenceInstrumentation.NewLocalVars);
        }
コード例 #13
0
ファイル: YieldTypeChecker.cs プロジェクト: omaragb/tlp182
            private int ParCallCmdLabel(ParCallCmd parCallCmd)
            {
                foreach (CallCmd callCmd in parCallCmd.CallCmds)
                {
                    if (@base.civlTypeChecker.procToYieldingProc[callCmd.Proc].upperLayer >= currLayerNum)
                    {
                        return(Y);
                    }
                }

                bool isRightMover     = true;
                bool isLeftMover      = true;
                int  numAtomicActions = 0;

                foreach (CallCmd callCmd in parCallCmd.CallCmds)
                {
                    YieldingProc callee = @base.civlTypeChecker.procToYieldingProc[callCmd.Proc];
                    isRightMover = isRightMover && callee.IsRightMover;
                    isLeftMover  = isLeftMover && callee.IsLeftMover;
                    if (callee is ActionProc)
                    {
                        numAtomicActions++;
                    }
                }

                if (isLeftMover && isRightMover)
                {
                    return(B);
                }
                else if (isLeftMover)
                {
                    return(L);
                }
                else if (isRightMover)
                {
                    return(R);
                }

                Debug.Assert(numAtomicActions == 1);
                return(A);
            }
コード例 #14
0
        public SomeRefinementInstrumentation(
            CivlTypeChecker civlTypeChecker,
            Implementation impl,
            Implementation originalImpl,
            Dictionary <Variable, Variable> oldGlobalMap,
            HashSet <Block> yieldingLoopHeaders)
        {
            newLocalVars = new List <Variable>();
            YieldingProc yieldingProc = civlTypeChecker.procToYieldingProc[originalImpl.Proc];
            int          layerNum     = yieldingProc.upperLayer;

            pc = Pc();
            newLocalVars.Add(pc);
            ok = Ok();
            newLocalVars.Add(ok);

            this.transitionRelationCache = new Dictionary <AtomicAction, Expr>();

            this.oldGlobalMap = new Dictionary <Variable, Variable>();
            foreach (Variable v in civlTypeChecker.sharedVariables)
            {
                var layerRange = civlTypeChecker.GlobalVariableLayerRange(v);
                if (layerRange.lowerLayerNum <= yieldingProc.upperLayer && yieldingProc.upperLayer < layerRange.upperLayerNum)
                {
                    this.oldGlobalMap[v] = oldGlobalMap[v];
                }
            }

            oldOutputMap = new Dictionary <Variable, Variable>();
            foreach (Variable f in impl.OutParams)
            {
                LocalVariable copy = Old(f);
                newLocalVars.Add(copy);
                oldOutputMap[f] = copy;
            }

            Dictionary <Variable, Expr> foroldMap = new Dictionary <Variable, Expr>();

            foreach (Variable g in civlTypeChecker.sharedVariables)
            {
                foroldMap[g] = Expr.Ident(oldGlobalMap[g]);
            }
            if (yieldingProc is ActionProc actionProc)
            {
                // The parameters of an atomic action come from the implementation that denotes the atomic action specification.
                // To use the transition relation computed below in the context of the yielding procedure of the refinement check,
                // we need to substitute the parameters.
                AtomicAction   atomicAction           = actionProc.refinedAction;
                Implementation atomicActionImpl       = atomicAction.impl;
                Dictionary <Variable, Expr> alwaysMap = new Dictionary <Variable, Expr>();
                for (int i = 0; i < impl.InParams.Count; i++)
                {
                    alwaysMap[atomicActionImpl.InParams[i]] = Expr.Ident(impl.InParams[i]);
                }

                for (int i = 0; i < impl.OutParams.Count; i++)
                {
                    alwaysMap[atomicActionImpl.OutParams[i]] = Expr.Ident(impl.OutParams[i]);
                }
                if (atomicAction.HasPendingAsyncs)
                {
                    Variable collectedPAs = civlTypeChecker.implToPendingAsyncCollector[originalImpl];
                    alwaysMap[atomicActionImpl.OutParams.Last()] = Expr.Ident(collectedPAs);
                    LocalVariable copy = Old(collectedPAs);
                    newLocalVars.Add(copy);
                    oldOutputMap[collectedPAs] = copy;
                }

                Substitution always   = Substituter.SubstitutionFromHashtable(alwaysMap);
                Substitution forold   = Substituter.SubstitutionFromHashtable(foroldMap);
                Expr         betaExpr = GetTransitionRelation(atomicAction);
                beta = Substituter.ApplyReplacingOldExprs(always, forold, betaExpr);
                Expr alphaExpr = Expr.And(atomicAction.gate.Select(g => g.Expr));
                alphaExpr.Type = Type.Bool;
                alpha          = Substituter.Apply(always, alphaExpr);
            }
            else
            {
                beta  = Expr.And(this.oldGlobalMap.Keys.Select(v => Expr.Eq(Expr.Ident(v), foroldMap[v])));
                alpha = Expr.True;
            }

            pcsForYieldingLoopsHeaders = new Dictionary <Block, Variable>();
            oksForYieldingLoopHeaders  = new Dictionary <Block, Variable>();
            foreach (Block header in yieldingLoopHeaders)
            {
                var pcForYieldingLoopHeader = PcForYieldingLoopHeader(header);
                newLocalVars.Add(pcForYieldingLoopHeader);
                pcsForYieldingLoopsHeaders[header] = pcForYieldingLoopHeader;
                var okForYieldingLoopHeader = OkForYieldingLoopHeader(header);
                newLocalVars.Add(okForYieldingLoopHeader);
                oksForYieldingLoopHeaders[header] = okForYieldingLoopHeader;
            }
        }