Example #1
0
    def report(state):
        init_tran = trans_dict[state.sig][e.Initial]
        msg = None

        get_state = lambda sig: l.get_state_by_sig(sig, flat_state_list)
        is_child = lambda sg: state in l.get_path_from_root(get_state(sg))[:-1]

        if isinstance(init_tran, e._Local):
            msg = 'cannot use LocalTransition for initial'
        elif isinstance(init_tran, e._Internal):
            msg = 'cannot use InternalTransition for initial'
        elif isinstance(init_tran, e._Choice):
            if init_tran.default is None:
                msg = ('must declare default when using Choice as initial')
            elif get_state(init_tran.default) is None:
                msg = 'default points to nonexistent state'
            elif not is_child(init_tran.default):
                msg = 'default target must be a child state'
            elif any(get_state(s) is None for s in init_tran.switch.values()):
                msg = 'switch dict references nonexistent state'
            elif not all(is_child(sig) for sig in init_tran.switch.values()):
                msg = 'switch dict value not a child state'
        # at this point we know it is instance of regular Transition
        elif init_tran.target == st.sig:
            msg = 'initial transition cannot be a loop'
        elif get_state(init_tran.target) is None:
            msg = 'transition target points to nonexistent state'
        elif not is_child(init_tran.target):
            msg = 'target state must be a child state'
        elif init_tran.guard is not e.always_true:
            msg = 'initial transition cannot have a guard'
        return (state, msg) if msg else None
Example #2
0
 def visit(state, visited=set()):  # instantiating should be ok in this case
     if state in visited:
         return set()
     visited.add(state)
     # if orthogonal is reachable, its states are automatically reachable
     if state.kind == 'orthogonal':
         [visit(st, visited) for st in state.states]
     # all state's parents are reachable
     # visit transition targets going out of every parent state
     for parent in l.get_path_from_root(state):
         visit(parent, visited)
     # visit transition targets going out of current state
     for tran in trans_dict.get(state.sig, {}).values():
         if isinstance(tran, e._Choice):
             to_visit = [l.get_state_by_sig(sig, flat_state_list)
                         for sig in tran.switch.values() + [tran.default]]
         else:
             to_visit = [l.get_state_by_sig(tran.target, flat_state_list)]
         # nonexistent states (None values in list) are checked elsewhere
         [visit(st, visited) for st in to_visit if st is not None]
     return visited