Пример #1
0
def _bitblast(aut):
    """Return `Automaton` with bitvector formulas.

    For each integer, the corresponding list of
    bitnames is added to the symbol table (attr `vars`).

    @type aut: `Automaton`
    """
    players = dict(aut.players)
    aut = copy.copy(aut)
    t = bv.bitblast_table(aut.vars)
    init, action = bv.type_invariants(t)
    for var, c in init.items():
        owner = aut.vars[var]['owner']
        # collect type invariants of parameters too,
        # for convenience later
        aut.init.setdefault(owner, list())
        aut.init[owner].extend(c)
    for var, c in action.items():
        owner = aut.vars[var]['owner']
        aut.action.setdefault(owner, list())
        aut.action[owner].extend(c)
    # conjoin to avoid it later over BDD nodes
    _conj_owner(aut, 'env', 'infix')
    _conj_owner(aut, 'sys', 'infix')
    a = Automaton()
    a.players = players
    a.vars = t
    # TODO: replace GR(1) syntax check
    # spec.check_syntax()
    _bitblast_owner(aut, a, 'env', t)
    _bitblast_owner(aut, a, 'sys', t)
    return a
Пример #2
0
def _bitblast(aut):
    """Return `Automaton` with bitvector formulas.

    For each integer, the corresponding list of
    bitnames is added to the symbol table (attr `vars`).

    @type aut: `Automaton`
    """
    players = dict(aut.players)
    aut = copy.copy(aut)
    t = bv.bitblast_table(aut.vars)
    init, action = bv.type_invariants(t)
    for var, c in init.items():
        owner = aut.vars[var]['owner']
        # collect type invariants of parameters too,
        # for convenience later
        aut.init.setdefault(owner, list())
        aut.init[owner].extend(c)
    for var, c in action.items():
        owner = aut.vars[var]['owner']
        aut.action.setdefault(owner, list())
        aut.action[owner].extend(c)
    # conjoin to avoid it later over BDD nodes
    _conj_owner(aut, 'env', 'infix')
    _conj_owner(aut, 'sys', 'infix')
    a = Automaton()
    a.players = players
    a.vars = t
    # TODO: replace GR(1) syntax check
    # spec.check_syntax()
    _bitblast_owner(aut, a, 'env', t)
    _bitblast_owner(aut, a, 'sys', t)
    return a
Пример #3
0
def test_type_invariants():
    t = dict(x=dict(type='int', dom=(0, 3), init=2))
    t = bv.bitblast_table(t)
    init, action = bv.type_invariants(t)
    init_ = dict(x=['x = 2', '(0 <= x)  /\  (x <= 3)'])
    assert init == init_, init
    s = (
         "    (0 <= x)  /\  (x <= 3)"
         "  /\ (0 <= x') /\  (x' <= 3)")
    action_ = dict(x=[s])
    assert action == action_, action
Пример #4
0
def test_mixed_fol_bitblasted():
    t = dict(x=dict(type='bool', owner='sys'),
             y=dict(type='int', dom=(0, 3), owner='sys'))
    t = bv.bitblast_table(t)
    s = '(x /\ y_0) \/ (y < 0)'
    tree_0 = parser.parse(s)
    q = 'y < 0'
    tree_1 = parser.parse(q)
    f0 = tree_0.flatten(t=t)
    f1 = tree_1.flatten(t=t)
    assert f0 == ' |  & x y_0  {f1} '.format(f1=f1), (f0, f1)
Пример #5
0
    def add_vars(self, dvars):
        r"""Refine variables in `dvars`.

        The variables in `dvars` should have type hints.
        A Boolean-valued variable remains so.
        An integer-valued variable is assumed to take the
        value resulting as a function of some (fresh)
        Boolean-valued variables.

        Sometimes these variables are called "bits".
        The function is based on two's complement,
        see `omega.logic.bitvector` for details.

        In other words, type hints are used to pick
        a refinement of integers by finitely many bits.
        A sufficient number of bits is selected,
        and operations assume this as type invariant,
        *not* the exact type hint given.

        For example, an integer `x` with type hint `x \in 0..2`
        will be refined using 2 Boolean-valued variables
        `x_0` and `x_1`. All operations and quantification
        will assume that `x \in 0..3`.
        Mind the extra value (3) allowed,
        compared to the hint (0..2).

        Attention:

        - Fine-grained type predicates
          (`n..m` with `n` and `m` other than powers of 2)
          are not managed here.

        - Priming is not reasoned about here.
          Priming is cared for by other modules.

        The method `add_vars` adds to `vars[var]` the keys:

          - `"bitnames"`: `list`
          - `"signed"`: `True` if signed integer
          - `"width"`: `len(bitnames)`
        """
        assert dvars, dvars
        self._avoid_redeclaration(dvars)
        vrs = {k: v for k, v in dvars.items()
               if k not in self.vars}
        if not vrs:
            return
        t = bv.bitblast_table(vrs)
        self.vars.update(t)
        bits = bv.bit_table(t, t)
        for bit in bits:
            self.bdd.add_var(bit)
Пример #6
0
    def add_vars(self, dvars):
        r"""Refine variables in `dvars`.

        The variables in `dvars` should have type hints.
        A Boolean-valued variable remains so.
        An integer-valued variable is assumed to take the
        value resulting as a function of some (fresh)
        Boolean-valued variables.

        Sometimes these variables are called "bits".
        The function is based on two's complement,
        see `omega.logic.bitvector` for details.

        In other words, type hints are used to pick
        a refinement of integers by finitely many bits.
        A sufficient number of bits is selected,
        and operations assume this as type invariant,
        *not* the exact type hint given.

        For example, an integer `x` with type hint `x \in 0..2`
        will be refined using 2 Boolean-valued variables
        `x_0` and `x_1`. All operations and quantification
        will assume that `x \in 0..3`.
        Mind the extra value (3) allowed,
        compared to the hint (0..2).

        Attention:

        - Fine-grained type predicates
          (`n..m` with `n` and `m` other than powers of 2)
          are not managed here.

        - Priming is not reasoned about here.
          Priming is cared for by other modules.

        The method `add_vars` adds to `vars[var]` the keys:

          - `"bitnames"`: `list`
          - `"signed"`: `True` if signed integer
          - `"width"`: `len(bitnames)`
        """
        assert dvars, dvars
        self._avoid_redeclaration(dvars)
        vrs = {k: v for k, v in dvars.items() if k not in self.vars}
        if not vrs:
            return
        t = bv.bitblast_table(vrs)
        self.vars.update(t)
        bits = bv.bit_table(t, t)
        for bit in bits:
            self.bdd.add_var(bit)
Пример #7
0
def _bitblast(aut):
    aut = copy.copy(aut)
    players = set(aut.players)
    players.add(None)
    t, init, action = bv.bitblast_table(aut.vars, players)
    init.pop(None)
    action.pop(None)
    for k, v in init.iteritems():
        aut.init[k].extend(v)
    for k, v in action.iteritems():
        aut.action[k].extend(v)
    # conjoin now, instead of later with BDDs
    for k in aut.players:
        symbolic._conj_owner(aut, k, 'infix')
    a = Automaton()
    a.players = aut.players
    a.vars = t
    _bitblast_attr(aut, a, t)
    return a
Пример #8
0
def _bitblast(aut):
    aut = copy.copy(aut)
    players = set(aut.players)
    players.add(None)
    t, init, action = bv.bitblast_table(aut.vars, players)
    init.pop(None)
    action.pop(None)
    for k, v in init.items():
        aut.init[k].extend(v)
    for k, v in action.items():
        aut.action[k].extend(v)
    # conjoin now, instead of later with BDDs
    for k in aut.players:
        symbolic._conj_owner(aut, k, 'infix')
    a = Automaton()
    a.players = aut.players
    a.vars = t
    _bitblast_attr(aut, a, t)
    return a