Пример #1
0
def simplify_if_only_one_name(res_dp, fnames, rnames):
    if len(fnames) == 1:
        fnames = fnames[0]
        funsp = res_dp.get_fun_space()
        res_dp = make_series(Mux(funsp[0], [()]), res_dp)

    if len(rnames) == 1:
        rnames = rnames[0]
        ressp = res_dp.get_res_space()
        res_dp = make_series(res_dp, Mux(ressp, 0))
    return res_dp, fnames, rnames
Пример #2
0
def simplify_if_only_one_name(res_dp, fnames, rnames):
    if len(fnames) == 1:
        fnames = fnames[0]
        funsp = res_dp.get_fun_space()
        res_dp = make_series(Mux(funsp[0], [()]), res_dp)

    if len(rnames) == 1:
        rnames = rnames[0]
        ressp = res_dp.get_res_space()
        res_dp = make_series(res_dp, Mux(ressp, 0))
    return res_dp, fnames, rnames
Пример #3
0
def its_dp_as_product(ndp):
    """ If fnames == 1 """
    dp = ndp.get_dp()
    if len(ndp.get_fnames()) == 1:
        F0 = dp.get_fun_space()
        F = PosetProduct((F0, ))
        down = Mux(F, 0)
        dp = make_series(down, dp)

    if len(ndp.get_rnames()) == 1:
        R0 = dp.get_res_space()
        lift = Mux(R0, [()])
        dp = make_series(dp, lift)
    return dp
Пример #4
0
def its_dp_as_product(ndp):
    """ If fnames == 1 """
    dp = ndp.get_dp()
    if len(ndp.get_fnames()) == 1:
        F0 = dp.get_fun_space()
        F = PosetProduct((F0,))
        down = Mux(F, 0)
        dp = make_series(down, dp)

    if len(ndp.get_rnames()) == 1:
        R0 = dp.get_res_space()
        lift = Mux(R0, [()])
        dp = make_series(dp, lift)
    return dp
Пример #5
0
def eval_ndp_dpwrap(r, context):
    tu = get_types_universe()

    statements = unwrap_list(r.statements)
    fun = [x for x in statements if isinstance(x, CDP.FunStatement)]
    res = [x for x in statements if isinstance(x, CDP.ResStatement)]

    assert len(fun) + len(res) == len(statements), statements
    impl = r.impl

    from .eval_primitivedp_imp import eval_primitivedp
    dp = eval_primitivedp(impl, context)

    fnames = [f.fname.value for f in fun]
    rnames = [r.rname.value for r in res]

    if len(fnames) == 1:
        use_fnames = fnames[0]
    else:
        use_fnames = fnames
    if len(rnames) == 1:
        use_rnames = rnames[0]
    else:
        use_rnames = rnames

    dp_F = dp.get_fun_space()
    dp_R = dp.get_res_space()

    # Check that the functions are the same
    want_Fs = tuple([eval_space(f.unit, context) for f in fun])
    if len(want_Fs) == 1:
        want_F = want_Fs[0]
    else:
        want_F = PosetProduct(want_Fs)

    want_Rs = tuple([eval_space(r.unit, context) for r in res])
    if len(want_Rs) == 1:
        want_R = want_Rs[0]
    else:
        want_R = PosetProduct(want_Rs)

    mcdp_dev_warning('Not sure about this')
    dp_prefix = get_conversion(want_F, dp_F)
    dp_postfix = get_conversion(dp_R, want_R)

    if dp_prefix is not None:
        dp = make_series(dp_prefix, dp)

    if dp_postfix is not None:
        dp = make_series(dp, dp_postfix)

    try:
        w = SimpleWrap(dp=dp, fnames=use_fnames, rnames=use_rnames)
    except ValueError as e:
        raise DPSemanticError(str(e), r.where)

    ftypes = w.get_ftypes(fnames)
    rtypes = w.get_rtypes(rnames)
    ftypes_expected = PosetProduct(tuple([eval_space(f.unit, context) for f in fun]))
    rtypes_expected = PosetProduct(tuple([eval_space(r.unit, context) for r in res]))

    try:
        tu.check_equal(ftypes, ftypes_expected)
        tu.check_equal(rtypes, rtypes_expected)
    except NotEqual as e:
        msg = 'The types in the description do not match.'
        raise_wrapped(DPSemanticError, e, msg,
                      dp=dp,
                   ftypes=ftypes,
                   ftypes_expected=ftypes_expected,
                   rtypes=rtypes,
                   rtypes_expected=rtypes_expected, compact=True)

    return w
Пример #6
0
def eval_ndp_dpwrap(r, context):
    tu = get_types_universe()

    statements = unwrap_list(r.statements)
    fun = [x for x in statements if isinstance(x, CDP.FunStatement)]
    res = [x for x in statements if isinstance(x, CDP.ResStatement)]

    assert len(fun) + len(res) == len(statements), statements
    impl = r.impl

    from .eval_primitivedp_imp import eval_primitivedp
    dp = eval_primitivedp(impl, context)

    fnames = [f.fname.value for f in fun]
    rnames = [r.rname.value for r in res]

    if len(fnames) == 1:
        use_fnames = fnames[0]
    else:
        use_fnames = fnames
    if len(rnames) == 1:
        use_rnames = rnames[0]
    else:
        use_rnames = rnames

    dp_F = dp.get_fun_space()
    dp_R = dp.get_res_space()

    # Check that the functions are the same
    want_Fs = tuple([eval_space(f.unit, context) for f in fun])
    if len(want_Fs) == 1:
        want_F = want_Fs[0]
    else:
        want_F = PosetProduct(want_Fs)

    want_Rs = tuple([eval_space(r.unit, context) for r in res])
    if len(want_Rs) == 1:
        want_R = want_Rs[0]
    else:
        want_R = PosetProduct(want_Rs)

    mcdp_dev_warning('Not sure about this')
    dp_prefix = get_conversion(want_F, dp_F)
    dp_postfix = get_conversion(dp_R, want_R)

    if dp_prefix is not None:
        dp = make_series(dp_prefix, dp)

    if dp_postfix is not None:
        dp = make_series(dp, dp_postfix)

    try:
        w = SimpleWrap(dp=dp, fnames=use_fnames, rnames=use_rnames)
    except ValueError as e:
        raise DPSemanticError(str(e), r.where)

    ftypes = w.get_ftypes(fnames)
    rtypes = w.get_rtypes(rnames)
    ftypes_expected = PosetProduct(
        tuple([eval_space(f.unit, context) for f in fun]))
    rtypes_expected = PosetProduct(
        tuple([eval_space(r.unit, context) for r in res]))

    try:
        tu.check_equal(ftypes, ftypes_expected)
        tu.check_equal(rtypes, rtypes_expected)
    except NotEqual as e:
        msg = 'The types in the description do not match.'
        raise_wrapped(DPSemanticError, e, msg,
                      dp=dp,
                      ftypes=ftypes,
                      ftypes_expected=ftypes_expected,
                      rtypes=rtypes,
                      rtypes_expected=rtypes_expected, compact=True)

    return w
Пример #7
0
def connect2(ndp1, ndp2, connections, split, repeated_ok=False):
    """ 
        Note the argument split must be a list of strings so 
        that orders are preserved and deterministic. 
    """

    if ndp1 is ndp2:
        raise ValueError('Equal')

    def common(x, y):
        return len(set(x + y)) != len(set(x)) + len(set(y))

    if not repeated_ok:
        if (common(ndp1.get_fnames(), ndp2.get_fnames())
                or common(ndp1.get_rnames(), ndp2.get_rnames())):
            raise_desc(DPInternalError,
                       'repeated names',
                       ndp1=ndp1,
                       ndp2=ndp2,
                       connections=connections,
                       split=split)

    if len(set(split)) != len(split):
        msg = 'Repeated signals in split: %s' % str(split)
        raise ValueError(msg)
    try:
        if not connections:
            raise ValueError('Empty connections')

        #     |   |------------------------->A
        #     |   |          |-B1(split)----->
        # f1->|   |--B1----->|         ___
        #     | 1 |          |----B2->|   |   all_s2 = B2 + C2  all_s1 = B1 + C1
        #     |___| -C1--C2---------->| 2 |->r2
        # ---------D----------------->|___|
        #
        # ftot = f1 + D
        # rtot = A + b1 + r2
        # A + B + C = r1
        # B + C + D = f2
        # split = A + B

        # split = B1 is given
        # find B2 from B1
        def s2_from_s1(s1):
            for c in connections:
                if c.s1 == s1: return c.s2
            assert False, 'Cannot find connection with s1 = %s' % s1

        def s1_from_s2(s2):
            for c in connections:
                if c.s2 == s2: return c.s1
            assert False, 'Cannot find connection with s2 = %s' % s2

        f1 = ndp1.get_fnames()
        r1 = ndp1.get_rnames()
        f2 = ndp2.get_fnames()
        r2 = ndp2.get_rnames()

        all_s2 = set([c.s2 for c in connections])
        all_s1 = set([c.s1 for c in connections])

        # assert that all split are in s1
        for x in split:
            assert x in all_s1

        B1 = list(split)
        B2 = map(s2_from_s1, B1)
        C2 = list_diff(all_s2, B2)
        C1 = map(s1_from_s2, C2)
        A = list_diff(r1, B1 + C1)
        D = list_diff(f2, B2 + C2)

        # print('B1: %s' % B1)
        # print('B2: %s' % B2)
        # print('C2: %s' % C1)
        # print('C1: %s' % C1)
        # print(' A: %s' % A)
        # print(' D: %s' % D)
        fntot = f1 + D
        rntot = A + B1 + r2

        if there_are_repetitions(fntot) or there_are_repetitions(rntot):
            raise_desc(NotImplementedError,
                       'Repeated names',
                       fnames=fntot,
                       rnames=fntot)

        # now I can create Ftot and Rtot
        f1_types = ndp1.get_ftypes(f1)

        D_types = ndp2.get_ftypes(D)
        #         print('f1: %s' % f1)
        #         print('f1 types: %s' % f1_types)
        #         print('D: %s' % D)
        #         print('D types: %s' % D_types)

        Ftot = PosetProduct(tuple(list(f1_types) + list(D_types)))
        Rtot = PosetProduct(
            tuple(
                list(ndp1.get_rtypes(A)) + list(ndp1.get_rtypes(B1)) +
                list(ndp2.get_rtypes(r2))))

        # print('Ftot: %s' % str(Ftot))
        # print('      %s' % str(fntot))
        # print('Rtot: %s' % str(Rtot))
        # print('      %s' % str(rntot))
        assert len(fntot) == len(Ftot), (fntot, Ftot)
        assert len(rntot) == len(Rtot), (rntot, Rtot)

        # I can create the first muxer m1
        # from ftot to Product(f1, D)

        m1_for_f1 = [fntot.index(s) for s in f1]
        m1_for_D = [fntot.index(s) for s in D]

        m1coords = [m1_for_f1, m1_for_D]
        m1 = Mux(Ftot, m1coords)

        # print('m1: %s' % m1)
        # print('m1.R: %s' % m1.get_res_space())

        # Get Identity on D
        D_types = ndp2.get_ftypes(D)
        Id_D = Identity(D_types)

        ndp1_p = its_dp_as_product(ndp1)
        X = make_parallel(ndp1_p, Id_D)

        # make sure we can connect
        m1_X = make_series(m1, X)

        # print('m1_X = %s' % m1_X)
        # print('m1_X.R = %s' % m1_X.get_res_space()  )

        def coords_cat(c1, m):
            if m != ():
                return c1 + (m, )
            else:
                return c1

        A_B1_types = PosetProduct(
            tuple(ndp1.get_rtypes(A)) + tuple(ndp1.get_rtypes(B1)))
        Id_A_B1 = Identity(A_B1_types)
        ndp2_p = its_dp_as_product(ndp2)
        Z = make_parallel(Id_A_B1, ndp2_p)
        # print('Z.R = %s' % Z.get_res_space())
        # print('B1: %s' % B1)
        # print('R2: %s' % r2)
        m2coords_A = [(0, (A + B1).index(x)) for x in A]
        m2coords_B1 = [(0, (A + B1).index(x)) for x in B1]
        m2coords_r2 = [(1, r2.index(x)) for x in r2]
        m2coords = m2coords_A + m2coords_B1 + m2coords_r2
        # print('m2coords_A: %r' % m2coords_A)
        # print('m2coords_B1: %r' % m2coords_B1)
        # print('m2coords_r2: %r' % m2coords_r2)
        # print('m2coords: %r' % m2coords)

        # print('Z.R: %s' % Z.get_res_space())
        m2 = Mux(Z.get_res_space(), m2coords)

        assert len(m2.get_res_space()) == len(rntot), ((m2.get_res_space(),
                                                        rntot))
        # make sure we can connect
        make_series(Z, m2)

        #
        #  f0 -> |m1| -> | X | -> |Y |-> |Z| -> |m2| -> r0
        #
        # X = dp1 | Id_D
        # Z = Id_B1 | dp2

        #      ___
        #     |   |------------------------->A
        #     |   |          |-B1----------->
        # f1->|   |--B1----->|         ___
        #     | 1 |          |----B2->|   |
        #     |___| -C1-----------C2->| 2 |->r2
        # ---------D----------------->|___|

        #      ___
        #     |   |-------------------------------->A
        #     |   |  .            *-B1-------.----->
        # f1->|   |  . |--B1----->*          .   ___
        #     | 1 |--.-|          *----B2->| .  |   |
        #     |___|  . |-C1------------C2->|-.->| 2 |->r2
        # ---------D-.-------------------->| .  |___|
        # m1  | X | Y                        |  Z    | m2

        # I need to write the muxer
        # look at the end
        # iterate 2's functions

        Y_coords_A_B1 = []
        for x in A:
            Y_coords_A_B1.append((0, r1.index(x)))
        for x in B1:
            Y_coords_A_B1.append((0, r1.index(x)))

        Y_coords_B2_C2_D = []
        for x in f2:
            if (x in B2) or (x in C2):
                Y_coords_B2_C2_D.append((0, r1.index(s1_from_s2(x))))
                assert x not in D
            elif x in D:
                Y_coords_B2_C2_D.append((1, D.index(x)))
            else:
                assert False

        # print ('Y_coords_A_B1: %s' % Y_coords_A_B1)
        # print ('Y_coords_B2_C2_D: %s' % Y_coords_B2_C2_D)
        Y_coords = [Y_coords_A_B1, Y_coords_B2_C2_D]
        Y = Mux(m1_X.get_res_space(), Y_coords)

        # m1* Xp Y* Zp m2*
        # Let's make series
        # m1_X is simplifed
        Y_Z = make_series(Y, Z)
        Y_Z_m2 = make_series(Y_Z, m2)

        res_dp = make_series(m1_X, Y_Z_m2)

        fnames = fntot
        rnames = rntot

        res_dp, fnames, rnames = simplify_if_only_one_name(
            res_dp, fnames, rnames)

        # print('res_dp: %s' % res_dp)
        res = dpwrap(res_dp, fnames, rnames)

        return res

    except Exception as e:
        msg = 'connect2() failed'
        raise_wrapped(DPInternalError,
                      e,
                      msg,
                      ndp1=ndp1,
                      ndp2=ndp2,
                      connections=connections,
                      split=split)
Пример #8
0
def connect2(ndp1, ndp2, connections, split, repeated_ok=False):
    """ 
        Note the argument split must be a list of strings so 
        that orders are preserved and deterministic. 
    """

    if ndp1 is ndp2:
        raise ValueError('Equal')
    
    def common(x, y):
        return len(set(x + y)) != len(set(x)) + len(set(y))

    if not repeated_ok:
        if (common(ndp1.get_fnames(), ndp2.get_fnames()) or
            common(ndp1.get_rnames(), ndp2.get_rnames())):
            raise_desc(DPInternalError, 'repeated names', ndp1=ndp1, ndp2=ndp2,
                       connections=connections, split=split)

    if len(set(split)) != len(split):
        msg = 'Repeated signals in split: %s' % str(split)
        raise ValueError(msg)
    try:
        if not connections:
            raise ValueError('Empty connections')

        #     |   |------------------------->A
        #     |   |          |-B1(split)----->
        # f1->|   |--B1----->|         ___
        #     | 1 |          |----B2->|   |   all_s2 = B2 + C2  all_s1 = B1 + C1
        #     |___| -C1--C2---------->| 2 |->r2
        # ---------D----------------->|___|
        #
        # ftot = f1 + D
        # rtot = A + b1 + r2
        # A + B + C = r1
        # B + C + D = f2
        # split = A + B

        # split = B1 is given
        # find B2 from B1
        def s2_from_s1(s1):
            for c in connections:
                if c.s1 == s1: return c.s2
            assert False, 'Cannot find connection with s1 = %s' % s1
        def s1_from_s2(s2):
            for c in connections:
                if c.s2 == s2: return c.s1
            assert False, 'Cannot find connection with s2 = %s' % s2

        f1 = ndp1.get_fnames()
        r1 = ndp1.get_rnames()
        f2 = ndp2.get_fnames()
        r2 = ndp2.get_rnames()

        all_s2 = set([c.s2 for c in connections])
        all_s1 = set([c.s1 for c in connections])

        # assert that all split are in s1
        for x in split: assert x in all_s1

        B1 = list(split)
        B2 = map(s2_from_s1, B1)
        C2 = list_diff(all_s2, B2)
        C1 = map(s1_from_s2, C2)
        A = list_diff(r1, B1 + C1)
        D = list_diff(f2, B2 + C2)

        # print('B1: %s' % B1)
        # print('B2: %s' % B2)
        # print('C2: %s' % C1)
        # print('C1: %s' % C1)
        # print(' A: %s' % A)
        # print(' D: %s' % D)
        fntot = f1 + D
        rntot = A + B1 + r2

        if there_are_repetitions(fntot) or there_are_repetitions(rntot):
            raise_desc(NotImplementedError, 'Repeated names', fnames=fntot, rnames=fntot)

        # now I can create Ftot and Rtot
        f1_types = ndp1.get_ftypes(f1)

        D_types = ndp2.get_ftypes(D)
#         print('f1: %s' % f1)
#         print('f1 types: %s' % f1_types)
#         print('D: %s' % D)
#         print('D types: %s' % D_types)

        Ftot = PosetProduct(tuple(list(f1_types) + list(D_types)))
        Rtot = PosetProduct(tuple(list(ndp1.get_rtypes(A)) +
                                  list(ndp1.get_rtypes(B1)) +
                                  list(ndp2.get_rtypes(r2))))

        # print('Ftot: %s' % str(Ftot))
        # print('      %s' % str(fntot))
        # print('Rtot: %s' % str(Rtot))
        # print('      %s' % str(rntot))
        assert len(fntot) == len(Ftot), (fntot, Ftot)
        assert len(rntot) == len(Rtot), (rntot, Rtot)

        # I can create the first muxer m1
        # from ftot to Product(f1, D)

        m1_for_f1 = [fntot.index(s) for s in f1]
        m1_for_D = [fntot.index(s) for s in D]

        m1coords = [m1_for_f1, m1_for_D]
        m1 = Mux(Ftot, m1coords)

        # print('m1: %s' % m1)
        # print('m1.R: %s' % m1.get_res_space())

        # Get Identity on D
        D_types = ndp2.get_ftypes(D)
        Id_D = Identity(D_types)

        ndp1_p = its_dp_as_product(ndp1)
        X = make_parallel(ndp1_p, Id_D)

        # make sure we can connect
        m1_X = make_series(m1, X)
        # print('m1_X = %s' % m1_X)
        # print('m1_X.R = %s' % m1_X.get_res_space()  )
        
        def coords_cat(c1, m):
            if m != ():
                return c1 + (m,)
            else:
                return c1
        
        A_B1_types = PosetProduct(tuple(ndp1.get_rtypes(A)) + tuple(ndp1.get_rtypes(B1)))
        Id_A_B1 = Identity(A_B1_types)
        ndp2_p = its_dp_as_product(ndp2)
        Z = make_parallel(Id_A_B1, ndp2_p)
        # print('Z.R = %s' % Z.get_res_space())
        # print('B1: %s' % B1)
        # print('R2: %s' % r2)
        m2coords_A = [(0, (A + B1).index(x)) for x in A]
        m2coords_B1 = [(0, (A + B1).index(x)) for x in B1]
        m2coords_r2 = [(1, r2.index(x)) for x in r2]
        m2coords = m2coords_A + m2coords_B1 + m2coords_r2
        # print('m2coords_A: %r' % m2coords_A)
        # print('m2coords_B1: %r' % m2coords_B1)
        # print('m2coords_r2: %r' % m2coords_r2)
        # print('m2coords: %r' % m2coords)

        # print('Z.R: %s' % Z.get_res_space())
        m2 = Mux(Z.get_res_space(), m2coords)
        
        assert len(m2.get_res_space()) == len(rntot), ((m2.get_res_space(), rntot))
        # make sure we can connect
        make_series(Z, m2)

        #
        #  f0 -> |m1| -> | X | -> |Y |-> |Z| -> |m2| -> r0
        #
        # X = dp1 | Id_D
        # Z = Id_B1 | dp2

        #      ___
        #     |   |------------------------->A
        #     |   |          |-B1----------->
        # f1->|   |--B1----->|         ___
        #     | 1 |          |----B2->|   |
        #     |___| -C1-----------C2->| 2 |->r2
        # ---------D----------------->|___|

        #      ___
        #     |   |-------------------------------->A
        #     |   |  .            *-B1-------.----->
        # f1->|   |  . |--B1----->*          .   ___
        #     | 1 |--.-|          *----B2->| .  |   |
        #     |___|  . |-C1------------C2->|-.->| 2 |->r2
        # ---------D-.-------------------->| .  |___|
        # m1  | X | Y                        |  Z    | m2

        # I need to write the muxer
        # look at the end
        # iterate 2's functions

        Y_coords_A_B1 = []
        for x in A:
            Y_coords_A_B1.append((0, r1.index(x)))
        for x in B1:
            Y_coords_A_B1.append((0, r1.index(x)))
        
        Y_coords_B2_C2_D = []
        for x in f2:
            if (x in B2) or (x in C2):
                Y_coords_B2_C2_D.append((0, r1.index(s1_from_s2(x))))
                assert x not in D
            elif x in D:
                Y_coords_B2_C2_D.append((1, D.index(x)))
            else:
                assert False

        # print ('Y_coords_A_B1: %s' % Y_coords_A_B1)
        # print ('Y_coords_B2_C2_D: %s' % Y_coords_B2_C2_D)
        Y_coords = [Y_coords_A_B1, Y_coords_B2_C2_D]
        Y = Mux(m1_X.get_res_space(), Y_coords)

        # m1* Xp Y* Zp m2*
        # Let's make series
        # m1_X is simplifed
        Y_Z = make_series(Y, Z)
        Y_Z_m2 = make_series(Y_Z, m2)

        res_dp = make_series(m1_X, Y_Z_m2)

        fnames = fntot
        rnames = rntot

        res_dp, fnames, rnames = simplify_if_only_one_name(res_dp, fnames, rnames)

        # print('res_dp: %s' % res_dp)
        res = dpwrap(res_dp, fnames, rnames)

        return res

    except Exception as e:
        msg = 'connect2() failed'
        raise_wrapped(DPInternalError, e, msg, ndp1=ndp1, ndp2=ndp2,
                      connections=connections, split=split)