Example #1
0
    def test_enums(self):
        version = ir.OFVersion("1.0", 1)
        input = fe.OFInput(filename="test.dat",
                    wire_versions=(1,),
                    classes=(),
                    enums=(
                        fe.OFEnum(name='ofp_flow_wildcards',
                                  entries=(fe.OFEnumEntry(name="OFPFW_IN_PORT", value=0x01, params={}),
                                           fe.OFEnumEntry(name="OFPFW_DL_VLAN", value=0x2, params={})),
                                  params = dict(wire_type="uint32_t", bitmask=True)
                                 ),
                        fe.OFEnum(name='ofp_queue_properties',
                                  entries=(fe.OFEnumEntry(name="OFPQT_NONE", value=0x00, params={}),
                                           fe.OFEnumEntry(name="OFPQT_MIN_RATE", value=0x1, params={})),
                                  params = dict(wire_type="uint32_t")
                                 ),
                        )
                    )

        p = ir.build_protocol(version, [ input ])
        eq_(0, len(p.classes))
        eq_(2, len(p.enums))
        e = p.enums[0]
        eq_("ofp_flow_wildcards", e.name)
        eq_(True, e.is_bitmask)
        eq_("uint32_t", e.wire_type)
        eq_(ir.OFEnumEntry(name="OFPFW_IN_PORT", value=0x01, params={}), e.entries[0])
        eq_(ir.OFEnumEntry(name="OFPFW_DL_VLAN", value=0x02, params={}), e.entries[1])

        e = p.enums[1]
        eq_("ofp_queue_properties", e.name)
        eq_(False, e.is_bitmask)
        eq_("uint32_t", e.wire_type)
        eq_(ir.OFEnumEntry(name="OFPQT_NONE", value=0x00, params={}), e.entries[0])
        eq_(ir.OFEnumEntry(name="OFPQT_MIN_RATE", value=0x01, params={}), e.entries[1])
Example #2
0
def create_ofinput(filename, ast):
    """
    Create an OFInput from an AST

    @param ast An AST as returned by loxi_front_end.parser.parse

    @returns An OFInput object
    """
    ctx = FrontendCtx(set())
    ofinput = ir.OFInput(filename, wire_versions=set(), classes=[], enums=[])

    for decl_ast in ast:
        if decl_ast[0] == 'struct':
            # 0: "struct"
            # 1: name
            # 2: potentially list of [param_name, param_value]
            # 3: super_class or None
            # 4: list of members
            superclass = decl_ast[3]
            members = [create_member(m_ast, ctx) for m_ast in decl_ast[4]]

            discriminators = [
                m for m in members if isinstance(m, ir.OFDiscriminatorMember)
            ]
            if len(discriminators) > 1:
                raise InputError(
                    "%s: Cannot support more than one discriminator by class - got %s"
                    % (decl_ast[1], repr(discriminators)))
            ofclass = ir.OFClass(
                name=decl_ast[1],
                members=members,
                superclass=superclass,
                virtual=len(discriminators) > 0,
                params={param: value
                        for param, value in decl_ast[2]})
            ofinput.classes.append(ofclass)
        if decl_ast[0] == 'enum':
            # 0: "enum"
            # 1: name
            # 2: potentially list of [param_name, param_value]
            # 3: list of [constant_name, constant_value]+
            enum = ir.OFEnum(
                name=decl_ast[1],
                entries=[
                    ir.OFEnumEntry(
                        name=x[0],
                        value=x[2],
                        params={param: value
                                for param, value in x[1]}) for x in decl_ast[3]
                ],
                params={param: value
                        for param, value in decl_ast[2]})
            ofinput.enums.append(enum)
        elif decl_ast[0] == 'metadata':
            if decl_ast[1] == 'version':
                if decl_ast[2] == 'any':
                    ofinput.wire_versions.update(
                        v.wire_version
                        for v in loxi_globals.OFVersions.all_supported)
                elif int(decl_ast[2]
                         ) in loxi_globals.OFVersions.wire_version_map:
                    ofinput.wire_versions.add(int(decl_ast[2]))
                else:
                    raise InputError("Unrecognized wire protocol version %r" %
                                     decl_ast[2])
                found_wire_version = True

    if not ofinput.wire_versions:
        raise InputError("Missing #version metadata")

    return ofinput