/*
 * Copyright 2018-present Open Networking Foundation
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * 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 License for the specific language governing permissions and
 * limitations under the License.
 */
package flows

import (
	"bytes"
	"crypto/md5"
	"errors"
	"fmt"
	"github.com/cevaris/ordered_map"
	"github.com/gogo/protobuf/proto"
	"github.com/opencord/voltha-lib-go/v3/pkg/log"
	ofp "github.com/opencord/voltha-protos/v3/go/openflow_13"
	"math/big"
	"strings"
)

var (
	// Instructions shortcut
	APPLY_ACTIONS  = ofp.OfpInstructionType_OFPIT_APPLY_ACTIONS
	WRITE_METADATA = ofp.OfpInstructionType_OFPIT_WRITE_METADATA
	METER_ACTION   = ofp.OfpInstructionType_OFPIT_METER

	//OFPAT_* shortcuts
	OUTPUT       = ofp.OfpActionType_OFPAT_OUTPUT
	COPY_TTL_OUT = ofp.OfpActionType_OFPAT_COPY_TTL_OUT
	COPY_TTL_IN  = ofp.OfpActionType_OFPAT_COPY_TTL_IN
	SET_MPLS_TTL = ofp.OfpActionType_OFPAT_SET_MPLS_TTL
	DEC_MPLS_TTL = ofp.OfpActionType_OFPAT_DEC_MPLS_TTL
	PUSH_VLAN    = ofp.OfpActionType_OFPAT_PUSH_VLAN
	POP_VLAN     = ofp.OfpActionType_OFPAT_POP_VLAN
	PUSH_MPLS    = ofp.OfpActionType_OFPAT_PUSH_MPLS
	POP_MPLS     = ofp.OfpActionType_OFPAT_POP_MPLS
	SET_QUEUE    = ofp.OfpActionType_OFPAT_SET_QUEUE
	GROUP        = ofp.OfpActionType_OFPAT_GROUP
	SET_NW_TTL   = ofp.OfpActionType_OFPAT_SET_NW_TTL
	NW_TTL       = ofp.OfpActionType_OFPAT_DEC_NW_TTL
	SET_FIELD    = ofp.OfpActionType_OFPAT_SET_FIELD
	PUSH_PBB     = ofp.OfpActionType_OFPAT_PUSH_PBB
	POP_PBB      = ofp.OfpActionType_OFPAT_POP_PBB
	EXPERIMENTER = ofp.OfpActionType_OFPAT_EXPERIMENTER

	//OFPXMT_OFB_* shortcuts (incomplete)
	IN_PORT         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IN_PORT
	IN_PHY_PORT     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IN_PHY_PORT
	METADATA        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_METADATA
	ETH_DST         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ETH_DST
	ETH_SRC         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ETH_SRC
	ETH_TYPE        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ETH_TYPE
	VLAN_VID        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_VID
	VLAN_PCP        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_VLAN_PCP
	IP_DSCP         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IP_DSCP
	IP_ECN          = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IP_ECN
	IP_PROTO        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IP_PROTO
	IPV4_SRC        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV4_SRC
	IPV4_DST        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV4_DST
	TCP_SRC         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_TCP_SRC
	TCP_DST         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_TCP_DST
	UDP_SRC         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_UDP_SRC
	UDP_DST         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_UDP_DST
	SCTP_SRC        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_SCTP_SRC
	SCTP_DST        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_SCTP_DST
	ICMPV4_TYPE     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ICMPV4_TYPE
	ICMPV4_CODE     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ICMPV4_CODE
	ARP_OP          = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ARP_OP
	ARP_SPA         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ARP_SPA
	ARP_TPA         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ARP_TPA
	ARP_SHA         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ARP_SHA
	ARP_THA         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ARP_THA
	IPV6_SRC        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_SRC
	IPV6_DST        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_DST
	IPV6_FLABEL     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_FLABEL
	ICMPV6_TYPE     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ICMPV6_TYPE
	ICMPV6_CODE     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_ICMPV6_CODE
	IPV6_ND_TARGET  = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_ND_TARGET
	OFB_IPV6_ND_SLL = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_ND_SLL
	IPV6_ND_TLL     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_ND_TLL
	MPLS_LABEL      = ofp.OxmOfbFieldTypes_OFPXMT_OFB_MPLS_LABEL
	MPLS_TC         = ofp.OxmOfbFieldTypes_OFPXMT_OFB_MPLS_TC
	MPLS_BOS        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_MPLS_BOS
	PBB_ISID        = ofp.OxmOfbFieldTypes_OFPXMT_OFB_PBB_ISID
	TUNNEL_ID       = ofp.OxmOfbFieldTypes_OFPXMT_OFB_TUNNEL_ID
	IPV6_EXTHDR     = ofp.OxmOfbFieldTypes_OFPXMT_OFB_IPV6_EXTHDR
)

//ofp_action_* shortcuts

func Output(port uint32, maxLen ...ofp.OfpControllerMaxLen) *ofp.OfpAction {
	maxLength := ofp.OfpControllerMaxLen_OFPCML_MAX
	if len(maxLen) > 0 {
		maxLength = maxLen[0]
	}
	return &ofp.OfpAction{Type: OUTPUT, Action: &ofp.OfpAction_Output{Output: &ofp.OfpActionOutput{Port: port, MaxLen: uint32(maxLength)}}}
}

func MplsTtl(ttl uint32) *ofp.OfpAction {
	return &ofp.OfpAction{Type: SET_MPLS_TTL, Action: &ofp.OfpAction_MplsTtl{MplsTtl: &ofp.OfpActionMplsTtl{MplsTtl: ttl}}}
}

func PushVlan(ethType uint32) *ofp.OfpAction {
	return &ofp.OfpAction{Type: PUSH_VLAN, Action: &ofp.OfpAction_Push{Push: &ofp.OfpActionPush{Ethertype: ethType}}}
}

func PopVlan() *ofp.OfpAction {
	return &ofp.OfpAction{Type: POP_VLAN}
}

func PopMpls(ethType uint32) *ofp.OfpAction {
	return &ofp.OfpAction{Type: POP_MPLS, Action: &ofp.OfpAction_PopMpls{PopMpls: &ofp.OfpActionPopMpls{Ethertype: ethType}}}
}

func Group(groupId uint32) *ofp.OfpAction {
	return &ofp.OfpAction{Type: GROUP, Action: &ofp.OfpAction_Group{Group: &ofp.OfpActionGroup{GroupId: groupId}}}
}

func NwTtl(nwTtl uint32) *ofp.OfpAction {
	return &ofp.OfpAction{Type: NW_TTL, Action: &ofp.OfpAction_NwTtl{NwTtl: &ofp.OfpActionNwTtl{NwTtl: nwTtl}}}
}

func SetField(field *ofp.OfpOxmOfbField) *ofp.OfpAction {
	actionSetField := &ofp.OfpOxmField{OxmClass: ofp.OfpOxmClass_OFPXMC_OPENFLOW_BASIC, Field: &ofp.OfpOxmField_OfbField{OfbField: field}}
	return &ofp.OfpAction{Type: SET_FIELD, Action: &ofp.OfpAction_SetField{SetField: &ofp.OfpActionSetField{Field: actionSetField}}}
}

func Experimenter(experimenter uint32, data []byte) *ofp.OfpAction {
	return &ofp.OfpAction{Type: EXPERIMENTER, Action: &ofp.OfpAction_Experimenter{Experimenter: &ofp.OfpActionExperimenter{Experimenter: experimenter, Data: data}}}
}

//ofb_field generators (incomplete set)

func InPort(inPort uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IN_PORT, Value: &ofp.OfpOxmOfbField_Port{Port: inPort}}
}

func InPhyPort(inPhyPort uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IN_PHY_PORT, Value: &ofp.OfpOxmOfbField_Port{Port: inPhyPort}}
}

func Metadata_ofp(tableMetadata uint64) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: METADATA, Value: &ofp.OfpOxmOfbField_TableMetadata{TableMetadata: tableMetadata}}
}

// should Metadata_ofp used here ?????
func EthDst(ethDst uint64) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ETH_DST, Value: &ofp.OfpOxmOfbField_TableMetadata{TableMetadata: ethDst}}
}

// should Metadata_ofp used here ?????
func EthSrc(ethSrc uint64) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ETH_SRC, Value: &ofp.OfpOxmOfbField_TableMetadata{TableMetadata: ethSrc}}
}

func EthType(ethType uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ETH_TYPE, Value: &ofp.OfpOxmOfbField_EthType{EthType: ethType}}
}

func VlanVid(vlanVid uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: VLAN_VID, Value: &ofp.OfpOxmOfbField_VlanVid{VlanVid: vlanVid}}
}

func VlanPcp(vlanPcp uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: VLAN_PCP, Value: &ofp.OfpOxmOfbField_VlanPcp{VlanPcp: vlanPcp}}
}

func IpDscp(ipDscp uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IP_DSCP, Value: &ofp.OfpOxmOfbField_IpDscp{IpDscp: ipDscp}}
}

func IpEcn(ipEcn uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IP_ECN, Value: &ofp.OfpOxmOfbField_IpEcn{IpEcn: ipEcn}}
}

func IpProto(ipProto uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IP_PROTO, Value: &ofp.OfpOxmOfbField_IpProto{IpProto: ipProto}}
}

func Ipv4Src(ipv4Src uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV4_SRC, Value: &ofp.OfpOxmOfbField_Ipv4Src{Ipv4Src: ipv4Src}}
}

func Ipv4Dst(ipv4Dst uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV4_DST, Value: &ofp.OfpOxmOfbField_Ipv4Dst{Ipv4Dst: ipv4Dst}}
}

func TcpSrc(tcpSrc uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: TCP_SRC, Value: &ofp.OfpOxmOfbField_TcpSrc{TcpSrc: tcpSrc}}
}

func TcpDst(tcpDst uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: TCP_DST, Value: &ofp.OfpOxmOfbField_TcpDst{TcpDst: tcpDst}}
}

func UdpSrc(udpSrc uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: UDP_SRC, Value: &ofp.OfpOxmOfbField_UdpSrc{UdpSrc: udpSrc}}
}

func UdpDst(udpDst uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: UDP_DST, Value: &ofp.OfpOxmOfbField_UdpDst{UdpDst: udpDst}}
}

func SctpSrc(sctpSrc uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: SCTP_SRC, Value: &ofp.OfpOxmOfbField_SctpSrc{SctpSrc: sctpSrc}}
}

func SctpDst(sctpDst uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: SCTP_DST, Value: &ofp.OfpOxmOfbField_SctpDst{SctpDst: sctpDst}}
}

func Icmpv4Type(icmpv4Type uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ICMPV4_TYPE, Value: &ofp.OfpOxmOfbField_Icmpv4Type{Icmpv4Type: icmpv4Type}}
}

func Icmpv4Code(icmpv4Code uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ICMPV4_CODE, Value: &ofp.OfpOxmOfbField_Icmpv4Code{Icmpv4Code: icmpv4Code}}
}

func ArpOp(arpOp uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ARP_OP, Value: &ofp.OfpOxmOfbField_ArpOp{ArpOp: arpOp}}
}

func ArpSpa(arpSpa uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ARP_SPA, Value: &ofp.OfpOxmOfbField_ArpSpa{ArpSpa: arpSpa}}
}

func ArpTpa(arpTpa uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ARP_TPA, Value: &ofp.OfpOxmOfbField_ArpTpa{ArpTpa: arpTpa}}
}

func ArpSha(arpSha []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ARP_SHA, Value: &ofp.OfpOxmOfbField_ArpSha{ArpSha: arpSha}}
}

func ArpTha(arpTha []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ARP_THA, Value: &ofp.OfpOxmOfbField_ArpTha{ArpTha: arpTha}}
}

func Ipv6Src(ipv6Src []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_SRC, Value: &ofp.OfpOxmOfbField_Ipv6Src{Ipv6Src: ipv6Src}}
}

func Ipv6Dst(ipv6Dst []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_DST, Value: &ofp.OfpOxmOfbField_Ipv6Dst{Ipv6Dst: ipv6Dst}}
}

func Ipv6Flabel(ipv6Flabel uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_FLABEL, Value: &ofp.OfpOxmOfbField_Ipv6Flabel{Ipv6Flabel: ipv6Flabel}}
}

func Icmpv6Type(icmpv6Type uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ICMPV6_TYPE, Value: &ofp.OfpOxmOfbField_Icmpv6Type{Icmpv6Type: icmpv6Type}}
}

func Icmpv6Code(icmpv6Code uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: ICMPV6_CODE, Value: &ofp.OfpOxmOfbField_Icmpv6Code{Icmpv6Code: icmpv6Code}}
}

func Ipv6NdTarget(ipv6NdTarget []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_ND_TARGET, Value: &ofp.OfpOxmOfbField_Ipv6NdTarget{Ipv6NdTarget: ipv6NdTarget}}
}

func OfbIpv6NdSll(ofbIpv6NdSll []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: OFB_IPV6_ND_SLL, Value: &ofp.OfpOxmOfbField_Ipv6NdSsl{Ipv6NdSsl: ofbIpv6NdSll}}
}

func Ipv6NdTll(ipv6NdTll []byte) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_ND_TLL, Value: &ofp.OfpOxmOfbField_Ipv6NdTll{Ipv6NdTll: ipv6NdTll}}
}

func MplsLabel(mplsLabel uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: MPLS_LABEL, Value: &ofp.OfpOxmOfbField_MplsLabel{MplsLabel: mplsLabel}}
}

func MplsTc(mplsTc uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: MPLS_TC, Value: &ofp.OfpOxmOfbField_MplsTc{MplsTc: mplsTc}}
}

func MplsBos(mplsBos uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: MPLS_BOS, Value: &ofp.OfpOxmOfbField_MplsBos{MplsBos: mplsBos}}
}

func PbbIsid(pbbIsid uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: PBB_ISID, Value: &ofp.OfpOxmOfbField_PbbIsid{PbbIsid: pbbIsid}}
}

func TunnelId(tunnelId uint64) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: TUNNEL_ID, Value: &ofp.OfpOxmOfbField_TunnelId{TunnelId: tunnelId}}
}

func Ipv6Exthdr(ipv6Exthdr uint32) *ofp.OfpOxmOfbField {
	return &ofp.OfpOxmOfbField{Type: IPV6_EXTHDR, Value: &ofp.OfpOxmOfbField_Ipv6Exthdr{Ipv6Exthdr: ipv6Exthdr}}
}

//frequently used extractors

func excludeAction(action *ofp.OfpAction, exclude ...ofp.OfpActionType) bool {
	for _, actionToExclude := range exclude {
		if action.Type == actionToExclude {
			return true
		}
	}
	return false
}

func GetActions(flow *ofp.OfpFlowStats, exclude ...ofp.OfpActionType) []*ofp.OfpAction {
	if flow == nil {
		return nil
	}
	for _, instruction := range flow.Instructions {
		if instruction.Type == uint32(ofp.OfpInstructionType_OFPIT_APPLY_ACTIONS) {
			instActions := instruction.GetActions()
			if instActions == nil {
				return nil
			}
			if len(exclude) == 0 {
				return instActions.Actions
			} else {
				filteredAction := make([]*ofp.OfpAction, 0)
				for _, action := range instActions.Actions {
					if !excludeAction(action, exclude...) {
						filteredAction = append(filteredAction, action)
					}
				}
				return filteredAction
			}
		}
	}
	return nil
}

func UpdateOutputPortByActionType(flow *ofp.OfpFlowStats, actionType uint32, toPort uint32) *ofp.OfpFlowStats {
	if flow == nil {
		return nil
	}
	nFlow := (proto.Clone(flow)).(*ofp.OfpFlowStats)
	nFlow.Instructions = nil
	nInsts := make([]*ofp.OfpInstruction, 0)
	for _, instruction := range flow.Instructions {
		if instruction.Type == actionType {
			instActions := instruction.GetActions()
			if instActions == nil {
				return nil
			}
			nActions := make([]*ofp.OfpAction, 0)
			for _, action := range instActions.Actions {
				if action.GetOutput() != nil {
					nActions = append(nActions, Output(toPort))
				} else {
					nActions = append(nActions, action)
				}
			}
			instructionAction := ofp.OfpInstruction_Actions{Actions: &ofp.OfpInstructionActions{Actions: nActions}}
			nInsts = append(nInsts, &ofp.OfpInstruction{Type: uint32(APPLY_ACTIONS), Data: &instructionAction})
		} else {
			nInsts = append(nInsts, instruction)
		}
	}
	nFlow.Instructions = nInsts
	return nFlow
}

func excludeOxmOfbField(field *ofp.OfpOxmOfbField, exclude ...ofp.OxmOfbFieldTypes) bool {
	for _, fieldToExclude := range exclude {
		if field.Type == fieldToExclude {
			return true
		}
	}
	return false
}

func GetOfbFields(flow *ofp.OfpFlowStats, exclude ...ofp.OxmOfbFieldTypes) []*ofp.OfpOxmOfbField {
	if flow == nil || flow.Match == nil || flow.Match.Type != ofp.OfpMatchType_OFPMT_OXM {
		return nil
	}
	ofbFields := make([]*ofp.OfpOxmOfbField, 0)
	for _, field := range flow.Match.OxmFields {
		if field.OxmClass == ofp.OfpOxmClass_OFPXMC_OPENFLOW_BASIC {
			ofbFields = append(ofbFields, field.GetOfbField())
		}
	}
	if len(exclude) == 0 {
		return ofbFields
	} else {
		filteredFields := make([]*ofp.OfpOxmOfbField, 0)
		for _, ofbField := range ofbFields {
			if !excludeOxmOfbField(ofbField, exclude...) {
				filteredFields = append(filteredFields, ofbField)
			}
		}
		return filteredFields
	}
}

func GetPacketOutPort(packet *ofp.OfpPacketOut) uint32 {
	if packet == nil {
		return 0
	}
	for _, action := range packet.GetActions() {
		if action.Type == OUTPUT {
			return action.GetOutput().Port
		}
	}
	return 0
}

func GetOutPort(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, action := range GetActions(flow) {
		if action.Type == OUTPUT {
			out := action.GetOutput()
			if out == nil {
				return 0
			}
			return out.GetPort()
		}
	}
	return 0
}

func GetInPort(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, field := range GetOfbFields(flow) {
		if field.Type == IN_PORT {
			return field.GetPort()
		}
	}
	return 0
}

func GetGotoTableId(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, instruction := range flow.Instructions {
		if instruction.Type == uint32(ofp.OfpInstructionType_OFPIT_GOTO_TABLE) {
			gotoTable := instruction.GetGotoTable()
			if gotoTable == nil {
				return 0
			}
			return gotoTable.GetTableId()
		}
	}
	return 0
}

func GetMeterId(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, instruction := range flow.Instructions {
		if instruction.Type == uint32(ofp.OfpInstructionType_OFPIT_METER) {
			MeterInstruction := instruction.GetMeter()
			if MeterInstruction == nil {
				return 0
			}
			return MeterInstruction.GetMeterId()
		}
	}
	return 0
}

func GetVlanVid(flow *ofp.OfpFlowStats) *uint32 {
	if flow == nil {
		return nil
	}
	for _, field := range GetOfbFields(flow) {
		if field.Type == VLAN_VID {
			ret := field.GetVlanVid()
			return &ret
		}
	}
	// Dont return 0 if the field is missing as vlan id value 0 has meaning and cannot be overloaded as "not found"
	return nil
}

func GetTunnelId(flow *ofp.OfpFlowStats) uint64 {
	if flow == nil {
		return 0
	}
	for _, field := range GetOfbFields(flow) {
		if field.Type == TUNNEL_ID {
			return field.GetTunnelId()
		}
	}
	return 0
}

//GetMetaData - legacy get method (only want lower 32 bits)
func GetMetaData(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, field := range GetOfbFields(flow) {
		if field.Type == METADATA {
			return uint32(field.GetTableMetadata() & 0xFFFFFFFF)
		}
	}
	logger.Debug("No-metadata-present")
	return 0
}

func GetMetaData64Bit(flow *ofp.OfpFlowStats) uint64 {
	if flow == nil {
		return 0
	}
	for _, field := range GetOfbFields(flow) {
		if field.Type == METADATA {
			return field.GetTableMetadata()
		}
	}
	logger.Debug("No-metadata-present")
	return 0
}

// function returns write metadata value from write_metadata action field
func GetMetadataFromWriteMetadataAction(flow *ofp.OfpFlowStats) uint64 {
	if flow != nil {
		for _, instruction := range flow.Instructions {
			if instruction.Type == uint32(WRITE_METADATA) {
				if writeMetadata := instruction.GetWriteMetadata(); writeMetadata != nil {
					return writeMetadata.GetMetadata()
				}
			}
		}
	}
	logger.Debugw("No-write-metadata-present", log.Fields{"flow": flow})
	return 0
}

func GetTechProfileIDFromWriteMetaData(metadata uint64) uint16 {
	/*
	   Write metadata instruction value (metadata) is 8 bytes:
	   MS 2 bytes: C Tag
	   Next 2 bytes: Technology Profile Id
	   Next 4 bytes: Port number (uni or nni)

	   This is set in the ONOS OltPipeline as a write metadata instruction
	*/
	var tpId uint16 = 0
	logger.Debugw("Write metadata value for Techprofile ID", log.Fields{"metadata": metadata})
	if metadata != 0 {
		tpId = uint16((metadata >> 32) & 0xFFFF)
		logger.Debugw("Found techprofile ID from write metadata action", log.Fields{"tpid": tpId})
	}
	return tpId
}

func GetEgressPortNumberFromWriteMetadata(flow *ofp.OfpFlowStats) uint32 {
	/*
			  Write metadata instruction value (metadata) is 8 bytes:
		    	MS 2 bytes: C Tag
		    	Next 2 bytes: Technology Profile Id
		    	Next 4 bytes: Port number (uni or nni)
		    	This is set in the ONOS OltPipeline as a write metadata instruction
	*/
	var uniPort uint32 = 0
	md := GetMetadataFromWriteMetadataAction(flow)
	logger.Debugw("Metadata found for egress/uni port ", log.Fields{"metadata": md})
	if md != 0 {
		uniPort = uint32(md & 0xFFFFFFFF)
		logger.Debugw("Found EgressPort from write metadata action", log.Fields{"egress_port": uniPort})
	}
	return uniPort

}

func GetInnerTagFromMetaData(flow *ofp.OfpFlowStats) uint16 {
	/*
			  Write metadata instruction value (metadata) is 8 bytes:
		    	MS 2 bytes: C Tag
		    	Next 2 bytes: Technology Profile Id
		    	Next 4 bytes: Port number (uni or nni)
		    	This is set in the ONOS OltPipeline as a write metadata instruction
	*/
	var innerTag uint16 = 0
	md := GetMetadataFromWriteMetadataAction(flow)
	if md != 0 {
		innerTag = uint16((md >> 48) & 0xFFFF)
		logger.Debugw("Found  CVLAN from write metadate action", log.Fields{"c_vlan": innerTag})
	}
	return innerTag
}

//GetInnerTagFromMetaData retrieves the inner tag from the Metadata_ofp. The port number (UNI on ONU) is in the
// lower 32-bits of Metadata_ofp and the inner_tag is in the upper 32-bits. This is set in the ONOS OltPipeline as
//// a Metadata_ofp field
/*func GetInnerTagFromMetaData(flow *ofp.OfpFlowStats) uint64 {
	md := GetMetaData64Bit(flow)
	if md == 0 {
		return 0
	}
	if md <= 0xffffffff {
		logger.Debugw("onos-upgrade-suggested", logger.Fields{"Metadata_ofp": md, "message": "Legacy MetaData detected form OltPipeline"})
		return md
	}
	return (md >> 32) & 0xffffffff
}*/

// Extract the child device port from a flow that contains the parent device peer port.  Typically the UNI port of an
// ONU child device.  Per TST agreement this will be the lower 32 bits of tunnel id reserving upper 32 bits for later
// use
func GetChildPortFromTunnelId(flow *ofp.OfpFlowStats) uint32 {
	tid := GetTunnelId(flow)
	if tid == 0 {
		return 0
	}
	// Per TST agreement we are keeping any child port id (uni port id) in the lower 32 bits
	return uint32(tid & 0xffffffff)
}

func HasNextTable(flow *ofp.OfpFlowStats) bool {
	if flow == nil {
		return false
	}
	return GetGotoTableId(flow) != 0
}

func GetGroup(flow *ofp.OfpFlowStats) uint32 {
	if flow == nil {
		return 0
	}
	for _, action := range GetActions(flow) {
		if action.Type == GROUP {
			grp := action.GetGroup()
			if grp == nil {
				return 0
			}
			return grp.GetGroupId()
		}
	}
	return 0
}

func HasGroup(flow *ofp.OfpFlowStats) bool {
	return GetGroup(flow) != 0
}

// GetNextTableId returns the next table ID if the "table_id" is present in the map, otherwise return nil
func GetNextTableId(kw OfpFlowModArgs) *uint32 {
	if val, exist := kw["table_id"]; exist {
		ret := uint32(val)
		return &ret
	}
	return nil
}

// GetMeterIdFlowModArgs returns the meterId if the "meter_id" is present in the map, otherwise return 0
func GetMeterIdFlowModArgs(kw OfpFlowModArgs) uint32 {
	if val, exist := kw["meter_id"]; exist {
		return uint32(val)
	}
	return 0
}

// Function returns the metadata if the "write_metadata" is present in the map, otherwise return nil
func GetMetadataFlowModArgs(kw OfpFlowModArgs) uint64 {
	if val, exist := kw["write_metadata"]; exist {
		ret := uint64(val)
		return ret
	}
	return 0
}

// Return unique 64-bit integer hash for flow covering the following attributes:
// 'table_id', 'priority', 'flags', 'cookie', 'match', '_instruction_string'
func HashFlowStats(flow *ofp.OfpFlowStats) (uint64, error) {
	if flow == nil { // Should never happen
		return 0, errors.New("hash-flow-stats-nil-flow")
	}
	// Create string with the instructions field first
	var instructionString bytes.Buffer
	for _, instruction := range flow.Instructions {
		instructionString.WriteString(instruction.String())
	}
	var flowString = fmt.Sprintf("%d%d%d%d%s%s", flow.TableId, flow.Priority, flow.Flags, flow.Cookie, flow.Match.String(), instructionString.String())
	h := md5.New()
	if _, err := h.Write([]byte(flowString)); err != nil {
		return 0, fmt.Errorf("hash-flow-stats-failed-hash: %v", err)
	}
	hash := big.NewInt(0)
	hash.SetBytes(h.Sum(nil))
	return hash.Uint64(), nil
}

// flowStatsEntryFromFlowModMessage maps an ofp_flow_mod message to an ofp_flow_stats message
func FlowStatsEntryFromFlowModMessage(mod *ofp.OfpFlowMod) (*ofp.OfpFlowStats, error) {
	flow := &ofp.OfpFlowStats{}
	if mod == nil {
		return flow, nil
	}
	flow.TableId = mod.TableId
	flow.Priority = mod.Priority
	flow.IdleTimeout = mod.IdleTimeout
	flow.HardTimeout = mod.HardTimeout
	flow.Flags = mod.Flags
	flow.Cookie = mod.Cookie
	flow.Match = mod.Match
	flow.Instructions = mod.Instructions
	var err error
	if flow.Id, err = HashFlowStats(flow); err != nil {
		return nil, err
	}

	return flow, nil
}

func GroupEntryFromGroupMod(mod *ofp.OfpGroupMod) *ofp.OfpGroupEntry {
	group := &ofp.OfpGroupEntry{}
	if mod == nil {
		return group
	}
	group.Desc = &ofp.OfpGroupDesc{Type: mod.Type, GroupId: mod.GroupId, Buckets: mod.Buckets}
	group.Stats = &ofp.OfpGroupStats{GroupId: mod.GroupId}
	//TODO do we need to instantiate bucket bins?
	return group
}

// flowStatsEntryFromFlowModMessage maps an ofp_flow_mod message to an ofp_flow_stats message
func MeterEntryFromMeterMod(meterMod *ofp.OfpMeterMod) *ofp.OfpMeterEntry {
	bandStats := make([]*ofp.OfpMeterBandStats, 0)
	meter := &ofp.OfpMeterEntry{Config: &ofp.OfpMeterConfig{},
		Stats: &ofp.OfpMeterStats{BandStats: bandStats}}
	if meterMod == nil {
		logger.Error("Invalid meter mod command")
		return meter
	}
	// config init
	meter.Config.MeterId = meterMod.MeterId
	meter.Config.Flags = meterMod.Flags
	meter.Config.Bands = meterMod.Bands
	// meter stats init
	meter.Stats.MeterId = meterMod.MeterId
	meter.Stats.FlowCount = 0
	meter.Stats.PacketInCount = 0
	meter.Stats.ByteInCount = 0
	meter.Stats.DurationSec = 0
	meter.Stats.DurationNsec = 0
	// band stats init
	for range meterMod.Bands {
		band := &ofp.OfpMeterBandStats{}
		band.PacketBandCount = 0
		band.ByteBandCount = 0
		bandStats = append(bandStats, band)
	}
	meter.Stats.BandStats = bandStats
	logger.Debugw("Allocated meter entry", log.Fields{"meter": *meter})
	return meter

}

func GetMeterIdFromFlow(flow *ofp.OfpFlowStats) uint32 {
	if flow != nil {
		for _, instruction := range flow.Instructions {
			if instruction.Type == uint32(METER_ACTION) {
				if meterInst := instruction.GetMeter(); meterInst != nil {
					return meterInst.GetMeterId()
				}
			}
		}
	}

	return uint32(0)
}

func MkOxmFields(matchFields []ofp.OfpOxmField) []*ofp.OfpOxmField {
	oxmFields := make([]*ofp.OfpOxmField, 0)
	for _, matchField := range matchFields {
		oxmField := ofp.OfpOxmField{OxmClass: ofp.OfpOxmClass_OFPXMC_OPENFLOW_BASIC, Field: matchField.Field}
		oxmFields = append(oxmFields, &oxmField)
	}
	return oxmFields
}

func MkInstructionsFromActions(actions []*ofp.OfpAction) []*ofp.OfpInstruction {
	instructions := make([]*ofp.OfpInstruction, 0)
	instructionAction := ofp.OfpInstruction_Actions{Actions: &ofp.OfpInstructionActions{Actions: actions}}
	instruction := ofp.OfpInstruction{Type: uint32(APPLY_ACTIONS), Data: &instructionAction}
	instructions = append(instructions, &instruction)
	return instructions
}

// Convenience function to generare ofp_flow_mod message with OXM BASIC match composed from the match_fields, and
// single APPLY_ACTIONS instruction with a list if ofp_action objects.
func MkSimpleFlowMod(matchFields []*ofp.OfpOxmField, actions []*ofp.OfpAction, command *ofp.OfpFlowModCommand, kw OfpFlowModArgs) *ofp.OfpFlowMod {

	// Process actions instructions
	instructions := make([]*ofp.OfpInstruction, 0)
	instructionAction := ofp.OfpInstruction_Actions{Actions: &ofp.OfpInstructionActions{Actions: actions}}
	instruction := ofp.OfpInstruction{Type: uint32(APPLY_ACTIONS), Data: &instructionAction}
	instructions = append(instructions, &instruction)

	// Process next table
	if tableId := GetNextTableId(kw); tableId != nil {
		var instGotoTable ofp.OfpInstruction_GotoTable
		instGotoTable.GotoTable = &ofp.OfpInstructionGotoTable{TableId: *tableId}
		inst := ofp.OfpInstruction{Type: uint32(ofp.OfpInstructionType_OFPIT_GOTO_TABLE), Data: &instGotoTable}
		instructions = append(instructions, &inst)
	}
	// Process meter action
	if meterId := GetMeterIdFlowModArgs(kw); meterId != 0 {
		var instMeter ofp.OfpInstruction_Meter
		instMeter.Meter = &ofp.OfpInstructionMeter{MeterId: meterId}
		inst := ofp.OfpInstruction{Type: uint32(METER_ACTION), Data: &instMeter}
		instructions = append(instructions, &inst)
	}
	//process write_metadata action
	if metadata := GetMetadataFlowModArgs(kw); metadata != 0 {
		var instWriteMetadata ofp.OfpInstruction_WriteMetadata
		instWriteMetadata.WriteMetadata = &ofp.OfpInstructionWriteMetadata{Metadata: metadata}
		inst := ofp.OfpInstruction{Type: uint32(WRITE_METADATA), Data: &instWriteMetadata}
		instructions = append(instructions, &inst)
	}

	// Process match fields
	oxmFields := make([]*ofp.OfpOxmField, 0)
	for _, matchField := range matchFields {
		oxmField := ofp.OfpOxmField{OxmClass: ofp.OfpOxmClass_OFPXMC_OPENFLOW_BASIC, Field: matchField.Field}
		oxmFields = append(oxmFields, &oxmField)
	}
	var match ofp.OfpMatch
	match.Type = ofp.OfpMatchType_OFPMT_OXM
	match.OxmFields = oxmFields

	// Create ofp_flow_message
	msg := &ofp.OfpFlowMod{}
	if command == nil {
		msg.Command = ofp.OfpFlowModCommand_OFPFC_ADD
	} else {
		msg.Command = *command
	}
	msg.Instructions = instructions
	msg.Match = &match

	// Set the variadic argument values
	msg = setVariadicModAttributes(msg, kw)

	return msg
}

func MkMulticastGroupMod(groupId uint32, buckets []*ofp.OfpBucket, command *ofp.OfpGroupModCommand) *ofp.OfpGroupMod {
	group := &ofp.OfpGroupMod{}
	if command == nil {
		group.Command = ofp.OfpGroupModCommand_OFPGC_ADD
	} else {
		group.Command = *command
	}
	group.Type = ofp.OfpGroupType_OFPGT_ALL
	group.GroupId = groupId
	group.Buckets = buckets
	return group
}

//SetVariadicModAttributes sets only uint64 or uint32 fields of the ofp_flow_mod message
func setVariadicModAttributes(mod *ofp.OfpFlowMod, args OfpFlowModArgs) *ofp.OfpFlowMod {
	if args == nil {
		return mod
	}
	for key, val := range args {
		switch key {
		case "cookie":
			mod.Cookie = val
		case "cookie_mask":
			mod.CookieMask = val
		case "table_id":
			mod.TableId = uint32(val)
		case "idle_timeout":
			mod.IdleTimeout = uint32(val)
		case "hard_timeout":
			mod.HardTimeout = uint32(val)
		case "priority":
			mod.Priority = uint32(val)
		case "buffer_id":
			mod.BufferId = uint32(val)
		case "out_port":
			mod.OutPort = uint32(val)
		case "out_group":
			mod.OutGroup = uint32(val)
		case "flags":
			mod.Flags = uint32(val)
		}
	}
	return mod
}

func MkPacketIn(port uint32, packet []byte) *ofp.OfpPacketIn {
	packetIn := &ofp.OfpPacketIn{
		Reason: ofp.OfpPacketInReason_OFPR_ACTION,
		Match: &ofp.OfpMatch{
			Type: ofp.OfpMatchType_OFPMT_OXM,
			OxmFields: []*ofp.OfpOxmField{
				{
					OxmClass: ofp.OfpOxmClass_OFPXMC_OPENFLOW_BASIC,
					Field: &ofp.OfpOxmField_OfbField{
						OfbField: InPort(port)},
				},
			},
		},
		Data: packet,
	}
	return packetIn
}

// MkFlowStat is a helper method to build flows
func MkFlowStat(fa *FlowArgs) (*ofp.OfpFlowStats, error) {
	//Build the match-fields
	matchFields := make([]*ofp.OfpOxmField, 0)
	for _, val := range fa.MatchFields {
		matchFields = append(matchFields, &ofp.OfpOxmField{Field: &ofp.OfpOxmField_OfbField{OfbField: val}})
	}
	return FlowStatsEntryFromFlowModMessage(MkSimpleFlowMod(matchFields, fa.Actions, fa.Command, fa.KV))
}

func MkGroupStat(ga *GroupArgs) *ofp.OfpGroupEntry {
	return GroupEntryFromGroupMod(MkMulticastGroupMod(ga.GroupId, ga.Buckets, ga.Command))
}

type OfpFlowModArgs map[string]uint64

type FlowArgs struct {
	MatchFields []*ofp.OfpOxmOfbField
	Actions     []*ofp.OfpAction
	Command     *ofp.OfpFlowModCommand
	Priority    uint32
	KV          OfpFlowModArgs
}

type GroupArgs struct {
	GroupId uint32
	Buckets []*ofp.OfpBucket
	Command *ofp.OfpGroupModCommand
}

type FlowsAndGroups struct {
	Flows  *ordered_map.OrderedMap
	Groups *ordered_map.OrderedMap
}

func NewFlowsAndGroups() *FlowsAndGroups {
	var fg FlowsAndGroups
	fg.Flows = ordered_map.NewOrderedMap()
	fg.Groups = ordered_map.NewOrderedMap()
	return &fg
}

func (fg *FlowsAndGroups) Copy() *FlowsAndGroups {
	copyFG := NewFlowsAndGroups()
	iter := fg.Flows.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpFlowStats); isMsg {
			copyFG.Flows.Set(kv.Key, proto.Clone(protoMsg))
		}
	}
	iter = fg.Groups.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpGroupEntry); isMsg {
			copyFG.Groups.Set(kv.Key, proto.Clone(protoMsg))
		}
	}
	return copyFG
}

func (fg *FlowsAndGroups) GetFlow(index int) *ofp.OfpFlowStats {
	iter := fg.Flows.IterFunc()
	pos := 0
	for kv, ok := iter(); ok; kv, ok = iter() {
		if pos == index {
			if protoMsg, isMsg := kv.Value.(*ofp.OfpFlowStats); isMsg {
				return protoMsg
			}
			return nil
		}
		pos += 1
	}
	return nil
}

func (fg *FlowsAndGroups) ListFlows() []*ofp.OfpFlowStats {
	flows := make([]*ofp.OfpFlowStats, 0)
	iter := fg.Flows.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpFlowStats); isMsg {
			flows = append(flows, protoMsg)
		}
	}
	return flows
}

func (fg *FlowsAndGroups) ListGroups() []*ofp.OfpGroupEntry {
	groups := make([]*ofp.OfpGroupEntry, 0)
	iter := fg.Groups.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpGroupEntry); isMsg {
			groups = append(groups, protoMsg)
		}
	}
	return groups
}

func (fg *FlowsAndGroups) String() string {
	var buffer bytes.Buffer
	iter := fg.Flows.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpFlowStats); isMsg {
			buffer.WriteString("\nFlow:\n")
			buffer.WriteString(proto.MarshalTextString(protoMsg))
			buffer.WriteString("\n")
		}
	}
	iter = fg.Groups.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpGroupEntry); isMsg {
			buffer.WriteString("\nGroup:\n")
			buffer.WriteString(proto.MarshalTextString(protoMsg))
			buffer.WriteString("\n")
		}
	}
	return buffer.String()
}

func (fg *FlowsAndGroups) AddFlow(flow *ofp.OfpFlowStats) {
	if flow == nil {
		return
	}

	if fg.Flows == nil {
		fg.Flows = ordered_map.NewOrderedMap()
	}
	if fg.Groups == nil {
		fg.Groups = ordered_map.NewOrderedMap()
	}
	//Add flow only if absent
	if _, exist := fg.Flows.Get(flow.Id); !exist {
		fg.Flows.Set(flow.Id, flow)
	}
}

func (fg *FlowsAndGroups) AddGroup(group *ofp.OfpGroupEntry) {
	if group == nil {
		return
	}

	if fg.Flows == nil {
		fg.Flows = ordered_map.NewOrderedMap()
	}
	if fg.Groups == nil {
		fg.Groups = ordered_map.NewOrderedMap()
	}
	//Add group only if absent
	if _, exist := fg.Groups.Get(group.Desc.GroupId); !exist {
		fg.Groups.Set(group.Desc.GroupId, group)
	}
}

//AddFrom add flows and groups from the argument into this structure only if they do not already exist
func (fg *FlowsAndGroups) AddFrom(from *FlowsAndGroups) {
	iter := from.Flows.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpFlowStats); isMsg {
			if _, exist := fg.Flows.Get(protoMsg.Id); !exist {
				fg.Flows.Set(protoMsg.Id, protoMsg)
			}
		}
	}
	iter = from.Groups.IterFunc()
	for kv, ok := iter(); ok; kv, ok = iter() {
		if protoMsg, isMsg := kv.Value.(*ofp.OfpGroupEntry); isMsg {
			if _, exist := fg.Groups.Get(protoMsg.Stats.GroupId); !exist {
				fg.Groups.Set(protoMsg.Stats.GroupId, protoMsg)
			}
		}
	}
}

type DeviceRules struct {
	Rules map[string]*FlowsAndGroups
}

func NewDeviceRules() *DeviceRules {
	var dr DeviceRules
	dr.Rules = make(map[string]*FlowsAndGroups)
	return &dr
}

func (dr *DeviceRules) Copy() *DeviceRules {
	copyDR := NewDeviceRules()
	if dr != nil {
		for key, val := range dr.Rules {
			if val != nil {
				copyDR.Rules[key] = val.Copy()
			}
		}
	}
	return copyDR
}

func (dr *DeviceRules) ClearFlows(deviceId string) {
	if _, exist := dr.Rules[deviceId]; exist {
		dr.Rules[deviceId].Flows = ordered_map.NewOrderedMap()
	}
}

func (dr *DeviceRules) FilterRules(deviceIds map[string]string) *DeviceRules {
	filteredDR := NewDeviceRules()
	for key, val := range dr.Rules {
		if _, exist := deviceIds[key]; exist {
			filteredDR.Rules[key] = val.Copy()
		}
	}
	return filteredDR
}

func (dr *DeviceRules) AddFlow(deviceId string, flow *ofp.OfpFlowStats) {
	if _, exist := dr.Rules[deviceId]; !exist {
		dr.Rules[deviceId] = NewFlowsAndGroups()
	}
	dr.Rules[deviceId].AddFlow(flow)
}

func (dr *DeviceRules) GetRules() map[string]*FlowsAndGroups {
	return dr.Rules
}

func (dr *DeviceRules) String() string {
	var buffer bytes.Buffer
	for key, value := range dr.Rules {
		buffer.WriteString("DeviceId:")
		buffer.WriteString(key)
		buffer.WriteString(value.String())
		buffer.WriteString("\n\n")
	}
	return buffer.String()
}

func (dr *DeviceRules) AddFlowsAndGroup(deviceId string, fg *FlowsAndGroups) {
	if _, ok := dr.Rules[deviceId]; !ok {
		dr.Rules[deviceId] = NewFlowsAndGroups()
	}
	dr.Rules[deviceId] = fg
}

// CreateEntryIfNotExist creates a new deviceId in the Map if it does not exist and assigns an
// empty FlowsAndGroups to it.  Otherwise, it does nothing.
func (dr *DeviceRules) CreateEntryIfNotExist(deviceId string) {
	if _, ok := dr.Rules[deviceId]; !ok {
		dr.Rules[deviceId] = NewFlowsAndGroups()
	}
}

/*
 *  Common flow routines
 */

//FindOverlappingFlows return a list of overlapping flow(s) where mod is the flow request
func FindOverlappingFlows(flows []*ofp.OfpFlowStats, mod *ofp.OfpFlowMod) []*ofp.OfpFlowStats {
	return nil //TODO - complete implementation
}

// FindFlowById returns the index of the flow in the flows array if present. Otherwise, it returns -1
func FindFlowById(flows []*ofp.OfpFlowStats, flow *ofp.OfpFlowStats) int {
	for idx, f := range flows {
		if flow.Id == f.Id {
			return idx
		}
	}
	return -1
}

// FindFlows returns the index in flows where flow if present.  Otherwise, it returns -1
func FindFlows(flows []*ofp.OfpFlowStats, flow *ofp.OfpFlowStats) int {
	for idx, f := range flows {
		if FlowMatch(f, flow) {
			return idx
		}
	}
	return -1
}

//FlowMatch returns true if two flows matches on the following flow attributes:
//TableId, Priority, Flags, Cookie, Match
func FlowMatch(f1 *ofp.OfpFlowStats, f2 *ofp.OfpFlowStats) bool {
	if f1 == nil || f2 == nil {
		return false
	}
	keysMatter := []string{"TableId", "Priority", "Flags", "Cookie", "Match"}
	for _, key := range keysMatter {
		switch key {
		case "TableId":
			if f1.TableId != f2.TableId {
				return false
			}
		case "Priority":
			if f1.Priority != f2.Priority {
				return false
			}
		case "Flags":
			if f1.Flags != f2.Flags {
				return false
			}
		case "Cookie":
			if f1.Cookie != f2.Cookie {
				return false
			}
		case "Match":
			if strings.Compare(f1.Match.String(), f2.Match.String()) != 0 {
				return false
			}
		}
	}
	return true
}

//FlowMatchesMod returns True if given flow is "covered" by the wildcard flow_mod, taking into consideration of
//both exact matches as well as masks-based match fields if any. Otherwise return False
func FlowMatchesMod(flow *ofp.OfpFlowStats, mod *ofp.OfpFlowMod) bool {
	if flow == nil || mod == nil {
		return false
	}
	//Check if flow.cookie is covered by mod.cookie and mod.cookie_mask
	if (flow.Cookie & mod.CookieMask) != (mod.Cookie & mod.CookieMask) {
		return false
	}

	//Check if flow.table_id is covered by flow_mod.table_id
	if mod.TableId != uint32(ofp.OfpTable_OFPTT_ALL) && flow.TableId != mod.TableId {
		return false
	}

	//Check out_port
	if (mod.OutPort&0x7fffffff) != uint32(ofp.OfpPortNo_OFPP_ANY) && !FlowHasOutPort(flow, mod.OutPort) {
		return false
	}

	//	Check out_group
	if (mod.OutGroup&0x7fffffff) != uint32(ofp.OfpGroup_OFPG_ANY) && !FlowHasOutGroup(flow, mod.OutGroup) {
		return false
	}

	//Priority is ignored

	//Check match condition
	//If the flow_mod match field is empty, that is a special case and indicates the flow entry matches
	if (mod.Match == nil) || (mod.Match.OxmFields == nil) || (len(mod.Match.OxmFields) == 0) {
		//If we got this far and the match is empty in the flow spec, than the flow matches
		return true
	} // TODO : implement the flow match analysis
	return false

}

//FlowHasOutPort returns True if flow has a output command with the given out_port
func FlowHasOutPort(flow *ofp.OfpFlowStats, outPort uint32) bool {
	if flow == nil {
		return false
	}
	for _, instruction := range flow.Instructions {
		if instruction.Type == uint32(ofp.OfpInstructionType_OFPIT_APPLY_ACTIONS) {
			if instruction.GetActions() == nil {
				return false
			}
			for _, action := range instruction.GetActions().Actions {
				if action.Type == ofp.OfpActionType_OFPAT_OUTPUT {
					if (action.GetOutput() != nil) && (action.GetOutput().Port == outPort) {
						return true
					}
				}

			}
		}
	}
	return false
}

//FlowHasOutGroup return True if flow has a output command with the given out_group
func FlowHasOutGroup(flow *ofp.OfpFlowStats, groupID uint32) bool {
	if flow == nil {
		return false
	}
	for _, instruction := range flow.Instructions {
		if instruction.Type == uint32(ofp.OfpInstructionType_OFPIT_APPLY_ACTIONS) {
			if instruction.GetActions() == nil {
				return false
			}
			for _, action := range instruction.GetActions().Actions {
				if action.Type == ofp.OfpActionType_OFPAT_GROUP {
					if (action.GetGroup() != nil) && (action.GetGroup().GroupId == groupID) {
						return true
					}
				}

			}
		}
	}
	return false
}

//FindGroup returns index of group if found, else returns -1
func FindGroup(groups []*ofp.OfpGroupEntry, groupId uint32) int {
	for idx, group := range groups {
		if group.Desc.GroupId == groupId {
			return idx
		}
	}
	return -1
}

func FlowsDeleteByGroupId(flows []*ofp.OfpFlowStats, groupId uint32) (bool, []*ofp.OfpFlowStats) {
	toKeep := make([]*ofp.OfpFlowStats, 0)

	for _, f := range flows {
		if !FlowHasOutGroup(f, groupId) {
			toKeep = append(toKeep, f)
		}
	}
	return len(toKeep) < len(flows), toKeep
}

func ToOfpOxmField(from []*ofp.OfpOxmOfbField) []*ofp.OfpOxmField {
	matchFields := make([]*ofp.OfpOxmField, 0)
	for _, val := range from {
		matchFields = append(matchFields, &ofp.OfpOxmField{Field: &ofp.OfpOxmField_OfbField{OfbField: val}})
	}
	return matchFields
}

//IsMulticastIp returns true if the ip starts with the byte sequence of 1110;
//false otherwise.
func IsMulticastIp(ip uint32) bool {
	return ip>>28 == 14
}

//ConvertToMulticastMacInt returns equivalent mac address of the given multicast ip address
func ConvertToMulticastMacInt(ip uint32) uint64 {
	//get last 23 bits of ip address by ip & 00000000011111111111111111111111
	theLast23BitsOfIp := ip & 8388607
	// perform OR with 0x1005E000000 to build mcast mac address
	return 1101088686080 | uint64(theLast23BitsOfIp)
}

//ConvertToMulticastMacBytes returns equivalent mac address of the given multicast ip address
func ConvertToMulticastMacBytes(ip uint32) []byte {
	mac := ConvertToMulticastMacInt(ip)
	var b bytes.Buffer
	// catalyze (48 bits) in binary:111111110000000000000000000000000000000000000000
	catalyze := uint64(280375465082880)
	//convert each octet to decimal
	for i := 0; i < 6; i++ {
		if i != 0 {
			catalyze = catalyze >> 8
		}
		octet := mac & catalyze
		octetDecimal := octet >> uint8(40-i*8)
		b.WriteByte(byte(octetDecimal))
	}
	return b.Bytes()
}
