:: # Copyright 2013, Big Switch Networks, Inc.
:: #
:: # LoxiGen is licensed under the Eclipse Public License, version 1.0 (EPL), with
:: # the following special exception:
:: #
:: # LOXI Exception
:: #
:: # As a special exception to the terms of the EPL, you may distribute libraries
:: # generated by LoxiGen (LoxiGen Libraries) under the terms of your choice, provided
:: # that copyright and licensing notices generated by LoxiGen are not altered or removed
:: # from the LoxiGen Libraries and the notice provided below is (i) included in
:: # the LoxiGen Libraries, if distributed in source code form and (ii) included in any
:: # documentation for the LoxiGen Libraries, if distributed in binary form.
:: #
:: # Notice: "Copyright 2013, Big Switch Networks, Inc. This library was generated by the LoxiGen Compiler."
:: #
:: # You may not use this file except in compliance with the EPL or LOXI Exception. You may obtain
:: # a copy of the EPL at:
:: #
:: # http://www.eclipse.org/legal/epl-v10.html
:: #
:: # Unless required by applicable law or agreed to in writing, software
:: # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
:: # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
:: # EPL for the specific language governing permissions and limitations
:: # under the EPL.
::
:: include('_copyright.py')

:: include('_autogen.py')

import sys
import struct
import action
:: if version >= 4:
import meter_band # for unpack_list
:: #endif
import const
import util
import loxi.generic_util

:: if version >= 3:
import oxm
:: #endif

# HACK make this module visible as 'common' to simplify code generation
common = sys.modules[__name__]

def unpack_list_flow_stats_entry(reader):
    return loxi.generic_util.unpack_list_lv16(reader, flow_stats_entry.unpack)

def unpack_list_queue_prop(reader):
    def deserializer(reader, typ):
        if typ == const.OFPQT_MIN_RATE:
            return queue_prop_min_rate.unpack(reader)
        else:
            raise loxi.ProtocolError("unknown queue prop %d" % typ)
    return loxi.generic_util.unpack_list_tlv16(reader, deserializer)

def unpack_list_packet_queue(reader):
    def wrapper(reader):
        length, = reader.peek('!4xH')
        return packet_queue.unpack(reader.slice(length))
    return loxi.generic_util.unpack_list(reader, wrapper)

def unpack_list_hello_elem(reader):
    def deserializer(reader, typ):
        if typ == const.OFPHET_VERSIONBITMAP:
            return hello_elem_versionbitmap.unpack(reader)
        else:
            return None
    return [x for x in loxi.generic_util.unpack_list_tlv16(reader, deserializer) if x != None]

def unpack_list_bucket(reader):
    return loxi.generic_util.unpack_list_lv16(reader, bucket.unpack)

def unpack_list_group_desc_stats_entry(reader):
    return loxi.generic_util.unpack_list_lv16(reader, group_desc_stats_entry.unpack)

def unpack_list_group_stats_entry(reader):
    return loxi.generic_util.unpack_list_lv16(reader, group_stats_entry.unpack)

:: for ofclass in ofclasses:
:: include('_ofclass.py', ofclass=ofclass, superclass="object")

:: #endfor

:: if version == 1:
match = match_v1
:: elif version == 2:
match = match_v2
:: elif version == 3:
match = match_v3
:: elif version == 4:
:: # HACK
match = match_v3
:: #endif
