# 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.

"""
@file code_gen.py
Code generation functions for LOCI
"""

import sys
import of_g
import c_match
from generic_utils import *
import c_gen.c_type_maps as c_type_maps
import loxi_front_end.type_maps as type_maps
import loxi_front_end.flags as flags
import loxi_utils.loxi_utils as loxi_utils
import loxi_front_end.identifiers as identifiers

# 'property' is for queues. Could be trouble


################################################################
#
# Misc helper functions
#
################################################################

def h_file_to_define(name):
    """
    Convert a .h file name to the define used for the header
    """
    h_name = name[:-2].upper()
    h_name = "_" + h_name + "_H_"
    return h_name

def enum_name(cls):
    """
    Return the name used for an enum identifier for the given class
    @param cls The class name
    """
    return loxi_utils.enum_name(cls)

def member_returns_val(cls, m_name):
    """
    Should get accessor return a value rather than void
    @param cls The class name
    @param m_name The member name
    @return True if of_g config and the specific member allow a 
    return value.  Otherwise False
    """
    m_type = of_g.unified[cls]["union"][m_name]["m_type"]
    return (config_check("get_returns") =="value" and 
            m_type in of_g.of_scalar_types)

# TODO serialize match outside accessor?
def accessor_return_type(a_type, m_type):
    if loxi_utils.accessor_returns_error(a_type, m_type):
        return "int WARN_UNUSED_RESULT"
    else:
        return "void"

def accessor_return_success(a_type, m_type):
    if loxi_utils.accessor_returns_error(a_type, m_type):
        return "OF_ERROR_NONE"
    else:
        return ""

################################################################
#
# Per-file generators, mapped to jump table below
#
################################################################

def base_h_gen(out, name):
    """
    Generate code for base header file
    @param out The file handle to write to
    @param name The name of the file
    """
    common_top_matter(out, name)
    base_h_content(out)
    gen_object_enum(out)
    out.write("""
/****************************************************************
 *
 * Experimenter IDs
 *
 ****************************************************************/

""")
    for name, val in of_g.experimenter_name_to_id.items():
        out.write("#define OF_EXPERIMENTER_ID_%s 0x%08x\n" %
                  (name.upper(), val))

    out.write("""
/****************************************************************
 *
 * OpenFlow Match version specific and generic defines
 *
 ****************************************************************/
""")
    c_match.gen_v4_match_compat(out)
    c_match.gen_match_macros(out)
    c_match.gen_oxm_defines(out)
    out.write("\n#endif /* Base header file */\n")

def identifiers_gen(out, filename):
    """
    Generate the macros for LOCI identifiers
    @param out The file handle to write to
    @param filename The name of the file
    """
    common_top_matter(out, filename)
    out.write("""
/**
 * For each identifier from an OpenFlow header file, a Loxi version
 * of the identifier is generated.  For example, ofp_port_flood becomes
 * OF_PORT_DEST_FLOOD.  Loxi provides the following macros related to 
 * OpenFlow identifiers (using OF_IDENT_ as an example below):
 *     OF_IDENT_BY_VERSION(version) Get the value for the specific version
 *     OF_IDENT_SUPPORTED(version) Boolean: Is OF_IDENT defined for version
 *     OF_IDENT The common value across all versions if defined
 *     OF_IDENT_GENERIC A unique value across all OF identifiers
 *
 * For identifiers marked as flags, the following are also defined
 *     OF_IDENT_SET(flags, version)
 *     OF_IDENT_CLEAR(flags, version)
 *     OF_IDENT_TEST(flags, version)
 *
 * Notes:
 *
 *     OF_IDENT_BY_VERSION(version) returns an undefined value
 * if the passed version does not define OF_IDENT.  It does not generate an
 * error, nor record anything to the log file.  If the value is the same
 * across all defined versions, the version is ignored.
 *
 *     OF_IDENT is only defined if the value is the same across all
 * target LOXI versions FOR WHICH IT IS DEFINED.  No error checking is
 * done.  This allows code to be written without requiring the version
 * to be known or referenced when it doesn't matter.  It does mean
 * that when porting to a new version of OpenFlow, compile errors may
 * occur.  However, this is an indication that the existing code must
 * be updated to account for a change in the semantics with the newly
 * supported OpenFlow version.
 *
 * @fixme Currently we do not handle multi-bit flags or field values; for
 * example, OF_TABLE_CONFIG_TABLE_MISS_CONTROLLER is the meaning for
 * a zero value in the bits indicated by OF_TABLE_CONFIG_TABLE_MISS_MASK.
 *
 * @fixme Need to decide (or make a code gen option) on the requirement
 * for defining OF_IDENT:  Is it that all target versions define it and
 * the agree?  Or only that the versions which define it agree?
 */
""")

    # Build value-by-version parameters and c_code
    if len(of_g.target_version_list) > 1: # Supporting more than one version
        vbv_params = []
        vbv_code = ""
        first = True
        for version in of_g.target_version_list:
            vbv_params.append("value_%s" % of_g.short_version_names[version])
            if not first:
                vbv_code += "\\\n     "
            else:
                first = False
            last_value = "value_%s" % of_g.short_version_names[version]
            vbv_code += "((version) == %s) ? (%s) : " % \
                (of_g.of_version_wire2name[version], last_value)
        # @todo Using last value, can optimize out last ?
        vbv_code += "(%s)" % last_value

    out.write("""
/**
 * @brief True for the special case of all versions supported
 */
#define OF_IDENT_IN_ALL_VERSIONS 1 /* Indicates identifier in all versions */

/**
 * @brief General macro to map version to value where values given as params
 *
 * If unknown version is passed, use the latest version's value
 */
#define OF_VALUE_BY_VERSION(version, %s) \\
    (%s)

/**
 * @brief Generic set a flag
 */
#define OF_FLAG_SET(flags, mask) (flags) = (flags) | (mask)

/**
 * @brief Generic test if a flag is set
 */
#define OF_FLAG_CLEAR(flags, mask) (flags) = (flags) & ~(mask)

/**
 * @brief Generic test if a flag is set
 */
#define OF_FLAG_TEST(flags, mask) ((flags) & (mask) ? 1 : 0)

/**
 * @brief Set a flag where the value is an enum indication of bit shift
 */
#define OF_FLAG_ENUM_SET(flags, e_val) OF_FLAG_SET(flags, 1 << (e_val))

/**
 * @brief Clear a flag where the value is an enum indication of bit shift
 */
#define OF_FLAG_ENUM_CLEAR(flags, e_val) OF_FLAG_CLEAR(flags, 1 << (e_val))

/**
 * @brief Test a flag where the value is an enum indication of bit shift
 */
#define OF_FLAG_ENUM_TEST(flags, e_val) OF_FLAG_TEST(flags, 1 << (e_val))
""" % (", ".join(vbv_params), vbv_code))

    # For each group of identifiers, bunch ident defns
    count = 1
    keys = of_g.identifiers_by_group.keys()
    keys.sort()
    for group in keys:
        idents = of_g.identifiers_by_group[group]
        idents.sort()
        out.write("""
/****************************************************************
 * Identifiers from %s 
 *****************************************************************/
""" % group)
        for ident in idents:
            info = of_g.identifiers[ident]

            keys = info["values_by_version"].keys()
            keys.sort()

            out.write("""
/*
 * Defines for %(ident)s
 * Original name %(ofp_name)s
 */
""" % dict(ident=ident, ofp_name=info["ofp_name"]))

            # Generate supported versions macro
            if len(keys) == len(of_g.target_version_list): # Defined for all
                out.write("""\
#define %(ident)s_SUPPORTED(version) OF_IDENT_IN_ALL_VERSIONS
""" % dict(ident=ident))
            else: # Undefined for some version
                sup_list = []
                for version in keys:
                    sup_list.append("((version) == %s)" %
                                    of_g.of_version_wire2name[version])
                out.write("""\
#define %(ident)s_SUPPORTED(version)      \\
    (%(sup_str)s)
""" % dict(ident=ident, sup_str=" || \\\n     ".join(sup_list)))

            # Generate value macro
            if identifiers.defined_versions_agree(of_g.identifiers,
                                                  of_g.target_version_list,
                                                  ident):
                out.write("""\
#define %(ident)s (%(value)s)
#define %(ident)s_BY_VERSION(version) (%(value)s)
""" % dict(ident=ident,value=info["common_value"]))
            else: # Values differ between versions
                # Generate version check and value by version
                val_list = []
                # Order of params matters
                for version in of_g.target_version_list:
                    if version in info["values_by_version"]:
                        value = info["values_by_version"][version]
                    else:
                        value = identifiers.UNDEFINED_IDENT_VALUE
                    val_list.append("%s" % value)
                out.write("""\
#define %(ident)s_BY_VERSION(version)     \\
    OF_VALUE_BY_VERSION(version, %(val_str)s)
""" % dict(ident=ident, val_str=", ".join(val_list)))
            if flags.ident_is_flag(ident):
                log("Treating %s as a flag" % ident)
                out.write("""
#define %(ident)s_SET(flags, version)     \\
    OF_FLAG_SET(flags, %(ident)s_BY_VERSION(version))
#define %(ident)s_TEST(flags, version)    \\
    OF_FLAG_TEST(flags, %(ident)s_BY_VERSION(version))
#define %(ident)s_CLEAR(flags, version)   \\
    OF_FLAG_CLEAR(flags, %(ident)s_BY_VERSION(version))
""" % dict(ident=ident))

            out.write("#define %(ident)s_GENERIC %(count)d\n"
                      % dict(ident=ident, count=count))
            count += 1 # This count should probably be promoted higher

    log("Generated %d identifiers" % (count - 1))
    out.write("\n#endif /* Loci identifiers header file */\n")

def base_h_external(out, filename):
    """
    Copy contents of external file to base header

    The contents of the filename are copied literally into the
    out file handler.  This allows openflow common defines to
    be entered into the LoxiGen code base.  The content of this
    code must depend only on standard C headers.
    """
    infile = open(filename, "r")
    contents = infile.read()
    out.write(contents)
    infile.close()

def match_h_gen(out, name):
    """
    Generate code for
    @param out The file handle to write to
    @param name The name of the file
    """
    c_match.match_h_top_matter(out, name)
    c_match.gen_incompat_members(out)
    c_match.gen_match_struct(out)
    c_match.gen_match_comp(out)
#    c_match.gen_match_accessors(out)
    out.write("\n#endif /* Match header file */\n")

def top_h_gen(out, name):
    """
    Generate code for
    @param out The file handle to write to
    @param name The name of the file
    """
    external_h_top_matter(out, name)
    out.write("""

typedef enum loci_log_level {
    LOCI_LOG_LEVEL_TRACE,
    LOCI_LOG_LEVEL_VERBOSE,
    LOCI_LOG_LEVEL_INFO,
    LOCI_LOG_LEVEL_WARN,
    LOCI_LOG_LEVEL_ERROR,
    LOCI_LOG_LEVEL_MSG
} loci_log_level_t;

/**
 * @brief Output a log message.
 * @param level The log level.
 * @param fname The function name.
 * @param file The file name.
 * @param line The line number.
 * @param format The message format string.
 */
typedef int (*loci_logger_f)(loci_log_level_t level,
                             const char *fname, const char *file, int line,
                             const char *format, ...);

/*
 * This variable should be set by the user of the library to redirect logs to
 * their log infrastructure. The default drops all logs.
 */
extern loci_logger_f loci_logger;

/**
 * Map a generic object to the underlying wire buffer
 *
 * Treat as private
 */
#define OF_OBJECT_TO_MESSAGE(obj) \\
    ((of_message_t)(WBUF_BUF((obj)->wire_object.wbuf)))

/**
 * Macro for the fixed length part of an object
 *
 * @param obj The object whose extended length is being calculated
 * @returns length in bytes of non-variable part of the object
 */
#define OF_OBJECT_FIXED_LENGTH(obj) \\
    (of_object_fixed_len[(obj)->version][(obj)->object_id])

/**
 * Return the length of the object beyond its fixed length
 *
 * @param obj The object whose extended length is being calculated
 * @returns length in bytes of non-variable part of the object
 *
 * Most variable length fields are alone at the end of a structure.
 * Their length is a simple calculation, just the total length of
 * the parent minus the length of the non-variable part of the
 * parent's class type.
 */

#define OF_OBJECT_VARIABLE_LENGTH(obj) \\
    ((obj)->length - OF_OBJECT_FIXED_LENGTH(obj))

/* FIXME: Where do these go? */
/* Low level maps btwn wire version + type and object ids */
extern int of_message_is_stats_request(int type, int w_ver);
extern int of_message_is_stats_reply(int type, int w_ver);
extern int of_message_stats_reply_to_object_id(int stats_type, int w_ver);
extern int of_message_stats_request_to_object_id(int stats_type, int w_ver);
extern int of_message_type_to_object_id(int type, int w_ver);

extern int of_wire_buffer_of_match_get(of_object_t *obj, int offset,
                                    of_match_t *match);
extern int of_wire_buffer_of_match_set(of_object_t *obj, int offset,
                                    of_match_t *match, int cur_len);
extern void of_extension_object_id_set(of_object_t *obj, of_object_id_t id);
""")

    # gen_base_types(out)

    gen_struct_typedefs(out)
    gen_acc_pointer_typedefs(out)
    gen_new_function_declarations(out)
    if config_check("gen_unified_fns"):
        gen_accessor_declarations(out)

    gen_common_struct_definitions(out)
    gen_flow_add_setup_function_declarations(out)
    if config_check("gen_fn_ptrs"): # Otherwise, all classes are from generic cls
        gen_struct_definitions(out)
    gen_generic_union(out)
    gen_generics(out)
    gen_top_static_functions(out)
    out.write("""
/****************************************************************
 *
 * Declarations of maps between on-the-wire type values and LOCI identifiers
 *
 ****************************************************************/
""")
    c_type_maps.gen_type_maps_header(out)
    c_type_maps.gen_type_data_header(out)
    c_match.gen_declarations(out)
    # @fixme Move debug stuff to own fn
    out.write("""
/**
 * Macro to check consistency of length for top level objects
 *
 * If the object has no parent then its length should match the
 * underlying wire buffer's current bytes.
 */
#define OF_LENGTH_CHECK_ASSERT(obj) \\
    ASSERT(((obj)->parent != NULL) || \\
     ((obj)->wire_object.wbuf == NULL) || \\
     (WBUF_CURRENT_BYTES((obj)->wire_object.wbuf) == (obj)->length))

#define OF_DEBUG_DUMP
#if defined(OF_DEBUG_DUMP)
extern void dump_match(of_match_t *match);
#endif /* OF_DEBUG_DUMP */
""")

    out.write("\n#endif /* Top header file */\n")

def match_c_gen(out, name):
    """
    Generate code for
    @param out The file handle to write to
    @param name The name of the file
    """
    c_match.match_c_top_matter(out, name)
    c_match.gen_match_conversions(out)
    c_match.gen_serialize(out)
    c_match.gen_deserialize(out)

def gen_len_offset_macros(out):
    """
    Special case length and offset calculations put directly into
    loci.c as they are private.
    """

    out.write("""
/****************************************************************
 * Special case macros for calculating variable lengths and offsets
 ****************************************************************/

/**
 * Get a u16 directly from an offset in an object's wire buffer
 * @param obj An of_object_t object
 * @param offset Base offset of the uint16 relative to the object
 *
 */

static inline int
of_object_u16_get(of_object_t *obj, int offset) {
    uint16_t val16;

    of_wire_buffer_u16_get(obj->wire_object.wbuf,
        obj->wire_object.obj_offset + offset, &val16);

    return (int)val16;
}

/**
 * Set a u16 directly at an offset in an object's wire buffer
 * @param obj An of_object_t object
 * @param offset Base offset of the uint16 relative to the object
 * @param val The value to store
 *
 */

static inline void
of_object_u16_set(of_object_t *obj, int offset, int value) {
    uint16_t val16;

    val16 = (uint16_t)value;
    of_wire_buffer_u16_set(obj->wire_object.wbuf,
        obj->wire_object.obj_offset + offset, val16);
}

/**
 * Get length of an object with a TLV header with uint16_t
 * @param obj An object with a match member
 * @param offset The wire offset of the start of the object
 *
 * The length field follows the type field.
 */

#define _TLV16_LEN(obj, offset) \\
    (of_object_u16_get((of_object_t *)(obj), (offset) + 2))

/**
 * Get length of an object that is the "rest" of the object
 * @param obj An object with a match member
 * @param offset The wire offset of the start of the object
 *
 */

#define _END_LEN(obj, offset) ((obj)->length - (offset))

/**
 * Get length of the action list object in a packet_out object
 * @param obj An object of type of_packet_out
 *
 * The length field is just before the end of the fixed length
 * part of the object in all versions.
 */

#define _PACKET_OUT_ACTION_LEN(obj) \\
    (of_object_u16_get((of_object_t *)(obj), \\
     of_object_fixed_len[(obj)->version][OF_PACKET_OUT] - 2))

/**
 * Set length of the action list object in a packet_out object
 * @param obj An object of type of_packet_out
 *
 * The length field is just before the end of the fixed length
 * part of the object in all versions.
 */

#define _PACKET_OUT_ACTION_LEN_SET(obj, len) \\
    (of_object_u16_set((of_object_t *)(obj), \\
     of_object_fixed_len[(obj)->version][OF_PACKET_OUT] - 2, len))

/*
 * Match structs in 1.2 come at the end of the fixed length part
 * of structures.  They add 8 bytes to the minimal length of the
 * message, but are also variable length.  This means that the 
 * type/length offsets are 8 bytes back from the end of the fixed 
 * length part of the object.  The right way to handle this is to 
 * expose the offset of the match member more explicitly.  For now, 
 * we make the calculation as described here.
 */

/* 1.2 min length of match is 8 bytes */
#define _MATCH_MIN_LENGTH_V3 8

/**
 * The offset of a 1.2 match object relative to fixed length of obj
 */
#define _MATCH_OFFSET_V3(fixed_obj_len) \\
    ((fixed_obj_len) - _MATCH_MIN_LENGTH_V3)

/**
 * The "extra" length beyond the minimal 8 bytes of a match struct
 * in an object
 */
#define _MATCH_EXTRA_LENGTH_V3(obj, fixed_obj_len) \\
    (OF_MATCH_BYTES(_TLV16_LEN(obj, _MATCH_OFFSET_V3(fixed_obj_len))) - \\
     _MATCH_MIN_LENGTH_V3)

/**
 * The offset of an object following a match object for 1.2
 */
#define _OFFSET_FOLLOWING_MATCH_V3(obj, fixed_obj_len) \\
    ((fixed_obj_len) + _MATCH_EXTRA_LENGTH_V3(obj, fixed_obj_len))

/**
 * Get length of a match object from its wire representation
 * @param obj An object with a match member
 * @param match_offset The wire offset of the match object.
 *
 * See above; for 1.2, 
 * The match length is raw bytes but the actual space it takes
 * up is padded for alignment to 64-bits
 */
#define _WIRE_MATCH_LEN(obj, match_offset) \\
    (((obj)->version == OF_VERSION_1_0) ? %(match1)d : \\
     (((obj)->version == OF_VERSION_1_1) ? %(match2)d : \\
      _TLV16_LEN(obj, match_offset)))

#define _WIRE_LEN_MIN 4

/*
 * Wrapper function for match len.  There are cases where the wire buffer
 * has not been set with the proper minimum length.  In this case, the
 * wire match len is interpretted as its minimum length, 4 bytes.
 */

static inline int
wire_match_len(of_object_t *obj, int match_offset) {
    int len;

    len = _WIRE_MATCH_LEN(obj, match_offset);

    return (len == 0) ? _WIRE_LEN_MIN : len;
}

#define _WIRE_MATCH_PADDED_LEN(obj, match_offset) \\
    OF_MATCH_BYTES(wire_match_len((of_object_t *)(obj), (match_offset)))

/**
 * Macro to calculate variable offset of instructions member in flow mod
 * @param obj An object of some type of flow modify/add/delete
 *
 * Get length of preceding match object and add to fixed length
 * Applies only to version 1.2
 */

#define _FLOW_MOD_INSTRUCTIONS_OFFSET(obj) \\
    _OFFSET_FOLLOWING_MATCH_V3(obj, %(flow_mod)d)

/* The different flavors of flow mod all use the above */
#define _FLOW_ADD_INSTRUCTIONS_OFFSET(obj) \\
    _FLOW_MOD_INSTRUCTIONS_OFFSET(obj)
#define _FLOW_MODIFY_INSTRUCTIONS_OFFSET(obj) \\
    _FLOW_MOD_INSTRUCTIONS_OFFSET(obj)
#define _FLOW_MODIFY_STRICT_INSTRUCTIONS_OFFSET(obj) \\
    _FLOW_MOD_INSTRUCTIONS_OFFSET(obj)
#define _FLOW_DELETE_INSTRUCTIONS_OFFSET(obj) \\
    _FLOW_MOD_INSTRUCTIONS_OFFSET(obj)
#define _FLOW_DELETE_STRICT_INSTRUCTIONS_OFFSET(obj) \\
    _FLOW_MOD_INSTRUCTIONS_OFFSET(obj)

/**
 * Macro to calculate variable offset of instructions member in flow stats
 * @param obj An object of type of_flow_mod_t
 *
 * Get length of preceding match object and add to fixed length
 * Applies only to version 1.2 and 1.3
 */

#define _FLOW_STATS_ENTRY_INSTRUCTIONS_OFFSET(obj) \\
    _OFFSET_FOLLOWING_MATCH_V3(obj, %(flow_stats)d)

/**
 * Macro to calculate variable offset of data (packet) member in packet_in
 * @param obj An object of type of_packet_in_t
 *
 * Get length of preceding match object and add to fixed length
 * Applies only to version 1.2 and 1.3
 */

#define _PACKET_IN_DATA_OFFSET(obj) \\
    _OFFSET_FOLLOWING_MATCH_V3((obj), (obj)->version == OF_VERSION_1_2 ? \
%(packet_in)d : %(packet_in_1_3)d)

/**
 * Macro to calculate variable offset of data (packet) member in packet_out
 * @param obj An object of type of_packet_out_t
 *
 * Find the length in the actions_len variable and add to the fixed len
 * Applies only to version 1.2 and 1.3
 */

#define _PACKET_OUT_DATA_OFFSET(obj) (_PACKET_OUT_ACTION_LEN(obj) + \\
     of_object_fixed_len[(obj)->version][OF_PACKET_OUT])

/**
 * Macro to map port numbers that changed across versions
 * @param port The port_no_t variable holding the value
 * @param ver The OpenFlow version from which the value was extracted
 */
#define OF_PORT_NO_VALUE_CHECK(port, ver) \\
    if (((ver) == OF_VERSION_1_0) && ((port) > 0xff00)) (port) += 0xffff0000

""" % dict(flow_mod=of_g.base_length[("of_flow_modify",of_g.VERSION_1_2)],
           packet_in=of_g.base_length[("of_packet_in",of_g.VERSION_1_2)],
           packet_in_1_3=of_g.base_length[("of_packet_in",of_g.VERSION_1_3)],
           flow_stats=of_g.base_length[("of_flow_stats_entry",
                                        of_g.VERSION_1_2)],
           match1=of_g.base_length[("of_match_v1",of_g.VERSION_1_0)],
           match2=of_g.base_length[("of_match_v2",of_g.VERSION_1_1)]))

def gen_obj_id_macros(out):
    """
    Flow modify (add, delete) messages (and maybe others) use ID checks allowing
    inheritance to use common accessor functions.
    """
    out.write("""
/**
 * Macro to detect if an object ID falls in the "flow mod" family of objects
 * This includes add, modify, modify_strict, delete and delete_strict
 */
#define IS_FLOW_MOD_SUBTYPE(object_id)                 \\
    (((object_id) == OF_FLOW_MODIFY) ||                \\
     ((object_id) == OF_FLOW_MODIFY_STRICT) ||         \\
     ((object_id) == OF_FLOW_DELETE) ||                \\
     ((object_id) == OF_FLOW_DELETE_STRICT) ||         \\
     ((object_id) == OF_FLOW_ADD))
""")


def top_c_gen(out, name):
    """
    Generate code for
    @param out The file handle to write to
    @param name The name of the file
    """
    common_top_matter(out, name)
    # Generic C code that needs to go into loci.c can go here.
    out.write("""
/****************************************************************
 *
 * This file is divided into the following sections.
 *
 * Instantiate strings such as object names
 * Special case macros for low level object access
 * Per-class, per-member accessor definitions
 * Per-class new/init function definitions
 * Per-class new/init pointer instantiations
 * Instantiate "set map" for pointer set fns
 *
 ****************************************************************/

#ifdef __GNUC__
#include <features.h>

#if __GNUC_PREREQ(4,4)
#pragma GCC optimize ("s")
#endif

#if __GNUC_PREREQ(4,6)
#pragma GCC diagnostic ignored "-Wunused-but-set-variable"
#endif

#endif

#include <loci/loci.h>
#include <loci/of_object.h>
#include "loci_log.h"

""")
    gen_object_enum_str(out)
    gen_len_offset_macros(out)
    gen_obj_id_macros(out)
    if config_check("gen_unified_fns"):
        gen_accessor_definitions(out)
    gen_new_function_definitions(out)
    gen_init_map(out)
    out.write("\n/* This code should be broken out to a different file */\n")
    gen_setup_from_add_fns(out)

def type_data_c_gen(out, name):
    common_top_matter(out, name)
    c_type_maps.gen_type_maps(out)
    c_type_maps.gen_length_array(out)

################################################################
# Top Matter
################################################################

def common_top_matter(out, name):
    loxi_utils.gen_c_copy_license(out)
    out.write("""\
/****************************************************************
 * File: %s
 *
 * DO NOT EDIT
 *
 * This file is automatically generated
 *
 ****************************************************************/

""" % name)

    if name[-2:] == ".h":
        out.write("""
#if !defined(%(h)s)
#define %(h)s

""" % dict(h=h_file_to_define(name)))

def base_h_content(out):
    """
    Generate base header file content

    @param out The output file object
    """

    # @fixme Supported version should be generated based on input to LoxiGen

    out.write("""
/*
 * Base OpenFlow definitions.  These depend only on standard C headers
 */
#include <string.h>
#include <stdint.h>

/* g++ requires this to pick up PRI, etc.
 * See  http://gcc.gnu.org/ml/gcc-help/2006-10/msg00223.html
 */
#if !defined(__STDC_FORMAT_MACROS)
#define __STDC_FORMAT_MACROS
#endif
#include <inttypes.h>

#include <stdlib.h>
#include <assert.h>
#include <loci/loci_idents.h>

/**
 * Macro to enable debugging for LOCI.
 *
 * This enables debug output to stdout.
 */
#define OF_DEBUG_ENABLE

#if defined(OF_DEBUG_ENABLE)
#include <stdio.h> /* Currently for debugging */
#define FIXME(str) do {                 \\
        fprintf(stderr, "%s\\n", str);  \\
        exit(1);                        \\
    } while (0)
#define debug printf
#else
#define FIXME(str)
#define debug(str, ...)
#endif /* OF_DEBUG_ENABLE */

/**
 * The type of a function used by the LOCI dump/show functions to
 * output text. Essentially the same signature as fprintf. May
 * be called many times per invocation of e.g. of_object_show().
 */
typedef int (*loci_writer_f)(void *cookie, const char *fmt, ...);

/**
 * Check if a version is supported
 */
#define OF_VERSION_OKAY(v) ((v) >= OF_VERSION_1_0 && (v) <= OF_VERSION_1_3)

""")
    gen_version_enum(out)
    out.write("\n")

    # for c_name in of_g.ofp_constants:
    #     val = str(of_g.ofp_constants[c_name])
    #     out.write("#define %s %s\n" % (c_name, val))
    # out.write("\n")

    out.write("""
typedef enum of_error_codes_e {
    OF_ERROR_NONE        = 0,
    OF_ERROR_RESOURCE    = -1,    /* Could not allocate space */
    OF_ERROR_PARAM       = -2,    /* Bad parameter */
    OF_ERROR_VERSION     = -3,    /* Version not supported */
    OF_ERROR_RANGE       = -4,    /* End of list indication */
    OF_ERROR_COMPAT      = -5,    /* Incompatible assignment */
    OF_ERROR_PARSE       = -6,    /* Error in parsing data */
    OF_ERROR_INIT        = -7,    /* Uninitialized data */
    OF_ERROR_UNKNOWN     = -8     /* Unknown error */
} of_error_codes_t;

#define OF_ERROR_STRINGS "none", \\
    "resource", \\
    "parameter", \\
    "version", \\
    "range", \\
    "incompatible", \\
    "parse", \\
    "init", \\
    "unknown"

extern const char *const of_error_strings[];

#ifndef NDEBUG
/* #define ASSERT(val) assert(val) */
#define FORCE_FAULT *(volatile int *)0 = 1
#define ASSERT(val) if (!(val)) \\
    fprintf(stderr, "\\nASSERT %s. %s:%d\\n", #val, __FILE__, __LINE__), \\
    FORCE_FAULT
#else
#define ASSERT(val)
#endif

/*
 * Some LOCI object accessors can fail, and it's easy to forget to check.
 * On certain compilers we can trigger a warning if the error code
 * is ignored.
 */
#ifndef DISABLE_WARN_UNUSED_RESULT
#ifdef __GNUC__
#define WARN_UNUSED_RESULT __attribute__ ((warn_unused_result))
#else
#define WARN_UNUSED_RESULT
#endif
#else
#define WARN_UNUSED_RESULT
#endif

typedef union of_generic_u of_generic_t;
typedef struct of_object_s of_object_t;

/* Define ipv4 address as uint32 */
typedef uint32_t of_ipv4_t;

/* Table ID is the OF standard uint8 */
typedef uint8_t of_table_id_t;

#define OF_MAC_ADDR_BYTES 6
typedef struct of_mac_addr_s {
   uint8_t addr[OF_MAC_ADDR_BYTES];
} of_mac_addr_t;

#define OF_IPV6_BYTES 16
typedef struct of_ipv6_s {
   uint8_t addr[OF_IPV6_BYTES];
} of_ipv6_t;

extern const of_mac_addr_t of_mac_addr_all_ones;
extern const of_mac_addr_t of_mac_addr_all_zeros;

extern const of_ipv6_t of_ipv6_all_ones;
extern const of_ipv6_t of_ipv6_all_zeros;

/**
 * Generic zero and all-ones values of size 16 bytes.
 *
 * IPv6 is longest data type we worry about for comparisons
 */
#define of_all_zero_value of_ipv6_all_zeros
#define of_all_ones_value of_ipv6_all_ones

/**
 * Non-zero/all ones check for arbitrary type of size <= 16 bytes
 */
#define OF_VARIABLE_IS_NON_ZERO(_ptr) \\
    (MEMCMP(&of_all_zero_value, (_ptr), sizeof(*(_ptr))))
#define OF_VARIABLE_IS_ALL_ONES(_ptr) \\
    (!MEMCMP(&of_all_ones_value, (_ptr), sizeof(*(_ptr))))

/* The octets object is a struct holding pointer and length */
typedef struct of_octets_s {
    uint8_t *data;
    int bytes;
} of_octets_t;

/* Macro to convert an octet object to a pointer; currently trivial */
#define OF_OCTETS_POINTER_GET(octet_ptr) ((octet_ptr)->data)
#define OF_OCTETS_POINTER_SET(octet_ptr, ptr) (octet_ptr)->data = (ptr)
#define OF_OCTETS_BYTES_GET(octet_ptr) ((octet_ptr)->bytes)
#define OF_OCTETS_BYTES_SET(octet_ptr, bytes) (octet_ptr)->bytes = (bytes)

/* Currently these are categorized as scalars */
typedef char of_port_name_t[OF_MAX_PORT_NAME_LEN];
typedef char of_table_name_t[OF_MAX_TABLE_NAME_LEN];
typedef char of_desc_str_t[OF_DESC_STR_LEN];
typedef char of_serial_num_t[OF_SERIAL_NUM_LEN];

/* These are types which change across versions.  */
typedef uint32_t of_port_no_t;
typedef uint16_t of_fm_cmd_t;
typedef uint64_t of_wc_bmap_t;
typedef uint64_t of_match_bmap_t;

#define MEMMOVE(dest, src, bytes) memmove(dest, src, bytes)
#define MEMSET(dest, val, bytes) memset(dest, val, bytes)
#define MEMCPY(dest, src, bytes) memcpy(dest, src, bytes)
#define MEMCMP(a, b, bytes) memcmp(a, b, bytes)
#define MALLOC(bytes) malloc(bytes)
#define FREE(ptr) free(ptr)

/** Try an operation and return on failure. */
#define OF_TRY(op) do {                                                      \\
        int _rv;                                                             \\
        if ((_rv = (op)) < 0) {                                              \\
            LOCI_LOG_ERROR("ERROR %d at %s:%d\\n", _rv, __FILE__, __LINE__); \\
            return _rv;                                                      \\
        }                                                                    \\
    } while (0)

/* The extent of an OF match object is determined by its length field, but
 * aligned to 8 bytes
 */

#define OF_MATCH_BYTES(length) (((length) + 7) & 0xfff8)

#if __BYTE_ORDER == __BIG_ENDIAN
#define U16_NTOH(val) (val)
#define U32_NTOH(val) (val)
#define U64_NTOH(val) (val)
#define IPV6_NTOH(dst, src) /* NOTE different syntax; currently no-op */
#define U16_HTON(val) (val)
#define U32_HTON(val) (val)
#define U64_HTON(val) (val)
#define IPV6_HTON(dst, src) /* NOTE different syntax; currently no-op */
#else /* Little Endian */
#define U16_NTOH(val) (((val) >> 8) | ((val) << 8))
#define U32_NTOH(val) ((((val) & 0xff000000) >> 24) |                   \\
                       (((val) & 0x00ff0000) >>  8) |                   \\
                       (((val) & 0x0000ff00) <<  8) |                   \\
                       (((val) & 0x000000ff) << 24))
#define U64_NTOH(val) ((((val) & 0xff00000000000000LL) >> 56) |         \\
                       (((val) & 0x00ff000000000000LL) >> 40) |         \\
                       (((val) & 0x0000ff0000000000LL) >> 24) |         \\
                       (((val) & 0x000000ff00000000LL) >>  8) |         \\
                       (((val) & 0x00000000ff000000LL) <<  8) |         \\
                       (((val) & 0x0000000000ff0000LL) << 24) |         \\
                       (((val) & 0x000000000000ff00LL) << 40) |         \\
                       (((val) & 0x00000000000000ffLL) << 56))
#define IPV6_NTOH(dst, src) /* NOTE different syntax; currently no-op */
#define U16_HTON(val) U16_NTOH(val)
#define U32_HTON(val) U32_NTOH(val)
#define U64_HTON(val) U64_NTOH(val)
#define IPV6_HTON(dst, src) /* NOTE different syntax; currently no-op */
#endif

/****************************************************************
 *
 * The following are internal definitions used by the automatically
 * generated code.  Users should not reference these definitions
 * as they may change between versions of this code
 *
 ****************************************************************/

#define OF_MESSAGE_IN_MATCH_POINTER(obj)                            \\
    (WIRE_BUF_POINTER(&((obj)->wire_buffer), OF_MESSAGE_IN_MATCH_OFFSET))
#define OF_MESSAGE_IN_MATCH_LEN(ptr) BUF_U16_GET(&ptr[2])
#define OF_MESSAGE_IN_DATA_OFFSET(obj) \\
    (FIXED_LEN + OF_MESSAGE_IN_MATCH_LEN(OF_MESSAGE_IN_MATCH_POINTER(obj)) + 2)

#define OF_MESSAGE_OUT_DATA_OFFSET(obj) \\
    (FIXED_LEN + of_message_out_actions_len_get(obj))

""")

def external_h_top_matter(out, name):
    """
    Generate top matter for external header file

    @param name The name of the output file
    @param out The output file object
    """
    common_top_matter(out, name)
    out.write("""
#include <loci/loci_base.h>
#include <loci/of_message.h>
#include <loci/of_match.h>
#include <loci/of_object.h>
#include <loci/of_wire_buf.h>

/****************************************************************
 *
 * This file is divided into the following sections.
 *
 * A few object specific macros
 * Class typedefs (no struct definitions)
 * Per-data type accessor function typedefs
 * Per-class new/delete function typedefs
 * Per-class static delete functions
 * Per-class, per-member accessor declarations
 * Per-class structure definitions
 * Generic union (inheritance) definitions
 * Pointer set function declarations
 * Some special case macros
 *
 ****************************************************************/
""")

def gen_top_static_functions(out):
    out.write("""

#define _MAX_PARENT_ITERATIONS 4
/**
 * Iteratively update parent lengths thru hierarchy
 * @param obj The object whose length is being updated
 * @param delta The difference between the current and new lengths
 *
 * Note that this includes updating the object itself.  It will
 * iterate thru parents.
 *
 * Assumes delta > 0.
 */
static inline void
of_object_parent_length_update(of_object_t *obj, int delta)
{
#ifndef NDEBUG
    int count = 0;
    of_wire_buffer_t *wbuf;  /* For debug asserts only */
#endif

    while (obj != NULL) {
        ASSERT(count++ < _MAX_PARENT_ITERATIONS);
        obj->length += delta;
        if (obj->wire_length_set != NULL) {
            obj->wire_length_set(obj, obj->length);
        }
#ifndef NDEBUG
        wbuf = obj->wire_object.wbuf;
#endif

        /* Asserts for wire length checking */
        ASSERT(obj->length + obj->wire_object.obj_offset <=
               WBUF_CURRENT_BYTES(wbuf));
        if (obj->parent == NULL) {
            ASSERT(obj->length + obj->wire_object.obj_offset ==
                   WBUF_CURRENT_BYTES(wbuf));
        }

        obj = obj->parent;
    }
}
""")

################################################################
#
################################################################

def gen_version_enum(out):
    """
    Generate the enumerated type for versions in LoxiGen
    @param out The file object to which to write the decs

    This just uses the wire versions for now
    """
    out.write("""
/**
 * Enumeration of OpenFlow versions
 *
 * The wire protocol numbers are currently used for values of the corresponding
 * version identifiers.
 */
typedef enum of_version_e {
    OF_VERSION_UNKNOWN = 0,
""")

    is_first = True
    max = 0
    for v in of_g.wire_ver_map:
        if is_first:
            is_first = False
        else:
            out.write(",\n")
        if v > max:
            max = v
        out.write("    %s = %d" % (of_g.wire_ver_map[v], v))

    out.write("""
} of_version_t;

/**
 * @brief Use this when declaring arrays indexed by wire version
 */
#define OF_VERSION_ARRAY_MAX %d
""" % (max + 1))
    
def gen_object_enum(out):
    """
    Generate the enumerated type for object identification in LoxiGen
    @param out The file object to which to write the decs
    """
    out.write("""

/**
 * Enumeration of OpenFlow objects
 *
 * We enumerate the OpenFlow objects used internally.  Note that some
 * message types are determined both by an outer type (message type like
 * stats_request) and an inner type (port stats).  These are different
 * messages in ofC.
 *
 * These values are for internal use only.  They will change with
 * different versions of ofC.
 */

typedef enum of_object_id_e {
    /* Root object type */
    OF_OBJECT_INVALID = -1, /* "invalid" return value for mappings */
    OF_OBJECT = 0, /* Generic, untyped object */

    /* OpenFlow message objects */
""")
    last = 0
    msg_count = 0
    for cls in of_g.ordered_messages:
        out.write("    %s = %d,\n" % (enum_name(cls),
                                   of_g.unified[cls]["object_id"]))
        msg_count = of_g.unified[cls]["object_id"] + 1

    out.write("\n    /* Non-message objects */\n")
    for cls in of_g.ordered_non_messages:
        out.write("    %s = %d,\n" % (enum_name(cls),
                                   of_g.unified[cls]["object_id"]))
        last = of_g.unified[cls]["object_id"]
    out.write("\n    /* List objects */\n")
    for cls in of_g.ordered_list_objects:
        out.write("    %s = %d,\n" % (enum_name(cls),
                                   of_g.unified[cls]["object_id"]))
        last = of_g.unified[cls]["object_id"]

    out.write("\n    /* Generic stats request/reply types; pseudo objects */\n")
    for cls in of_g.ordered_pseudo_objects:
        out.write("    %s = %d,\n" % (enum_name(cls),
                                   of_g.unified[cls]["object_id"]))
        last = of_g.unified[cls]["object_id"]

    out.write("""
    OF_OBJECT_COUNT = %d
} of_object_id_t;

extern const char *const of_object_id_str[];

#define OF_MESSAGE_OBJECT_COUNT %d
""" % ((last + 1), msg_count))

    # Generate object type range checking for inheritance classes

    # @fixme These should be determined algorithmicly
    out.write("""
/*
 * Macros to check if an object ID is within an inheritance class range
 */
""")
    # Alphabetical order for 'last'
    last_ids = dict(of_action="OF_ACTION_STRIP_VLAN",
                    of_oxm="OF_OXM_VLAN_VID_MASKED",
                    of_instruction="OF_INSTRUCTION_WRITE_METADATA",
                    of_queue_prop="OF_QUEUE_PROP_MIN_RATE",
                    of_table_feature_prop="OF_TABLE_FEATURE_PROP_WRITE_SETFIELD_MISS",
                    # @FIXME add meter_band ?
                    )
    for cls, last in last_ids.items():
        out.write("""
#define %(enum)s_FIRST_ID      (%(enum)s + 1)
#define %(enum)s_LAST_ID       %(last)s
#define %(enum)s_VALID_ID(id) \\
    ((id) >= %(enum)s_FIRST_ID && \\
     (id) <= %(enum)s_LAST_ID)
""" % dict(enum=enum_name(cls), last=last))
    out.write("""
/**
 * Function to check a wire ID
 * @param object_id The ID to check
 * @param base_object_id The inheritance parent, if applicable
 * @returns boolean: If base_object_id is an inheritance class, check if
 * object_id is valid as a subclass.  Otherwise return 1.
 *
 * Note: Could check that object_id == base_object_id in the
 * second case.
 */
static inline int
of_wire_id_valid(int object_id, int base_object_id) {
    switch (base_object_id) {
    case OF_ACTION:
        return OF_ACTION_VALID_ID(object_id);
    case OF_OXM:
        return OF_OXM_VALID_ID(object_id);
    case OF_QUEUE_PROP:
        return OF_QUEUE_PROP_VALID_ID(object_id);
    case OF_TABLE_FEATURE_PROP:
        return OF_TABLE_FEATURE_PROP_VALID_ID(object_id);
    case OF_INSTRUCTION:
        return OF_INSTRUCTION_VALID_ID(object_id);
    default:
        break;
    }
    return 1;
}
""")

def gen_object_enum_str(out):
    out.write("\nconst char *const of_object_id_str[] = {\n")
    out.write("    \"of_object\",\n")
    for cls in of_g.ordered_messages:
        out.write("    \"%s\",\n" % cls)
    out.write("\n    /* Non-message objects */\n")
    for cls in of_g.ordered_non_messages:
        out.write("    \"%s\",\n" % cls)
    out.write("\n    /* List objects */\n")
    for cls in of_g.ordered_list_objects:
        out.write("    \"%s\",\n" % cls)
    out.write("\n    /* Generic stats request/reply types; pseudo objects */\n")
    for cls in of_g.ordered_pseudo_objects:
        out.write("    \"%s\",\n" % cls)
    out.write("\n    \"of_unknown_object\"\n};\n")

    # We'll do version strings while we're at it
    out.write("""
 const char *const of_version_str[] = {
    "Unknown OpenFlow Version",
    "OpenFlow-1.0",
    "OpenFlow-1.1",
    "OpenFlow-1.2"
};

const of_mac_addr_t of_mac_addr_all_ones = {
    {
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff
    }
};
/* Just to be explicit; static duration vars are init'd to 0 */
const of_mac_addr_t of_mac_addr_all_zeros = {
    {
        0, 0, 0, 0, 0, 0
    }
};

const of_ipv6_t of_ipv6_all_ones = {
    {
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
    }
};
/* Just to be explicit; static duration vars are init'd to 0 */
const of_ipv6_t of_ipv6_all_zeros = {
    {
        0, 0, 0, 0, 0, 0, 0, 0,
        0, 0, 0, 0, 0, 0, 0, 0
    }
};

/** @var of_error_strings
 * The error string map; use abs value to index
 */
const char *const of_error_strings[] = { OF_ERROR_STRINGS };
""")

################################################################
#
# Internal Utility Functions
#
################################################################


def acc_name(cls, m_name):
    """
    Generate the root name of an accessor function for typedef
    @param cls The class name
    @param m_name The member name
    """
    (m_type, get_rv) = get_acc_rv(cls, m_name)
    return "%s_%s" % (cls, m_type)

def get_acc_rv(cls, m_name):
    """
    Determine the data type and return type for a get accessor.

    The return type may be "void" or it may be the accessor type
    depending on the system configuration and on the data type.

    @param cls The class name
    @param m_name The member name
    @return A pair (m_type, rv) where m_type is the unified type of the
    member and rv is the get_accessor return type
    """
    member = of_g.unified[cls]["union"][m_name]
    m_type = member["m_type"]
    rv = "int"
    if member_returns_val(cls, m_name):
        rv = m_type
    if m_type[-2:] == "_t":
        m_type = m_type[:-2]

    return (m_type, rv)

def param_list(cls, m_name, a_type):
    """
    Generate the parameter list (no parens) for an a_type accessor
    @param cls The class name
    @param m_name The member name
    @param a_type One of "set" or "get" or TBD
    """
    member = of_g.unified[cls]["union"][m_name]
    m_type = member["m_type"]
    params = ["%s_t *obj" % cls]
    if a_type == "set":
        if loxi_utils.type_is_scalar(m_type):
            params.append("%s %s" % (m_type, m_name))
        else:
            params.append("%s *%s" % (m_type, m_name))
    elif a_type in ["get", "bind"]:
        params.append("%s *%s" % (m_type, m_name))
    else:
        debug("Class %s, name %s Bad param list a_type: %s" %
            (cls, m_name, a_type))
        sys.exit(1)
    return params

def typed_function_base(cls, m_name):
    """
    Generate the core name for accessors based on the type
    @param cls The class name
    @param m_name The member name
    """
    (m_type, get_rv) = get_acc_rv(cls, m_name)
    return "%s_%s" % (cls, m_type)

def member_function_base(cls, m_name):
    """
    Generate the core name for accessors based on the member name
    @param cls The class name
    @param m_name The member name
    """
    return "%s_%s" % (cls, m_name)

def field_ver_get(cls, m_name):
    """
    Generate a dict, indexed by wire version, giving a pair (type, offset)

    @param cls The class name
    @param m_name The name of the class member

    If offset is not known for m_name, the type
    A dict is used for more convenient indexing.
    """
    result = {}

    for ver in of_g.unified[cls]:
        if type(ver) == type(0): # It's a version
            if "use_version" in of_g.unified[cls][ver]: # deref version ref
                ref_ver = of_g.unified[cls][ver]["use_version"]
                members = of_g.unified[cls][ref_ver]["members"]
            else:
                members = of_g.unified[cls][ver]["members"]
            idx = loxi_utils.member_to_index(m_name, members)
            if (idx < 0):
                continue # Member not in this version
            m_type = members[idx]["m_type"]
            offset = members[idx]["offset"]

            # If m_type is mixed, get wire version type from global data
            if m_type in of_g.of_mixed_types and \
                    ver in of_g.of_mixed_types[m_type]:
                m_type = of_g.of_mixed_types[m_type][ver]

            # add version to result list
            result[ver] = (m_type, offset)

    return result

def v3_match_offset_get(cls):
    """
    Return the offset of an OF 1.2 match in an object if it has such; 
    otherwise return -1
    """
    result = field_ver_get(cls, "match")
    if of_g.VERSION_1_2 in result:
        if result[of_g.VERSION_1_2][0] == "of_match_v3_t":
            return result[of_g.VERSION_1_2][1]
    return -1

################################################################
#
# OpenFlow Object Definitions
#
################################################################


def gen_of_object_defs(out):
    """
    Generate low level of_object core operations
    @param out The file for output, already open
    """

def gen_generics(out):
    for (cls, subclasses) in type_maps.inheritance_map.items():
        out.write("""
/**
 * Inheritance super class for %(cls)s
 *
 * This class is the union of %(cls)s classes.  You can refer
 * to it untyped by refering to the member 'header' whose structure
 * is common across all sub-classes.
 */

union %(cls)s_u {
    %(cls)s_header_t header; /* Generic instance */
""" % dict(cls=cls))
        for subcls in sorted(subclasses):
            out.write("    %s_%s_t %s;\n" % (cls, subcls, subcls))
        out.write("};\n")

def gen_struct_typedefs(out):
    """
    Generate typedefs for all struct objects
    @param out The file for output, already open
    """

    out.write("\n/* LOCI inheritance parent typedefs */\n")
    for cls in type_maps.inheritance_map:
        out.write("typedef union %(cls)s_u %(cls)s_t;\n" % dict(cls=cls))
    out.write("\n/* LOCI object typedefs */\n")
    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue
        if config_check("gen_fn_ptrs"):
            out.write("typedef struct %(cls)s_s %(cls)s_t;\n" % dict(cls=cls))
        else:
            template = "typedef of_object_t %(cls)s_t;\n"
            out.write(template % dict(cls=cls))

    out.write("""
/****************************************************************
 *
 * Additional of_object defines
 * These are needed for some static inline ops, so we put them here.
 *
 ****************************************************************/

/* Delete an OpenFlow object without reference to its type */
extern void of_object_delete(of_object_t *obj);

""")

def gen_generic_union(out):
    """
    Generate the generic union object composing all LOCI objects

    @param out The file to which to write the decs
    """
    out.write("""
/**
 * The common LOCI object is a union of all possible objects.
 */
union of_generic_u {
    of_object_t object;  /* Common base class with fundamental accessors */

    /* Message objects */
""")
    for cls in of_g.ordered_messages:
        out.write("    %s_t %s;\n" % (cls, cls))
    out.write("\n    /* Non-message composite objects */\n")
    for cls in of_g.ordered_non_messages:
        if cls in type_maps.inheritance_map:
            continue
        out.write("    %s_t %s;\n" % (cls, cls))
    out.write("\n    /* List objects */\n")
    for cls in of_g.ordered_list_objects:
        out.write("    %s_t %s;\n" % (cls, cls))
    out.write("};\n")

def gen_common_struct_definitions(out):
    out.write("""
/****************************************************************
 *
 * Unified structure definitions
 *
 ****************************************************************/

struct of_object_s {
    /* Common members */
%(common)s
};
""" % dict(common=of_g.base_object_members))

def gen_flow_add_setup_function_declarations(out):
    """
    Add the declarations for functions that can be initialized
    by a flow add.  These are defined external to LOXI.
    """

    out.write("""
/****************************************************************
 * Functions for objects that can be initialized by a flow add message.
 * These are defined in a non-autogenerated file
 ****************************************************************/

/**
 * @brief Set up a flow removed message from the original add
 * @param obj The flow removed message being updated
 * @param flow_add The flow_add message to use
 *
 * Initialize the following fields of obj to be identical
 * to what was originally on the wire from the flow_add object:
 *     match
 *     cookie
 *     priority
 *     idle_timeout
 *     hard_timeout
 *
 */

extern int
of_flow_removed_setup_from_flow_add(of_flow_removed_t *obj,
                                    of_flow_add_t *flow_add);


/**
 * @brief Set up the packet in match structure from the original add
 * @param obj The packet in message being updated
 * @param flow_add The flow_add message to use
 * @returns Indigo error code.  Does not return a version error if
 * the version does not require initializing obj.
 *
 * Initialize the match member of obj to be identical to what was originally
 * on the wire from the flow_add object.  If applicable, the table ID is also
 * initialized from the flow_add object.
 *
 * This API applies to 1.2 and later only.
 */

extern int
of_packet_in_setup_from_flow_add(of_packet_in_t *obj,
                                 of_flow_add_t *flow_add);


/**
 * @brief Set up the flow stats entry from the original add
 * @param obj The packet in message being updated
 * @param flow_add The flow_add message to use
 * @param effects Optional actions or instructions; see below.
 *
 * Initialize the following fields of obj to be identical
 * to what was originally on the wire from the flow_add object:
 *     match
 *     actions/instructions (effects)
 *     cookie
 *     priority
 *     idle_timeout
 *     hard_timeout
 *
 * Note that the actions/instructions of a flow may be modified by a 
 * subsequent flow modify message.  To facilitate implementations,
 * the "effects" parameter is provided.  If effects is NULL, the
 * actions/instructions are taken from the flow_add message.
 * Otherwise, effects is coerced to the proper type (actions or
 * instructions) and used to init obj.
 */

extern int
of_flow_stats_entry_setup_from_flow_add(of_flow_stats_entry_t *obj,
                                        of_flow_add_t *flow_add,
                                        of_object_t *effects);
""")

def gen_struct_definitions(out):
    """
    Generate the declaration of all of_ C structures

    @param out The file to which to write the decs
    """

    # This should only get called if gen_fn_ptr is true in code_gen_config
    if not config_check("gen_fn_ptrs"):
        debug("Error: gen_struct_defs called, but no fn ptrs set")
        return

    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue # These are generated elsewhere
        note = ""
        if loxi_utils.class_is_message(cls):
            note = " /* Class is message */"
        out.write("struct %s_s {%s\n" % (cls, note))
        out.write("""    /* Common members */
%s
    /* Class specific members */
""" % of_g.base_object_members)
        if loxi_utils.class_is_list(cls):
            out.write("""
    %(cls)s_first_f first;
    %(cls)s_next_f next;
    %(cls)s_append_bind_f append_bind;
    %(cls)s_append_f append;
};

""" % {"cls": cls})
            continue   # All done with list object

        # Else, not a list instance; add accessors for all data members
        for m_name in of_g.ordered_members[cls]:
            if m_name in of_g.skip_members:
                # These members (length, etc) are handled internally
                continue
            f_name = acc_name(cls, m_name)
            out.write("    %s_get_f %s;\n" % (f_name, m_name + "_get"))
            out.write("    %s_set_f %s;\n" % (f_name, m_name + "_set"))
        out.write("};\n\n")


################################################################
#
# List accessor code generation
#
# Currently these all implement copy on read semantics
#
################################################################

def init_call(e_type, obj, ver, length, cw):
    """
    Generate the init call given the strings for params
    """
    hdr = "" # If inheritance type, coerce to hdr object
    obj_name = obj
    if e_type in type_maps.inheritance_map:
        hdr = "_header"
        obj_name = "(%s_header_t *)" % e_type + obj

    return """\
%(e_type)s%(hdr)s_init(%(obj_name)s,
            %(ver)s, %(length)s, %(cw)s)\
""" % dict(e_type=e_type, hdr=hdr, obj_name=obj_name, ver=ver,
           length=length, cw=cw)

def gen_list_first(out, cls, e_type):
    """
    Generate the body of a list_first operation
    @param cls The class name for which code is being generated
    @param e_type The element type of the list
    @param out The file to which to write
    """
    i_call = init_call(e_type, "obj", "list->version", "0", "1")
    if e_type in type_maps.inheritance_map:
        len_str = "obj->header.length"
    else:
        len_str = "obj->length"

    out.write("""
/**
 * Associate an iterator with a list
 * @param list The list to iterate over
 * @param obj The list entry iteration pointer
 * @return OF_ERROR_RANGE if the list is empty (end of list)
 *
 * The obj instance is completely initialized.  The caller is responsible
 * for cleaning up any wire buffers associated with obj before this call
 */

int
%(cls)s_first(%(cls)s_t *list,
    %(e_type)s_t *obj)
{
    int rv;

    %(i_call)s;
    if ((rv = of_list_first((of_object_t *)list, (of_object_t *)obj)) < 0) {
        return rv;
    }
""" % dict(cls=cls, e_type=e_type, i_call=i_call))

    # Special case flow_stats_entry lists

    out.write("""
    of_object_wire_init((of_object_t *) obj, %(u_type)s,
                        list->length);
    if (%(len_str)s == 0) {
        return OF_ERROR_PARSE;
    }

    return rv;
}
""" % dict(cls=cls, e_type=e_type, u_type=enum_name(e_type), len_str=len_str))


def gen_bind(out, cls, m_name, m_type):
    """
    Generate the body of a bind function
    @param out The file to which to write
    @param cls The class name for which code is being generated
    @param m_name The name of the data member
    @param m_type The type of the data member
    """

    bparams = ",\n    ".join(param_list(cls, m_name, "bind"))

    i_call = init_call(e_type, "child", "parent->version", "0", "1")

    out.write("""
/**
 * Bind the child object to the parent object for read processing
 * @param parent The parent object
 * @param child The child object
 *
 * The child obj instance is completely initialized.
 */

int
%(cls)s_%(m_name)_bind(%(cls)s_t *parent,
    %(e_type)s_t *child)
{
    int rv;

    %(i_call)s;

    /* Derive offset and length of child in parent */
    OF_TRY(of_object_child_attach(parent, child, 
    if ((rv = of_list_first((of_object_t *)list, (of_object_t *)obj)) < 0) {
        return rv;
    }
""" % dict(cls=cls, e_type=e_type, i_call=i_call))

    # Special case flow_stats_entry lists

    out.write("""
    rv = of_object_wire_init((of_object_t *) obj, %(u_type)s,
                               list->length);
    if ((rv == OF_ERROR_NONE) && (%(len_str)s == 0)) {
        return OF_ERROR_PARSE;
    }

    return rv;
}
""" % dict(cls=cls, e_type=e_type, u_type=enum_name(e_type), len_str=len_str))


def gen_list_next(out, cls, e_type):
    """
    Generate the body of a list_next operation
    @param cls The class name for which code is being generated
    @param e_type The element type of the list
    @param out The file to which to write
    """

    if e_type in type_maps.inheritance_map:
        len_str = "obj->header.length"
    else:
        len_str = "obj->length"
        
    out.write("""
/**
 * Advance an iterator to the next element in a list
 * @param list The list being iterated
 * @param obj The list entry iteration pointer
 * @return OF_ERROR_RANGE if already at the last entry on the list
 *
 */

int
%(cls)s_next(%(cls)s_t *list,
    %(e_type)s_t *obj)
{
    int rv;

    if ((rv = of_list_next((of_object_t *)list, (of_object_t *)obj)) < 0) {
        return rv;
    }

    rv = of_object_wire_init((of_object_t *) obj, %(u_type)s,
        list->length);

    if ((rv == OF_ERROR_NONE) && (%(len_str)s == 0)) {
        return OF_ERROR_PARSE;
    }

    return rv;
}
""" % dict(cls=cls, e_type=e_type, u_type=enum_name(e_type), len_str=len_str))

def gen_list_append(out, cls, e_type):
    """
    Generate the body of a list append functions
    @param cls The class name for which code is being generated
    @param e_type The element type of the list
    @param out The file to which to write
    """

    out.write("""
/**
 * Set up to append an object of type %(e_type)s to an %(cls)s.
 * @param list The list that is prepared for append
 * @param obj Pointer to object to hold data to append
 *
 * The obj instance is completely initialized.  The caller is responsible
 * for cleaning up any wire buffers associated with obj before this call.
 *
 * See the generic documentation for of_list_append_bind.
 */

int
%(cls)s_append_bind(%(cls)s_t *list,
    %(e_type)s_t *obj)
{
    return of_list_append_bind((of_object_t *)list, (of_object_t *)obj);
}

/**
 * Append an item to a %(cls)s list.
 *
 * This copies data from item and leaves item untouched.
 *
 * See the generic documentation for of_list_append.
 */

int
%(cls)s_append(%(cls)s_t *list,
    %(e_type)s_t *item)
{
    return of_list_append((of_object_t *)list, (of_object_t *)item);
}

""" % dict(cls=cls, e_type=e_type))

def gen_list_accessors(out, cls):
    e_type = loxi_utils.list_to_entry_type(cls)
    gen_list_first(out, cls, e_type)
    gen_list_next(out, cls, e_type)
    gen_list_append(out, cls, e_type)

################################################################
#
# Accessor Functions
#
################################################################

    
def gen_accessor_declarations(out):
    """
    Generate the declaration of each version independent accessor

    @param out The file to which to write the decs
    """

    out.write("""
/****************************************************************
 *
 * Unified, per-member accessor function declarations
 *
 ****************************************************************/
""")
    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue
        out.write("\n/* Unified accessor functions for %s */\n" % cls)
        for m_name in of_g.ordered_members[cls]:
            if m_name in of_g.skip_members:
                continue
            m_type = loxi_utils.member_base_type(cls, m_name)
            base_name = "%s_%s" % (cls, m_name)
            gparams = ",\n    ".join(param_list(cls, m_name, "get"))
            get_ret_type = accessor_return_type("get", m_type)
            sparams = ",\n    ".join(param_list(cls, m_name, "set"))
            set_ret_type = accessor_return_type("set", m_type)
            bparams = ",\n    ".join(param_list(cls, m_name, "bind"))
            bind_ret_type = accessor_return_type("bind", m_type)

            if loxi_utils.type_is_of_object(m_type):
                # Generate bind accessors, but not get accessor
                out.write("""
extern %(set_ret_type)s %(base_name)s_set(
    %(sparams)s);
extern %(bind_ret_type)s %(base_name)s_bind(
    %(bparams)s);
extern %(m_type)s *%(cls)s_%(m_name)s_get(
    %(cls)s_t *obj);
""" % dict(base_name=base_name, sparams=sparams, bparams=bparams,
           m_name=m_name, m_type=m_type, cls=cls,
           set_ret_type=set_ret_type, bind_ret_type=bind_ret_type))
            else:
                out.write("""
extern %(set_ret_type)s %(base_name)s_set(
    %(sparams)s);
extern %(get_ret_type)s %(base_name)s_get(
    %(gparams)s);
""" % dict(base_name=base_name, gparams=gparams, sparams=sparams,
           get_ret_type=get_ret_type, set_ret_type=set_ret_type))
            
        if loxi_utils.class_is_list(cls):
            e_type = loxi_utils.list_to_entry_type(cls)
            out.write("""
extern int %(cls)s_first(
    %(cls)s_t *list, %(e_type)s_t *obj);
extern int %(cls)s_next(
    %(cls)s_t *list, %(e_type)s_t *obj);
extern int %(cls)s_append_bind(
    %(cls)s_t *list, %(e_type)s_t *obj);
extern int %(cls)s_append(
    %(cls)s_t *list, %(e_type)s_t *obj);

/**
 * Iteration macro for list of type %(cls)s
 * @param list Pointer to the list being iterated over of
 * type %(cls)s
 * @param elt Pointer to an element of type %(e_type)s
 * @param rv On exiting the loop will have the value OF_ERROR_RANGE.
 */
#define %(u_cls)s_ITER(list, elt, rv)  \\
    for ((rv) = %(cls)s_first((list), (elt));   \\
         (rv) == OF_ERROR_NONE;   \\
         (rv) = %(cls)s_next((list), (elt)))
""" % dict(u_cls=cls.upper(), cls=cls, e_type=e_type))


def wire_accessor(m_type, a_type):
    """
    Returns the name of the a_type accessor for low level wire buff offset
    @param m_type The member type
    @param a_type The accessor type (set or get)
    """
    # Strip off _t if present
    if m_type in of_g.of_base_types:
        m_type = of_g.of_base_types[m_type]["short_name"]
    if m_type in of_g.of_mixed_types:
        m_type = of_g.of_mixed_types[m_type]["short_name"]
    if m_type[-2:] == "_t":
        m_type = m_type[:-2]
    if m_type == "octets":
        m_type = "octets_data"
    return "of_wire_buffer_%s_%s" % (m_type, a_type)

def get_len_macro(cls, m_type, version):
    """
    Get the length macro for m_type in cls
    """
    if m_type.find("of_match") == 0:
        return "_WIRE_MATCH_PADDED_LEN(obj, offset)"
    if m_type.find("of_list_oxm") == 0:
        return "wire_match_len(obj, 0) - 4"
    if loxi_utils.class_is_tlv16(m_type):
        return "_TLV16_LEN(obj, offset)"
    if cls == "of_packet_out" and m_type == "of_list_action_t":
        return "_PACKET_OUT_ACTION_LEN(obj)"
    # Default is everything to the end of the object
    return "_END_LEN(obj, offset)"

def gen_accessor_offsets(out, cls, m_name, version, a_type, m_type, offset):
    """
    Generate the sub-object offset and length calculations for accessors
    @param out File being written
    @param m_name Name of member
    @param version Wire version being processed
    @param a_type The accessor type (set or get)
    @param m_type The original member type
    @param offset The offset of the object or -1 if not fixed
    """
    # determine offset
    o_str = "%d" % offset  # Default is fixed length
    if offset == -1:
        # There are currently 4 special cases for this
        # In general, get offset and length of predecessor
        if (loxi_utils.cls_is_flow_mod(cls) and m_name == "instructions"):
            pass
        elif (cls == "of_flow_stats_entry" and m_name == "instructions"):
            pass
        elif (cls == "of_packet_in" and m_name == "data"):
            pass
        elif (cls == "of_packet_out" and m_name == "data"):
            pass
        else:
            debug("Error: Unknown member with offset == -1")
            debug("  cls %s, m_name %s, version %d" % (cls, m_name, version))
            sys.exit(1)
        o_str = "_%s_%s_OFFSET(obj)" % (cls.upper()[3:], m_name.upper())

    out.write("""\
        offset = %s;
""" % o_str);

    # This could be moved to main body but for version check
    if not loxi_utils.type_is_scalar(m_type):
        if loxi_utils.class_is_var_len(m_type[:-2], version) or \
                m_type == "of_match_t":
            len_macro = get_len_macro(cls, m_type, version)
        else:
            len_macro = "%d" % of_g.base_length[(m_type[:-2], version)]
        out.write("        cur_len = %s;\n" % len_macro)
    out.write("        break;\n")

def length_of(m_type, version):
    """
    Return the length of a type based on the version
    """
    if m_type in of_g.of_mixed_types:
        m_type = of_g.of_mixed_types[m_type][version]
    if m_type in of_g.of_base_types:
        return of_g.of_base_types[m_type]["bytes"]
    if (m_type[:-2], version) in of_g.base_length:
        return of_g.base_length[(m_type[:-2], version)]
    print "Unknown length request", m_type, version
    sys.exit(1)
        

def gen_get_accessor_body(out, cls, m_type, m_name):
    """
    Generate the common operations for a get accessor
    """
    if loxi_utils.type_is_scalar(m_type):
        ver = ""      # See if version required for scalar update
        if m_type in of_g.of_mixed_types:
            ver = "ver, "
        out.write("""\
    %(wa)s(%(ver)swbuf, abs_offset, %(m_name)s);
""" % dict(wa=wire_accessor(m_type, "get"), ver=ver, m_name=m_name))

        if m_type == "of_port_no_t":
           out.write("    OF_PORT_NO_VALUE_CHECK(*%s, ver);\n" % m_name)
    elif m_type == "of_octets_t":
        out.write("""\
    ASSERT(cur_len + abs_offset <= WBUF_CURRENT_BYTES(wbuf));
    %(m_name)s->bytes = cur_len;
    %(m_name)s->data = OF_WIRE_BUFFER_INDEX(wbuf, abs_offset);
""" % dict(m_name=m_name))
    elif m_type == "of_match_t":
        out.write("""
    ASSERT(cur_len + abs_offset <= WBUF_CURRENT_BYTES(wbuf));
    match_octets.bytes = cur_len;
    match_octets.data = OF_OBJECT_BUFFER_INDEX(obj, offset);
    OF_TRY(of_match_deserialize(ver, %(m_name)s, &match_octets));
""" % dict(m_name=m_name))
    else:
        out.write("""
    /* Initialize child */
    %(m_type)s_init(%(m_name)s, obj->version, 0, 1);
    /* Attach to parent */
    %(m_name)s->parent = (of_object_t *)obj;
    %(m_name)s->wire_object.wbuf = obj->wire_object.wbuf;
    %(m_name)s->wire_object.obj_offset = abs_offset;
    %(m_name)s->wire_object.owned = 0;
    %(m_name)s->length = cur_len;
""" % dict(m_type=m_type[:-2], m_name=m_name))


def gen_set_accessor_body(out, cls, m_type, m_name):
    """
    Generate the contents of a set accessor
    """
    if loxi_utils.type_is_scalar(m_type) or m_type == "of_octets_t":
        ver = "" # See if version required for scalar update
        if m_type in of_g.of_mixed_types:
            ver = "ver, "
        cur_len = "" # See if version required for scalar update
        if m_type == "of_octets_t":
            cur_len = ", cur_len"
            out.write("""\
    new_len = %(m_name)s->bytes;
    of_wire_buffer_grow(wbuf, abs_offset + (new_len - cur_len));
""" % dict(m_name=m_name))
        out.write("""\
    %(wa)s(%(ver)swbuf, abs_offset, %(m_name)s%(cur_len)s);
""" % dict(wa=wire_accessor(m_type, "set"), ver=ver, cur_len=cur_len,
           m_name=m_name))

    elif m_type == "of_match_t":
        out.write("""
    /* Match object */
    OF_TRY(of_match_serialize(ver, %(m_name)s, &match_octets));
    new_len = match_octets.bytes;
    of_wire_buffer_replace_data(wbuf, abs_offset, cur_len,
        match_octets.data, new_len);
    /* Free match serialized octets */
    FREE(match_octets.data);
""" % dict(m_name=m_name))

    else:  # Other object type
        out.write("\n    /* LOCI object type */")
        # Need to special case OXM list
        out.write("""
    new_len = %(m_name)s->length;
    /* If underlying buffer already shared; nothing to do */
    if (obj->wire_object.wbuf == %(m_name)s->wire_object.wbuf) {
        of_wire_buffer_grow(wbuf, abs_offset + new_len);
        /* Verify that the offsets are correct */
        ASSERT(abs_offset == OF_OBJECT_ABSOLUTE_OFFSET(%(m_name)s, 0));
        /* ASSERT(new_len == cur_len); */ /* fixme: may fail for OXM lists */
        return %(ret_success)s;
    }

    /* Otherwise, replace existing object in data buffer */
    of_wire_buffer_replace_data(wbuf, abs_offset, cur_len,
        OF_OBJECT_BUFFER_INDEX(%(m_name)s, 0), new_len);
""" % dict(m_name=m_name, ret_success=accessor_return_success("set", m_type)))

    if not loxi_utils.type_is_scalar(m_type):
        if cls == "of_packet_out" and m_type == "of_list_action_t":
            out.write("""
    /* Special case for setting action lengths */
    _PACKET_OUT_ACTION_LEN_SET(obj, %(m_name)s->length);
""" % dict(m_name=m_name))
        elif m_type not in ["of_match_t", "of_octets_t"]:
            out.write("""
    /* @fixme Shouldn't this precede copying value's data to buffer? */
    if (%(m_name)s->wire_length_set != NULL) {
        %(m_name)s->wire_length_set((of_object_t *)%(m_name)s, %(m_name)s->length);
    }
""" % dict(m_name=m_name))
        out.write("""
    /* Not scalar, update lengths if needed */
    delta = new_len - cur_len;
    if (delta != 0) {
        /* Update parent(s) */
        of_object_parent_length_update((of_object_t *)obj, delta);
    }
""")

def obj_assert_check(cls):
    """
    The body of the assert check for an accessor
    We allow all versions of add/delete/modify to use the same accessors
    """
    if cls in ["of_flow_modify", "of_flow_modify_strict",
               "of_flow_delete", "of_flow_delete_strict",
               "of_flow_add"]:
        return "IS_FLOW_MOD_SUBTYPE(obj->object_id)"
    else:
        return "obj->object_id == %s" % cls.upper()

def gen_of_object_get(out, cls, m_name, m_type):
    sub_cls = m_type[:-2]
    out.write("""
/**
 * Create a copy of %(m_name)s into a new variable of type %(m_type)s from 
 * a %(cls)s instance.
 *
 * @param obj Pointer to the source of type %(cls)s_t
 * @returns A pointer to a new instance of type %(m_type)s whose contents
 * match that of %(m_name)s from source
 * @returns NULL if an error occurs
 */
%(m_type)s *
%(cls)s_%(m_name)s_get(%(cls)s_t *obj) {
    %(m_type)s _%(m_name)s;
    %(m_type)s *_%(m_name)s_ptr;

    %(cls)s_%(m_name)s_bind(obj, &_%(m_name)s);
    _%(m_name)s_ptr = (%(m_type)s *)of_object_dup(&_%(m_name)s);
    return _%(m_name)s_ptr;
}
""" % dict(m_name=m_name, m_type=m_type, cls=cls, sub_cls=sub_cls))

def gen_unified_acc_body(out, cls, m_name, ver_type_map, a_type, m_type):
    """
    Generate the body of a set or get accessor function

    @param out The file to which to write the decs
    @param cls The class name
    @param m_name The member name
    @param ver_type_map Maps (type, offset) pairs to a list of versions
    @param a_type The accessor type, set or get
    @param m_type The original member type

    The type values in ver_type_map are now ignored as we've pushed down
    the type munging to the lower level.

    This is unified because the version switch case processing is the
    same for both set and get
    """
    out.write("""{
    of_wire_buffer_t *wbuf;
    int offset = 0; /* Offset of value relative to the start obj */
    int abs_offset; /* Offset of value relative to start of wbuf */
    of_version_t ver;
""")

    if not loxi_utils.type_is_scalar(m_type):
        out.write("""\
    int cur_len = 0; /* Current length of object data */
""")
        if a_type == "set":
            out.write("""\
    int new_len, delta; /* For set, need new length and delta */
""")

    # For match, need octet string for set/get
    if m_type == "of_match_t":
        out.write("""\
    of_octets_t match_octets; /* Serialized string for match */
""")

    out.write("""
    ASSERT(%(assert_str)s);
    ver = obj->version;
    wbuf = OF_OBJECT_TO_WBUF(obj);
    ASSERT(wbuf != NULL);

    /* By version, determine offset and current length (where needed) */
    switch (ver) {
""" % dict(assert_str=obj_assert_check(cls)))

    for first in sorted(ver_type_map):
        (prev_t, prev_o) = ver_type_map[first]
        prev_len = length_of(prev_t, first)
        prev = first
        out.write("    case %s:\n" % of_g.wire_ver_map[first])
        break

    for next in sorted(ver_type_map):
        if next == first:
            continue

        (t, o) = ver_type_map[next]
        cur_len = length_of(t, next)
        if o == prev_o and cur_len == prev_len:
            out.write("    case %s:\n" % of_g.wire_ver_map[next])
            continue
        gen_accessor_offsets(out, cls, m_name, prev, a_type, m_type, prev_o)
        out.write("    case %s:\n" % of_g.wire_ver_map[next])
        (prev_t, prev_o, prev_len, prev) = (t, o, cur_len, next)

    gen_accessor_offsets(out, cls, m_name, next, a_type, m_type, prev_o)
    out.write("""\
    default:
        ASSERT(0);
    }

    abs_offset = OF_OBJECT_ABSOLUTE_OFFSET(obj, offset);
    ASSERT(abs_offset >= 0);
""")
    if not loxi_utils.type_is_scalar(m_type):
        out.write("    ASSERT(cur_len >= 0 && cur_len < 64 * 1024);\n")

    # Now generate the common accessor code
    if a_type in ["get", "bind"]:
        gen_get_accessor_body(out, cls, m_type, m_name)
    else:
        gen_set_accessor_body(out, cls, m_type, m_name)

    out.write("""
    OF_LENGTH_CHECK_ASSERT(obj);

    return %s;
}
""" % accessor_return_success(a_type, m_type))

def gen_of_obj_bind(out, cls, m_name, m_type, ver_type_map):
    """
    For generating the bind call for OF sub-objects
    """

    params = ",\n    ".join(param_list(cls, m_name, "bind"))
    out.write("""
/**
 * Bind an object of type %(m_type)s to the parent of type %(cls)s for
 * member %(m_name)s
 * @param obj Pointer to an object of type %(cls)s.
 * @param %(m_name)s Pointer to the child object of type
 * %(m_type)s to be filled out.
 * \ingroup %(cls)s
 *
 * The parameter %(m_name)s is filled out to point to the same underlying
 * wire buffer as its parent.
 *
 */
""" % dict(m_name=m_name, cls=cls, m_type=m_type))

    ret_type = accessor_return_type("bind", m_type)
    out.write("%s\n%s_%s_bind(\n    %s)\n" % (ret_type, cls, m_name, params))
    gen_unified_acc_body(out, cls, m_name, ver_type_map, "bind", m_type)

def gen_get_accessor(out, cls, m_name, m_type, ver_type_map):
    """
    For generating the get call for non- OF sub-objects
    """
    params = ",\n    ".join(param_list(cls, m_name, "get"))
    out.write("""
/**
 * Get %(m_name)s from an object of type %(cls)s.
 * @param obj Pointer to an object of type %(cls)s.
 * @param %(m_name)s Pointer to the child object of type
 * %(m_type)s to be filled out.
 *
 */
""" % dict(m_name=m_name, cls=cls, m_type=m_type))

    ret_type =  accessor_return_type("get", m_type)
    out.write("%s\n%s_%s_get(\n    %s)\n" % (ret_type, cls, m_name, params))
    gen_unified_acc_body(out, cls, m_name, ver_type_map, "get", m_type)

def gen_accessor_definitions(out):
    """
    Generate the body of each version independent accessor

    @param out The file to which to write the decs
    """

    out.write("""
/****************************************************************
 *
 * Unified accessor function definitions
 *
 ****************************************************************/
""")
    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue
        out.write("\n/* Unified accessor functions for %s */\n" % cls)
        if loxi_utils.class_is_list(cls):
            gen_list_accessors(out, cls)
            continue
        out.write("/** \\ingroup %s \n * @{ */\n" % cls)
        for m_name in of_g.ordered_members[cls]:
            if m_name in of_g.skip_members:
                continue
            m_type = loxi_utils.member_base_type(cls, m_name)
            ver_type_map = field_ver_get(cls, m_name)

            # Generate get/bind pending on member type
            # FIXME:  Does this do the right thing for match?
            if loxi_utils.type_is_of_object(m_type):
                gen_of_obj_bind(out, cls, m_name, m_type, ver_type_map)
                gen_of_object_get(out, cls, m_name, m_type)
            else:
                gen_get_accessor(out, cls, m_name, m_type, ver_type_map)

            # Now generate set accessor for all objects
            params = ",\n    ".join(param_list(cls, m_name, "set"))
            out.write("""
/**
 * Set %(m_name)s in an object of type %(cls)s.
 * @param obj Pointer to an object of type %(cls)s.
""" % dict(m_name=m_name, cls=cls, m_type=m_type))
            if loxi_utils.type_is_scalar(m_type) or m_type == "of_octets_t":
                out.write("""\
 * @param %(m_name)s The value to write into the object
 */
""" % dict(m_name=m_name, cls=cls, m_type=m_type))
            else:
                out.write("""\
 * @param %(m_name)s Pointer to the child of type %(m_type)s.
 *
 * If the child's wire buffer is the same as the parent's, then
 * nothing is done as the changes have already been registered in the
 * parent.  Otherwise, the data in the child's wire buffer is inserted
 * into the parent's and the appropriate lengths are updated.
 */
""" % dict(m_name=m_name, cls=cls, m_type=m_type))
            ret_type = accessor_return_type("set", m_type)
            out.write("%s\n%s_%s_set(\n    %s)\n" % (ret_type, cls, m_name, params))
            gen_unified_acc_body(out, cls, m_name, ver_type_map, "set", m_type)

        out.write("\n/** @} */\n")

def gen_acc_pointer_typedefs(out):
    """
    Generate the function pointer typedefs for in-struct accessors
    @param out The file to which to write the typedefs
    """

    out.write("""
/****************************************************************
 *
 * Accessor function pointer typedefs
 *
 ****************************************************************/

/*
 * Generic accessors:
 *
 * Many objects have a length represented in the wire buffer
 * wire_length_get and wire_length_set access these values directly on the
 * wire.
 *
 * Many objects have a length represented in the wire buffer
 * wire_length_get and wire_length_set access these values directly on the
 * wire.
 *
 * FIXME: TBD if wire_length_set and wire_type_set are required.
 */
typedef void (*of_wire_length_get_f)(of_object_t *obj, int *bytes);
typedef void (*of_wire_length_set_f)(of_object_t *obj, int bytes);
typedef void (*of_wire_type_get_f)(of_object_t *obj, of_object_id_t *id);
typedef void (*of_wire_type_set_f)(of_object_t *obj, of_object_id_t id);
""")
    # If not using function pointers in classes, don't gen typedefs below
    if not config_check("gen_fn_ptrs"):
        return

    # For each class, for each type it uses, generate a typedef
    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue
        out.write("\n/* Accessor function pointer typedefs for %s */\n" % cls)
        types_done = list()
        for m_name in of_g.ordered_members[cls]:
            (m_type, get_rv) = get_acc_rv(cls, m_name)
            if (m_type, get_rv) in types_done:
                continue
            types_done.append((m_type, get_rv))
            fn = "%s_%s" % (cls, m_type)
            params = ", ".join(param_list(cls, m_name, "get"))
            out.write("typedef int (*%s_get_f)(\n    %s);\n" %
                      (fn, params))

            params = ", ".join(param_list(cls, m_name, "set"))
            out.write("typedef int (*%s_set_f)(\n    %s);\n" %
                      (fn, params))
        if loxi_utils.class_is_list(cls):
            obj_type = loxi_utils.list_to_entry_type(cls)
            out.write("""typedef int (*%(cls)s_first_f)(
    %(cls)s_t *list,
    %(obj_type)s_t *obj);
typedef int (*%(cls)s_next_f)(
    %(cls)s_t *list,
    %(obj_type)s_t *obj);
typedef int (*%(cls)s_append_bind_f)(
    %(cls)s_t *list,
    %(obj_type)s_t *obj);
typedef int (*%(cls)s_append_f)(
    %(cls)s_t *list,
    %(obj_type)s_t *obj);
""" % {"cls":cls, "obj_type":obj_type})

#             out.write("""
# typedef int (*%(cls)s_get_f)(
#     %(cls)s_t *list,
#     %(obj_type)s_t *obj, int index);
# typedef int (*%(cls)s_set_f)(
#     %(cls)s_t *list,
#     %(obj_type)s_t *obj, int index);
# typedef int (*%(cls)s_append_f)(
#     %(cls)s_t *list,
#     %(obj_type)s_t *obj, int index);
# typedef int (*%(cls)s_insert_f)(
#     %(cls)s_t *list,
#     %(obj_type)s_t *obj, int index);
# typedef int (*%(cls)s_remove_f)(
#     %(cls)s_t *list,
#     int index);
# """ % {"cls":cls, "obj_type":obj_type})

################################################################
#
# New/Delete Function Definitions
#
################################################################


################################################################
# First, some utility functions for new/delete
################################################################

def del_function_proto(cls):
    """
    Return the prototype for the delete operator for the given class
    @param cls The class name
    """
    fn = "void\n"
    return fn


def instantiate_fn_ptrs(cls, ilvl, out):
    """
    Generate the C code to instantiate function pointers for a class
    @param cls The class name
    @param ilvl The base indentation level
    @param out The file to which to write the functions
    """
    for m_name in of_g.ordered_members[cls]:
        if m_name in of_g.skip_members:
            continue
        out.write(" " * ilvl + "obj->%s_get = %s_%s_get;\n" %
                  (m_name, cls, m_name))
        out.write(" " * ilvl + "obj->%s_set = %s_%s_set;\n" %
                  (m_name, cls, m_name))

################################################################
# Routines to generate the body of new/delete functions
################################################################

def gen_init_fn_body(cls, out):
    """
    Generate function body for init function
    @param cls The class name for the function
    @param out The file to which to write
    """
    if cls in type_maps.inheritance_map:
        param = "obj_p"
    else:
        param = "obj"

    out.write("""
/**
 * Initialize an object of type %(cls)s.
 *
 * @param obj Pointer to the object to initialize
 * @param version The wire version to use for the object
 * @param bytes How many bytes in the object
 * @param clean_wire Boolean: If true, clear the wire object control struct
 *
 * If bytes < 0, then the default fixed length is used for the object
 *
 * This is a "coerce" function that sets up the pointers for the
 * accessors properly.  
 *
 * If anything other than 0 is passed in for the buffer size, the underlying
 * wire buffer will have 'grow' called.
 */

void
%(cls)s_init(%(cls)s_t *%(param)s,
    of_version_t version, int bytes, int clean_wire)
{
""" % dict(cls=cls, param=param))

    # Use an extra pointer to deal with inheritance classes
    if cls in type_maps.inheritance_map:
        out.write("""\
    %s_header_t *obj;

    obj = &obj_p->header;  /* Need instantiable subclass */
""" % cls)

    out.write("""
    ASSERT(of_object_fixed_len[version][%(enum)s] >= 0);
    if (clean_wire) {
        MEMSET(obj, 0, sizeof(*obj));
    }
    if (bytes < 0) {
        bytes = of_object_fixed_len[version][%(enum)s];
    }
    obj->version = version;
    obj->length = bytes;
    obj->object_id = %(enum)s;
""" % dict(cls=cls, enum=enum_name(cls)))
    gen_coerce_ops(out, cls)

    out.write("""
    /* Grow the wire buffer */
    if (obj->wire_object.wbuf != NULL) {
        int tot_bytes;

        tot_bytes = bytes + obj->wire_object.obj_offset;
        of_wire_buffer_grow(obj->wire_object.wbuf, tot_bytes);
    }
}

""")

## @fixme This should also be updated once there is a map from
# class instance to wire length/type accessors
def gen_wire_push_fn(cls, out):
    """
    Generate the calls to push values into the wire buffer
    """
    if type_maps.class_is_virtual(cls):
        print "Push fn gen called for virtual class " + cls
        return

    out.write("""
/**
 * Helper function to push values into the wire buffer
 */
static inline int
%(cls)s_push_wire_values(%(cls)s_t *obj)
{
""" % dict(cls=cls))

    if loxi_utils.class_is_message(cls):
        out.write("""
    /* Message obj; push version, length and type to wire */
    of_message_t msg;

    if ((msg = OF_OBJECT_TO_MESSAGE(obj)) != NULL) {
        of_message_version_set(msg, obj->version);
        of_message_length_set(msg, obj->length);
        OF_TRY(of_wire_message_object_id_set(OF_OBJECT_TO_WBUF(obj),
                 %(name)s));
    }
""" % dict(name = enum_name(cls)))
 
        for version in of_g.of_version_range:
            if type_maps.class_is_extension(cls, version):
                exp_name = type_maps.extension_to_experimenter_macro_name(cls)
                subtype = type_maps.extension_message_to_subtype(cls, version)
                if subtype is None or exp_name is None:
                    print "Error in mapping extension message"
                    print cls, version
                    sys.exit(1)
                out.write("""
    if (obj->version == %(version)s) {
        of_message_experimenter_id_set(OF_OBJECT_TO_MESSAGE(obj),
                                       %(exp_name)s);
        of_message_experimenter_subtype_set(OF_OBJECT_TO_MESSAGE(obj),
                                            %(subtype)s);
    }
""" % dict(exp_name=exp_name, version=of_g.wire_ver_map[version],
           subtype=str(subtype)))
           
    else: # Not a message
        if loxi_utils.class_is_tlv16(cls):
            out.write("""
    /* TLV obj; set length and type */
    of_tlv16_wire_length_set((of_object_t *)obj, obj->length);
    of_tlv16_wire_object_id_set((of_object_t *)obj,
           %(enum)s);
""" % dict(enum=enum_name(cls)))
            # Some tlv16 types may be extensions requiring more work
            if cls in ["of_action_bsn_mirror", "of_action_id_bsn_mirror",
                       "of_action_bsn_set_tunnel_dst", "of_action_id_bsn_set_tunnel_dst",
                       "of_action_nicira_dec_ttl", "of_action_id_nicira_dec_ttl"]:
                out.write("""
    /* Extended TLV obj; Call specific accessor */
    of_extension_object_id_set(obj, %(enum)s);
""" % dict(cls=cls, enum=enum_name(cls)))
                

        if loxi_utils.class_is_oxm(cls):
            out.write("""\
    /* OXM obj; set length and type */
    of_oxm_wire_length_set((of_object_t *)obj, obj->length);
    of_oxm_wire_object_id_set((of_object_t *)obj, %(enum)s);
""" % dict(enum=enum_name(cls)))
        if loxi_utils.class_is_u16_len(cls) or cls == "of_packet_queue":
            out.write("""
    obj->wire_length_set((of_object_t *)obj, obj->length);
""")

        if cls == "of_meter_stats":
            out.write("""
    of_meter_stats_wire_length_set((of_object_t *)obj, obj->length);
""" % dict(enum=enum_name(cls)))

    out.write("""
    return OF_ERROR_NONE;
}
""")

def gen_new_fn_body(cls, out):
    """
    Generate function body for new function
    @param cls The class name for the function
    @param out The file to which to write
    """

    out.write("""
/**
 * \\defgroup %(cls)s %(cls)s
 */
""" % dict(cls=cls))

    if not type_maps.class_is_virtual(cls):
        gen_wire_push_fn(cls, out)

    out.write("""
/**
 * Create a new %(cls)s object
 *
 * @param version The wire version to use for the object
 * @return Pointer to the newly create object or NULL on error
 *
 * Initializes the new object with it's default fixed length associating
 * a new underlying wire buffer.
 *
 * Use new_from_message to bind an existing message to a message object,
 * or a _get function for non-message objects.
 *
 * \\ingroup %(cls)s
 */

%(cls)s_t *
%(cls)s_new_(of_version_t version)
{
    %(cls)s_t *obj;
    int bytes;

    bytes = of_object_fixed_len[version][%(enum)s];

    /* Allocate a maximum-length wire buffer assuming we'll be appending to it. */
    if ((obj = (%(cls)s_t *)of_object_new(OF_WIRE_BUFFER_MAX_LENGTH)) == NULL) {
        return NULL;
    }

    %(cls)s_init(obj, version, bytes, 0);
""" % dict(cls=cls, enum=enum_name(cls)))
    if not type_maps.class_is_virtual(cls):
        out.write("""
    if (%(cls)s_push_wire_values(obj) < 0) {
        FREE(obj);
        return NULL;
    }
""" % dict(cls=cls))

    match_offset = v3_match_offset_get(cls)
    if match_offset >= 0:
        # Init length field for match object
        out.write("""
    /* Initialize match TLV for 1.2 */
    /* FIXME: Check 1.3 below */
    if ((version == OF_VERSION_1_2) || (version == OF_VERSION_1_3)) {
        of_object_u16_set((of_object_t *)obj, %(match_offset)d + 2, 4);
    }
""" % dict(match_offset=match_offset))
    out.write("""
    return obj;
}

#if defined(OF_OBJECT_TRACKING)

/*
 * Tracking objects.  Call the new function and then record location
 */

%(cls)s_t *
%(cls)s_new_tracking(of_version_t version,
     const char *file, int line)
{
    %(cls)s_t *obj;

    obj = %(cls)s_new_(version);
    of_object_track((of_object_t *)obj, file, line);

    return obj;
}
#endif
""" % dict(cls=cls))


def gen_from_message_fn_body(cls, out):
    """
    Generate function body for from_message function
    @param cls The class name for the function
    @param out The file to which to write
    """
    out.write("""
/**
 * Create a new %(cls)s object and bind it to an existing message
 *
 * @param msg The message to bind the new object to
 * @return Pointer to the newly create object or NULL on error
 *
 * \ingroup %(cls)s
 */

%(cls)s_t *
%(cls)s_new_from_message_(of_message_t msg)
{
    %(cls)s_t *obj = NULL;
    of_version_t version;
    int length;

    if (msg == NULL) return NULL;

    version = of_message_version_get(msg);
    if (!OF_VERSION_OKAY(version)) return NULL;

    length = of_message_length_get(msg);

    if ((obj = (%(cls)s_t *)of_object_new(-1)) == NULL) {
        return NULL;
    }

    %(cls)s_init(obj, version, 0, 0);

    if ((of_object_buffer_bind((of_object_t *)obj, OF_MESSAGE_TO_BUFFER(msg),
                               length, OF_MESSAGE_FREE_FUNCTION)) < 0) {
       FREE(obj);
       return NULL;
    }
    obj->length = length;
    obj->version = version;

    return obj;
}

#if defined(OF_OBJECT_TRACKING)

/*
 * Tracking objects.  Call the new function and then record location
 */

%(cls)s_t *
%(cls)s_new_from_message_tracking(of_message_t msg,
    const char *file, int line)
{
    %(cls)s_t *obj;

    obj = %(cls)s_new_from_message_(msg);
    of_object_track((of_object_t *)obj, file, line);

    return obj;
}
#endif
""" % dict(cls=cls))


################################################################
# Now the top level generator functions
################################################################

def gen_new_function_declarations(out):
    """
    Gerenate the header file declarations for new operators for all classes
    @param out The file to which to write the decs
    """

    out.write("""
/****************************************************************
 *
 * New operator declarations
 *
 * _new: Create a new object for writing; includes init
 * _new_from_message: Create a new instance of the object and bind the
 *    message data to the object
 * _init: Initialize and optionally allocate buffer space for an
 *    automatic instance
 *
 * _new and _from_message require a delete operation to be called
 * on the object.
 *
 ****************************************************************/
""")
    out.write("""
/*
 * If object tracking is enabled, map "new" and "new from msg"
 * calls to tracking versions; otherwise, directly to internal
 * versions of fns which have the same name but end in _.
 */

#if defined(OF_OBJECT_TRACKING)
""")
    for cls in of_g.standard_class_order:
        out.write("""
extern %(cls)s_t *
    %(cls)s_new_tracking(of_version_t version,
        const char *file, int line);
#define %(cls)s_new(version) \\
    %(cls)s_new_tracking(version, \\
        __FILE__, __LINE__)
""" % dict(cls=cls))
        if loxi_utils.class_is_message(cls):
            out.write("""extern %(cls)s_t *
    %(cls)s_new_from_message_tracking(of_message_t msg,
        const char *file, int line);
#define %(cls)s_new_from_message(msg) \\
    %(cls)s_new_from_message_tracking(msg, \\
        __FILE__, __LINE__)
""" % dict(cls=cls))

    out.write("""
#else /* No object tracking */
""")
    for cls in of_g.standard_class_order:
        out.write("""
#define %(cls)s_new(version) \\
    %(cls)s_new_(version)
""" % dict(cls=cls))
        if loxi_utils.class_is_message(cls):
            out.write("""#define %(cls)s_new_from_message(msg) \\
    %(cls)s_new_from_message_(msg)
""" % dict(cls=cls))

    out.write("""
#endif /* Object tracking */
""")

    for cls in of_g.standard_class_order:
        out.write("""
extern %(cls)s_t *
    %(cls)s_new_(of_version_t version);
""" % dict(cls=cls))
        if loxi_utils.class_is_message(cls):
            out.write("""extern %(cls)s_t *
    %(cls)s_new_from_message_(of_message_t msg);
""" % dict(cls=cls))
        out.write("""extern void %(cls)s_init(
    %(cls)s_t *obj, of_version_t version, int bytes, int clean_wire);
""" % dict(cls=cls))

    out.write("""
/****************************************************************
 *
 * Delete operator static inline definitions.
 * These are here for type checking purposes only
 *
 ****************************************************************/
""")
    for cls in of_g.standard_class_order:
#        if cls in type_maps.inheritance_map:
#            continue
        out.write("""
/**
 * Delete an object of type %(cls)s_t
 * @param obj An instance of type %(cls)s_t
 *
 * \ingroup %(cls)s
 */
static inline void
%(cls)s_delete(%(cls)s_t *obj) {
    of_object_delete((of_object_t *)(obj));
}
""" % dict(cls=cls))

    out.write("""
typedef void (*of_object_init_f)(of_object_t *obj, of_version_t version,
    int bytes, int clean_wire);
extern const of_object_init_f of_object_init_map[];
""")

    out.write("""
/****************************************************************
 *
 * Function pointer initialization functions
 * These are part of the "coerce" type casting for objects
 *
 ****************************************************************/
""")

#
# @fixme Not clear that these should all be set for virtual fns
#
# @fixme Clean up.  should have a (language specific) map from class
# to length and type get/set functions
#

def gen_coerce_ops(out, cls):
    out.write("""
    /* Set up the object's function pointers */
""")

    if loxi_utils.class_is_message(cls):
        out.write("""
    obj->wire_length_get = of_object_message_wire_length_get;
    obj->wire_length_set = of_object_message_wire_length_set;
""")
    else:
        if loxi_utils.class_is_tlv16(cls):
            if not (cls in type_maps.inheritance_map): # Don't set for super
                out.write("""
    obj->wire_length_set = of_tlv16_wire_length_set;
    obj->wire_type_set = of_tlv16_wire_object_id_set;\
""")
            out.write("""
    obj->wire_length_get = of_tlv16_wire_length_get;
""")
            if loxi_utils.class_is_action(cls):
                out.write("""
    obj->wire_type_get = of_action_wire_object_id_get;
""")
            if loxi_utils.class_is_action_id(cls):
                out.write("""
    obj->wire_type_get = of_action_id_wire_object_id_get;
""")
            if loxi_utils.class_is_instruction(cls):
                out.write("""
    obj->wire_type_get = of_instruction_wire_object_id_get;
""")
            if loxi_utils.class_is_queue_prop(cls):
                    out.write("""
    obj->wire_type_get = of_queue_prop_wire_object_id_get;
""")
            if loxi_utils.class_is_table_feature_prop(cls):
                    out.write("""
    obj->wire_type_get = of_table_feature_prop_wire_object_id_get;
""")
            if loxi_utils.class_is_meter_band(cls):
                    out.write("""
    obj->wire_type_get = of_meter_band_wire_object_id_get;
""")
            if loxi_utils.class_is_hello_elem(cls):
                    out.write("""
    obj->wire_type_get = of_hello_elem_wire_object_id_get;
""")
        if loxi_utils.class_is_oxm(cls):
            out.write("""
    obj->wire_length_get = of_oxm_wire_length_get;
    obj->wire_length_set = of_oxm_wire_length_set;
    obj->wire_type_get = of_oxm_wire_object_id_get;
    obj->wire_type_set = of_oxm_wire_object_id_set;
""")
        if loxi_utils.class_is_u16_len(cls):
            out.write("""
    obj->wire_length_get = of_u16_len_wire_length_get;
    obj->wire_length_set = of_u16_len_wire_length_set;
""")
        if cls == "of_packet_queue":
            out.write("""
    obj->wire_length_get = of_packet_queue_wire_length_get;
    obj->wire_length_set = of_packet_queue_wire_length_set;
""")
#        if cls == "of_list_meter_band_stats":
#            out.write("""
#    obj->wire_length_get = of_list_meter_band_stats_wire_length_get;
#""")
        if cls == "of_meter_stats":
            out.write("""
    obj->wire_length_get = of_meter_stats_wire_length_get;
    obj->wire_length_set = of_meter_stats_wire_length_set;
""")

    if config_check("gen_fn_ptrs"):
        if loxi_utils.class_is_list(cls):
            out.write("""
    obj->first = %(cls)s_first;
    obj->next = %(cls)s_next;
    obj->append = %(cls)s_append;
    obj->append_bind = %(cls)s_append_bind;
""" % dict(cls=cls))
        else:
            instantiate_fn_ptrs(cls, 4, out)

def gen_new_function_definitions(out):
    """
    Generate the new operator for all classes

    @param out The file to which to write the functions
    """

    out.write("\n/* New operators for each message class */\n")
    for cls in of_g.standard_class_order:
        out.write("\n/* New operators for %s */\n" % cls)
        gen_new_fn_body(cls, out)
        gen_init_fn_body(cls, out)
        if loxi_utils.class_is_message(cls):
            gen_from_message_fn_body(cls, out)

def gen_init_map(out):
    """
    Generate map from object ID to type coerce function
    """
    out.write("""
/**
 * Map from object ID to type coerce function
 */
const of_object_init_f of_object_init_map[] = {
    (of_object_init_f)NULL,
""")
    count = 1
    for i, cls in enumerate(of_g.standard_class_order):
        if count != of_g.unified[cls]["object_id"]:
            print "Error in class mapping: object IDs not sequential"
            print cls, count, of_g.unified[cls]["object_id"]
            sys.exit(1)
        s = "(of_object_init_f)%s_init" % cls
        if cls in type_maps.inheritance_map:
            s = "(of_object_init_f)%s_header_init" % cls
        if i < len(of_g.standard_class_order) - 1:
            s += ","
        out.write("    %-65s /* %d */\n" % (s, count))
        count += 1
    out.write("};\n")

"""
Document generation functions

The main reason this is here is to generate documentation per
accessor that indicates the versions that support the interface.
"""


def gen_accessor_doc(out, name):
    """
    Generate documentation for each accessor function that indicates
    the versions supporting the accessor.
    """

    common_top_matter(out, name)

    out.write("/* DOCUMENTATION ONLY */\n")

    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            pass # Check this

        out.write("""
/**
 * Structure for %(cls)s object.  Get/set 
 * accessors available in all versions unless noted otherwise
 *
""" % dict(cls=cls))
        if loxi_utils.class_is_list(cls):
            out.write("""\
 * @param first Function of type %(cls)s_first_f.
 * Setup a TBD class object to the first entry in the list
 * @param next Function of type %(cls)s_next_f.
 * Advance a TBD class object to the next entry in the list
 * @param append_bind Function of type %(cls)s_append_bind_f
 * Setup a TBD class object for append to the end of the current list
 * @param append  Function of type @ref %(cls)s_append_f.
 * Copy an item to the end of a list
""" % dict(cls=cls))

        for m_name in of_g.ordered_members[cls]:
            if m_name in of_g.skip_members:
                continue
            ver_type_map = field_ver_get(cls, m_name)
            (m_type, get_rv) = get_acc_rv(cls, m_name)
            if len(ver_type_map) == 3:
                # ver_string = "Available in all versions"
                ver_string = ""
            else:
                ver_string = "("
                for ver in sorted(ver_type_map):
                    ver_string += " " + of_g.short_version_names[ver]
                ver_string += ")."

            f_name = acc_name(cls, m_name)
            out.write("""\
 * @param %(m_name)s_get/set %(ver_string)s
 *   Accessors for %(m_name)s, a variable of type %(m_type)s.  Functions
 *   are of type %(f_name)s_get_f and _set_f.
 *
""" % dict(f_name=f_name, m_name=m_name, ver_string=ver_string, m_type=m_type))

        out.write("""\
 */
typedef struct %(cls)s_s %(cls)s_t;
""" % dict(cls=cls))

    out.write("#endif /* _LOCI_DOC_H_ */\n")

################################################################
#
# For fun, here are some unified, traditional C structure representation
#
################################################################

def gen_cof_to_wire(out):
    pass

def gen_wire_to_cof(out):
    pass

def gen_cof_instance(out, cls):
    out.write("struct c%s_s {\n" % cls)
    for m in of_g.ordered_members[cls]:
        if m in of_g.skip_members:
            continue
        entry = of_g.unified[cls]["union"][m]
        cof_type = type_to_cof_type(entry["m_type"])
        out.write("    %-20s %s;\n" % (cof_type, m))
    out.write("};\n\n");

def gen_cof_structs(out):
    """
    Generate non-version specific (common) representation of structures

    @param out The file to which to write the functions
    """

    out.write("\n/* Common, unified OpenFlow structure representations */\n")
    for cls in of_g.standard_class_order:
        if cls in type_maps.inheritance_map:
            continue
        gen_cof_instance(out, cls)

################################################################
#
# Generate code samples for applications.
#
################################################################

def gen_code_samples(out, name):
    out.write("""
#if 0 /* Do not compile in */
/**
 * @file %(name)s
 *
 * These are code samples for inclusion in other components
 */

""" % dict(name=name))

    gen_jump_table_template(out)
    # These are messages that a switch might expect.
    msg_list = ["of_echo_request",
                "of_hello",
                "of_packet_in",
                "of_packet_out",
                "of_port_mod",
                "of_port_stats_request",
                "of_queue_get_config_request",
                "of_queue_stats_request",
                "of_flow_add",
                "of_flow_modify",
                "of_flow_modify_strict",
                "of_flow_delete",
                "of_flow_delete_strict",
                "of_get_config_request",
                "of_flow_stats_request",
                "of_barrier_request",
                "of_echo_reply",
                "of_aggregate_stats_request",
                "of_desc_stats_request",
                "of_table_stats_request",
                "of_features_request",
                "of_table_mod",
                "of_set_config",
                "of_experimenter",
                "of_experimenter_stats_request",
                "of_group_desc_stats_request",
                "of_group_features_stats_request",
                "of_role_request"]

    gen_message_handler_templates(out, msgs=msg_list)

    out.write("""
#endif
""")

def gen_jump_table_template(out=sys.stdout, all_unhandled=True,
                            cxn_type="ls_cxn_handle_t", 
                            unhandled="unhandled_message"):
    """
    Generate a template for a jump table.
    @param out The file to which to write the functions
    """
    out.write("""
/*
 * Simple jump table definition for message handling
 */
typedef int (*msg_handler_f)(%(cxn_type)s cxn, of_object_t *obj);
typedef msg_handler_f msg_jump_table_t[OF_MESSAGE_OBJECT_COUNT];

/* Jump table template for message objects */
extern msg_jump_table_t jump_table;

/* C-code template */
msg_jump_table_t jump_table = {
    %(unhandled)s, /* OF_OBJECT; place holder for generic object  */
""" % dict(unhandled=unhandled, cxn_type=cxn_type))
    count = 0
    fn_name = unhandled
    for cls in of_g.ordered_messages:
        comma = ","
        count += 1
        if count == len(of_g.ordered_messages):
            comma = " "
        if not all_unhandled:
            fn_name = "%s_handler" % cls[3:]
        out.write("    %s%s /* %s */\n" % (fn_name, comma, enum_name(cls)))
            
    out.write("};\n")

def gen_message_switch_stmt_tmeplate(out=sys.stdout, all_unhandled=True,
                                     cxn_type="ls_cxn_handle_t", 
                                     unhandled="unhandled_message"):
    out.write("""
/*
 * Simple switch statement for message handling
 */

    switch (obj->object_id):
""")
    fn_name = unhandled
    for cls in of_g.ordered_messages:
        if not all_unhandled:
            fn_name = "%s_handler" % cls[3:]
        out.write("""
    case %(enum)s:
        rv = %(fn_name)s(cxn, obj);
        break;
""" % dict(fn_name=fn_name, cls=cls, enum=enum_name(cls)))
    out.write("""
    default:
        rv = LS_ERROR_PARAM;
        break;
    }

    TRACE("Handled msg %p with rv %d (%s)", obj, rv, ls_error_strings[rv]);

    return rv;
""")


def gen_message_handler_templates(out=sys.stdout, cxn_type="ls_cxn_handle_t",
                                  unhandled="unhandled_message", msgs=None):
    gen_jump_table_template(out, False, cxn_type)
    out.write("""
/**
 * Function for unhandled message
 */
static int
unhandled_message(%(cxn_type)s cxn, of_object_t *obj)
{
    (void)cxn;
    (void)obj;
    TRACE("Unhandled message %%p.  Object id %%d", obj, obj->object_id);

    return LS_ERROR_UNAVAIL;
}
""" % dict(unhandled=unhandled, cxn_type=cxn_type))

    if not msgs:
        msgs = of_g.ordered_messages
    for cls in msgs:
        out.write("""
/**
 * Handle a %(s_cls)s message
 * @param cxn Connection handler for the owning connection
 * @param _obj Generic type object for the message to be coerced
 * @returns Error code
 */

static int
%(s_cls)s_handler(%(cxn_type)s cxn, of_object_t *_obj)
{
    %(cls)s_t *obj;

    TRACE("Handling %(cls)s message: %%p.", obj);
    obj = (%(cls)s_t *)_obj;

    /* Handle object of type %(cls)s_t */

    return LS_ERROR_NONE;
}
""" % dict(s_cls=cls[3:], cls=cls, cxn_type=cxn_type))
    gen_message_switch_stmt_tmeplate(out, False, cxn_type)

def gen_setup_from_add_fns(out):
    """
    Generate functions that setup up objects based on an add

    Okay, this is getting out of hand.  We need to refactor the code
    so that this can be done without so much pain.
    """
    out.write("""

/* Flow stats entry setup for all versions */

static int
flow_stats_entry_setup_from_flow_add_common(of_flow_stats_entry_t *obj,
                                            of_flow_add_t *flow_add,
                                            of_object_t *effects,
                                            int entry_match_offset,
                                            int add_match_offset)
{
    of_list_action_t actions;
    int entry_len, add_len;
    of_wire_buffer_t *wbuf;
    int abs_offset;
    int delta;
    uint16_t val16;
    uint64_t cookie;
    of_octets_t match_octets;

    /* Effects may come from different places */
    if (effects != NULL) {
        OF_TRY(of_flow_stats_entry_actions_set(obj,
               (of_list_action_t *)effects));
    } else {
        of_flow_add_actions_bind(flow_add, &actions);
        OF_TRY(of_flow_stats_entry_actions_set(obj, &actions));
    }

    /* Transfer the match underlying object from add to stats entry */
    wbuf = OF_OBJECT_TO_WBUF(obj);
    entry_len = _WIRE_MATCH_PADDED_LEN(obj, entry_match_offset);
    add_len = _WIRE_MATCH_PADDED_LEN(flow_add, add_match_offset);

    match_octets.bytes = add_len;
    match_octets.data = OF_OBJECT_BUFFER_INDEX(flow_add, add_match_offset);

    /* Copy data into flow entry */
    abs_offset = OF_OBJECT_ABSOLUTE_OFFSET(obj, entry_match_offset);
    of_wire_buffer_replace_data(wbuf, abs_offset, entry_len,
                                match_octets.data, add_len);

    /* Not scalar, update lengths if needed */
    delta = add_len - entry_len;
    if (delta != 0) {
        /* Update parent(s) */
        of_object_parent_length_update((of_object_t *)obj, delta);
    }

    of_flow_add_cookie_get(flow_add, &cookie);
    of_flow_stats_entry_cookie_set(obj, cookie);

    of_flow_add_priority_get(flow_add, &val16);
    of_flow_stats_entry_priority_set(obj, val16);

    of_flow_add_idle_timeout_get(flow_add, &val16);
    of_flow_stats_entry_idle_timeout_set(obj, val16);

    of_flow_add_hard_timeout_get(flow_add, &val16);
    of_flow_stats_entry_hard_timeout_set(obj, val16);

    return OF_ERROR_NONE;
}

/* Flow removed setup for all versions */

static int
flow_removed_setup_from_flow_add_common(of_flow_removed_t *obj,
                                        of_flow_add_t *flow_add,
                                        int removed_match_offset,
                                        int add_match_offset)
{
    int add_len, removed_len;
    of_wire_buffer_t *wbuf;
    int abs_offset;
    int delta;
    uint16_t val16;
    uint64_t cookie;
    of_octets_t match_octets;

    /* Transfer the match underlying object from add to removed obj */
    wbuf = OF_OBJECT_TO_WBUF(obj);
    removed_len = _WIRE_MATCH_PADDED_LEN(obj, removed_match_offset);
    add_len = _WIRE_MATCH_PADDED_LEN(flow_add, add_match_offset);

    match_octets.bytes = add_len;
    match_octets.data = OF_OBJECT_BUFFER_INDEX(flow_add, add_match_offset);

    /* Copy data into flow removed */
    abs_offset = OF_OBJECT_ABSOLUTE_OFFSET(obj, removed_match_offset);
    of_wire_buffer_replace_data(wbuf, abs_offset, removed_len,
                                match_octets.data, add_len);

    /* Not scalar, update lengths if needed */
    delta = add_len - removed_len;
    if (delta != 0) {
        /* Update parent(s) */
        of_object_parent_length_update((of_object_t *)obj, delta);
    }

    of_flow_add_cookie_get(flow_add, &cookie);
    of_flow_removed_cookie_set(obj, cookie);

    of_flow_add_priority_get(flow_add, &val16);
    of_flow_removed_priority_set(obj, val16);

    of_flow_add_idle_timeout_get(flow_add, &val16);
    of_flow_removed_idle_timeout_set(obj, val16);
 
    if (obj->version >= OF_VERSION_1_2) {
        of_flow_add_hard_timeout_get(flow_add, &val16);
        of_flow_removed_hard_timeout_set(obj, val16);
    }

    return OF_ERROR_NONE;
}

/* Set up a flow removed message from the original add */

int
of_flow_removed_setup_from_flow_add(of_flow_removed_t *obj,
                                    of_flow_add_t *flow_add)
{
    switch (obj->version) {
    case OF_VERSION_1_0:
        return flow_removed_setup_from_flow_add_common(obj, flow_add, 
                                                       8, 8);
        break;
    case OF_VERSION_1_1:
    case OF_VERSION_1_2:
    case OF_VERSION_1_3:
        return flow_removed_setup_from_flow_add_common(obj, flow_add, 
                                                       48, 48);
        break;
    default:
        return OF_ERROR_VERSION;
        break;
    }

    return OF_ERROR_NONE;
}


/* Set up a packet in message from the original add */

int
of_packet_in_setup_from_flow_add(of_packet_in_t *obj,
                                 of_flow_add_t *flow_add)
{
    int add_len, pkt_in_len;
    of_wire_buffer_t *wbuf;
    int abs_offset;
    int delta;
    const int pkt_in_match_offset = 16;
    const int add_match_offset = 48;
    of_octets_t match_octets;

    if (obj->version < OF_VERSION_1_2) {
        /* Nothing to be done before OF 1.2 */
        return OF_ERROR_NONE;
    }

    /* Transfer match struct from flow add to packet in object */
    wbuf = OF_OBJECT_TO_WBUF(obj);
    pkt_in_len = _WIRE_MATCH_PADDED_LEN(obj, pkt_in_match_offset);
    add_len = _WIRE_MATCH_PADDED_LEN(flow_add, add_match_offset);

    match_octets.bytes = add_len;
    match_octets.data = OF_OBJECT_BUFFER_INDEX(flow_add, add_match_offset);

    /* Copy data into pkt_in msg */
    abs_offset = OF_OBJECT_ABSOLUTE_OFFSET(obj, pkt_in_match_offset);
    of_wire_buffer_replace_data(wbuf, abs_offset, pkt_in_len,
                                match_octets.data, add_len);

    /* Not scalar, update lengths if needed */
    delta = add_len - pkt_in_len;
    if (delta != 0) {
        /* Update parent(s) */
        of_object_parent_length_update((of_object_t *)obj, delta);
    }

    return OF_ERROR_NONE;
}

/* Set up a stats entry from the original add */

int
of_flow_stats_entry_setup_from_flow_add(of_flow_stats_entry_t *obj,
                                        of_flow_add_t *flow_add,
                                        of_object_t *effects)
{
    switch (obj->version) {
    case OF_VERSION_1_0:
        return flow_stats_entry_setup_from_flow_add_common(obj, flow_add,
                                                           effects, 4, 8);
        break;
    case OF_VERSION_1_1:
    case OF_VERSION_1_2:
    case OF_VERSION_1_3:
        return flow_stats_entry_setup_from_flow_add_common(obj, flow_add, 
                                                           effects, 48, 48);
        break;
    default:
        return OF_ERROR_VERSION;
    }

    return OF_ERROR_NONE;
}
""")
