/*
 * 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 dhcp

import (
	"context"
	"encoding/hex"
	"errors"
	"fmt"
	"github.com/google/gopacket"
	"github.com/google/gopacket/layers"
	"github.com/looplab/fsm"
	"github.com/opencord/bbsim/internal/bbsim/packetHandlers"
	bbsim "github.com/opencord/bbsim/internal/bbsim/types"
	"github.com/opencord/voltha-protos/v4/go/openolt"
	log "github.com/sirupsen/logrus"
	"net"
	"reflect"
	"strconv"
)

var dhcpLogger = log.WithFields(log.Fields{
	"module": "DHCP",
})

var defaultParamsRequestList = []layers.DHCPOpt{
	layers.DHCPOptSubnetMask,
	layers.DHCPOptBroadcastAddr,
	layers.DHCPOptTimeOffset,
	layers.DHCPOptRouter,
	layers.DHCPOptDomainName,
	layers.DHCPOptDNS,
	layers.DHCPOptDomainSearch,
	layers.DHCPOptHostname,
	layers.DHCPOptNetBIOSTCPNS,
	layers.DHCPOptNetBIOSTCPScope,
	layers.DHCPOptInterfaceMTU,
	layers.DHCPOptClasslessStaticRoute,
	layers.DHCPOptNTPServers,
}

func macAddressToTxId(mac net.HardwareAddr) uint32 {

	// NOTE we want to generate a unique XID,
	// the easiest way is to transform the macAddress (already unique) into an integer
	str := ""
	for _, i := range mac {
		str = str + fmt.Sprintf("%d", i)
	}
	xid, err := strconv.Atoi(str)
	if err != nil {
		log.Fatal("Can't generate unique XID for ONU")
	}

	return uint32(xid)
}

func createDefaultDHCPReq(mac net.HardwareAddr) layers.DHCPv4 {
	xid := macAddressToTxId(mac)

	return layers.DHCPv4{
		Operation:    layers.DHCPOpRequest,
		HardwareType: layers.LinkTypeEthernet,
		HardwareLen:  6,
		HardwareOpts: 0,
		Xid:          uint32(xid),
		ClientHWAddr: mac,
	}
}

func createDefaultOpts(gemPortId uint32, intfId uint32, onuId uint32) []layers.DHCPOption {
	hostname := []byte(fmt.Sprintf("%d.%d.%d.bbsim.onf.org", gemPortId, intfId, onuId))
	opts := []layers.DHCPOption{}
	opts = append(opts, layers.DHCPOption{
		Type:   layers.DHCPOptHostname,
		Data:   hostname,
		Length: uint8(len(hostname)),
	})

	bytes := []byte{}
	for _, option := range defaultParamsRequestList {
		bytes = append(bytes, byte(option))
	}

	opts = append(opts, layers.DHCPOption{
		Type:   layers.DHCPOptParamsRequest,
		Data:   bytes,
		Length: uint8(len(bytes)),
	})
	return opts
}

func createDHCPDisc(intfId uint32, onuId uint32, gemPort uint32, macAddress net.HardwareAddr) *layers.DHCPv4 {
	dhcpLayer := createDefaultDHCPReq(macAddress)
	defaultOpts := createDefaultOpts(gemPort, intfId, onuId)
	dhcpLayer.Options = append([]layers.DHCPOption{{
		Type:   layers.DHCPOptMessageType,
		Data:   []byte{byte(layers.DHCPMsgTypeDiscover)},
		Length: 1,
	}}, defaultOpts...)

	data := []byte{01}
	data = append(data, macAddress...)
	dhcpLayer.Options = append(dhcpLayer.Options, layers.DHCPOption{
		Type:   layers.DHCPOptClientID,
		Data:   data,
		Length: uint8(len(data)),
	})

	return &dhcpLayer
}

func createDHCPReq(intfId uint32, onuId uint32, macAddress net.HardwareAddr, offeredIp net.IP, gemPortId uint32) *layers.DHCPv4 {
	dhcpLayer := createDefaultDHCPReq(macAddress)
	defaultOpts := createDefaultOpts(gemPortId, intfId, onuId)

	dhcpLayer.Options = append(defaultOpts, layers.DHCPOption{
		Type:   layers.DHCPOptMessageType,
		Data:   []byte{byte(layers.DHCPMsgTypeRequest)},
		Length: 1,
	})

	data := []byte{182, 21, 0, 128}
	dhcpLayer.Options = append(dhcpLayer.Options, layers.DHCPOption{
		Type:   layers.DHCPOptServerID,
		Data:   data,
		Length: uint8(len(data)),
	})

	data = []byte{0xcd, 0x28, 0xcb, 0xcc, 0x00, 0x01, 0x00, 0x01,
		0x23, 0xed, 0x11, 0xec, 0x4e, 0xfc, 0xcd, 0x28, byte(intfId), byte(onuId)}
	dhcpLayer.Options = append(dhcpLayer.Options, layers.DHCPOption{
		Type:   layers.DHCPOptClientID,
		Data:   data,
		Length: uint8(len(data)),
	})

	// NOTE we should not request a specific IP, or we should request the one that has been offered
	dhcpLayer.Options = append(dhcpLayer.Options, layers.DHCPOption{
		Type:   layers.DHCPOptRequestIP,
		Data:   offeredIp,
		Length: uint8(len(offeredIp)),
	})
	return &dhcpLayer
}

func serializeDHCPPacket(cTag int, srcMac net.HardwareAddr, dhcp *layers.DHCPv4, pbit uint8) (gopacket.Packet, error) {
	buffer := gopacket.NewSerializeBuffer()

	options := gopacket.SerializeOptions{
		ComputeChecksums: true,
		FixLengths:       true,
	}

	ethernetLayer := &layers.Ethernet{
		SrcMAC:       srcMac,
		DstMAC:       net.HardwareAddr{0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
		EthernetType: layers.EthernetTypeIPv4,
	}

	ipLayer := &layers.IPv4{
		Version:  4,
		TOS:      0x10,
		TTL:      128,
		SrcIP:    []byte{0, 0, 0, 0},
		DstIP:    []byte{255, 255, 255, 255},
		Protocol: layers.IPProtocolUDP,
	}

	udpLayer := &layers.UDP{
		SrcPort: 68,
		DstPort: 67,
	}

	_ = udpLayer.SetNetworkLayerForChecksum(ipLayer)
	if err := gopacket.SerializeLayers(buffer, options, ethernetLayer, ipLayer, udpLayer, dhcp); err != nil {
		dhcpLogger.Error("SerializeLayers")
		return nil, err
	}

	untaggedPkt := gopacket.NewPacket(buffer.Bytes(), layers.LayerTypeEthernet, gopacket.Default)

	taggedPkt, err := packetHandlers.PushSingleTag(cTag, untaggedPkt, pbit)
	if err != nil {
		dhcpLogger.Error("TagPacket")
		return nil, err
	}

	return taggedPkt, nil
}

func GetDhcpLayer(pkt gopacket.Packet) (*layers.DHCPv4, error) {
	layerDHCP := pkt.Layer(layers.LayerTypeDHCPv4)
	dhcp, _ := layerDHCP.(*layers.DHCPv4)
	if dhcp == nil {
		return nil, errors.New("Failed-to-extract-DHCP-layer")
	}
	return dhcp, nil
}

func GetDhcpMessageType(dhcp *layers.DHCPv4) (layers.DHCPMsgType, error) {
	for _, option := range dhcp.Options {
		if option.Type == layers.DHCPOptMessageType {
			if reflect.DeepEqual(option.Data, []byte{byte(layers.DHCPMsgTypeDiscover)}) {
				return layers.DHCPMsgTypeDiscover, nil
			} else if reflect.DeepEqual(option.Data, []byte{byte(layers.DHCPMsgTypeOffer)}) {
				return layers.DHCPMsgTypeOffer, nil
			} else if reflect.DeepEqual(option.Data, []byte{byte(layers.DHCPMsgTypeRequest)}) {
				return layers.DHCPMsgTypeRequest, nil
			} else if reflect.DeepEqual(option.Data, []byte{byte(layers.DHCPMsgTypeAck)}) {
				return layers.DHCPMsgTypeAck, nil
			} else if reflect.DeepEqual(option.Data, []byte{byte(layers.DHCPMsgTypeRelease)}) {
				return layers.DHCPMsgTypeRelease, nil
			} else {
				msg := fmt.Sprintf("This type %x is not supported", option.Data)
				return 0, errors.New(msg)
			}
		}
	}
	return 0, errors.New("Failed to extract MsgType from dhcp")
}

// returns the DHCP Layer type or error if it's not a DHCP Packet
func GetDhcpPacketType(pkt gopacket.Packet) (string, error) {
	dhcpLayer, err := GetDhcpLayer(pkt)
	if err != nil {
		return "", err
	}
	dhcpMessageType, err := GetDhcpMessageType(dhcpLayer)
	if err != nil {
		return "", err
	}

	return dhcpMessageType.String(), nil
}

func sendDHCPPktIn(msg bbsim.ByteMsg, portNo uint32, gemPortId uint32, stream bbsim.Stream) error {

	dhcpLogger.WithFields(log.Fields{
		"OnuId":   msg.OnuId,
		"IntfId":  msg.IntfId,
		"GemPort": gemPortId,
		"Type":    "DHCP",
		"Pkt":     hex.EncodeToString(msg.Bytes),
	}).Trace("Sending DHCP packet in")

	data := &openolt.Indication_PktInd{PktInd: &openolt.PacketIndication{
		IntfType:  "pon",
		IntfId:    msg.IntfId,
		GemportId: gemPortId,
		Pkt:       msg.Bytes,
		PortNo:    portNo,
	}}

	if err := stream.Send(&openolt.Indication{Data: data}); err != nil {
		dhcpLogger.Errorf("Fail to send DHCP PktInd indication. %v", err)
		return err
	}
	return nil
}

func sendDHCPRequest(ponPortId uint32, onuId uint32, serviceName string, serialNumber string, portNo uint32,
	cTag int, gemPortId uint32, onuStateMachine *fsm.FSM, onuHwAddress net.HardwareAddr,
	offeredIp net.IP, pbit uint8, stream bbsim.Stream) error {
	dhcp := createDHCPReq(ponPortId, onuId, onuHwAddress, offeredIp, gemPortId)
	pkt, err := serializeDHCPPacket(cTag, onuHwAddress, dhcp, pbit)

	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":     onuId,
			"IntfId":    ponPortId,
			"OnuSn":     serialNumber,
			"OfferedIp": offeredIp.String(),
		}).Errorf("Cannot serializeDHCPPacket: %s", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, onuStateMachine); err != nil {
			return err
		}
		return err
	}
	// NOTE I don't think we need to tag the packet
	//taggedPkt, err := packetHandlers.PushSingleTag(cTag, pkt)

	msg := bbsim.ByteMsg{
		IntfId: ponPortId,
		OnuId:  onuId,
		Bytes:  pkt.Data(),
	}

	if err := sendDHCPPktIn(msg, portNo, gemPortId, stream); err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
		}).Errorf("Cannot sendDHCPPktIn: %s", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, onuStateMachine); err != nil {
			return err
		}
		return err
	}

	dhcpLogger.WithFields(log.Fields{
		"OnuId":       onuId,
		"IntfId":      ponPortId,
		"OnuSn":       serialNumber,
		"OfferedIp":   offeredIp.String(),
		"ServiceName": serviceName,
	}).Infof("DHCPRequest Sent")
	return nil
}

func updateDhcpFailed(onuId uint32, ponPortId uint32, serialNumber string, onuStateMachine *fsm.FSM) error {
	if err := onuStateMachine.Event("dhcp_failed"); err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
		}).Errorf("Error while transitioning ONU State %v", err)
		return err
	}
	return nil
}

func SendDHCPDiscovery(ponPortId uint32, onuId uint32, serviceName string, cTag int, gemPortId uint32,
	serialNumber string, portNo uint32, stateMachine *fsm.FSM, onuHwAddress net.HardwareAddr,
	pbit uint8, stream bbsim.Stream) error {

	dhcp := createDHCPDisc(ponPortId, onuId, gemPortId, onuHwAddress)
	pkt, err := serializeDHCPPacket(cTag, onuHwAddress, dhcp, pbit)

	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Errorf("Cannot serializeDHCPPacket: %s", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, stateMachine); err != nil {
			return err
		}
		return err
	}
	// NOTE I don't think we need to tag the packet
	//taggedPkt, err := packetHandlers.PushSingleTag(cTag, pkt)

	msg := bbsim.ByteMsg{
		IntfId: ponPortId,
		OnuId:  onuId,
		Bytes:  pkt.Data(),
	}

	if err := sendDHCPPktIn(msg, portNo, gemPortId, stream); err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Errorf("Cannot sendDHCPPktIn: %s", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, stateMachine); err != nil {
			return err
		}
		return err
	}
	dhcpLogger.WithFields(log.Fields{
		"OnuId":       onuId,
		"IntfId":      ponPortId,
		"OnuSn":       serialNumber,
		"ServiceName": serviceName,
	}).Info("DHCPDiscovery Sent")

	if err := stateMachine.Event("dhcp_discovery_sent"); err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Errorf("Error while transitioning ONU State %v", err)
		return err
	}
	return nil
}

func HandleNextPacket(onuId uint32, ponPortId uint32, serviceName string, serialNumber string, portNo uint32,
	cTag int, gemPortId uint32, onuHwAddress net.HardwareAddr, onuStateMachine *fsm.FSM,
	pkt gopacket.Packet, pbit uint8, stream bbsim.Stream) error {

	dhcpLayer, err := GetDhcpLayer(pkt)
	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Errorf("Can't get DHCP Layer from Packet: %v", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, onuStateMachine); err != nil {
			return err
		}
		return err
	}
	dhcpMessageType, err := GetDhcpMessageType(dhcpLayer)
	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Errorf("Can't get DHCP Message Type from DHCP Layer: %v", err)
		if err := updateDhcpFailed(onuId, ponPortId, serialNumber, onuStateMachine); err != nil {
			return err
		}
		return err
	}

	if dhcpLayer.Operation == layers.DHCPOpReply {
		if dhcpMessageType == layers.DHCPMsgTypeOffer {
			offeredIp := dhcpLayer.YourClientIP
			if err := sendDHCPRequest(ponPortId, onuId, serviceName, serialNumber, portNo, cTag, gemPortId, onuStateMachine, onuHwAddress, offeredIp, pbit, stream); err != nil {
				dhcpLogger.WithFields(log.Fields{
					"OnuId":       onuId,
					"IntfId":      ponPortId,
					"OnuSn":       serialNumber,
					"ServiceName": serviceName,
				}).Errorf("Can't send DHCP Request: %s", err)
				if err := updateDhcpFailed(onuId, ponPortId, serialNumber, onuStateMachine); err != nil {
					return err
				}
				return err
			}
			if err := onuStateMachine.Event("dhcp_request_sent"); err != nil {
				dhcpLogger.WithFields(log.Fields{
					"OnuId":       onuId,
					"IntfId":      ponPortId,
					"OnuSn":       serialNumber,
					"ServiceName": serviceName,
				}).Errorf("Error while transitioning State %v", err)
			}

		} else if dhcpMessageType == layers.DHCPMsgTypeAck {
			// NOTE once the ack is received we don't need to do anything but change the state
			if err := onuStateMachine.Event("dhcp_ack_received"); err != nil {
				dhcpLogger.WithFields(log.Fields{
					"OnuId":       onuId,
					"IntfId":      ponPortId,
					"OnuSn":       serialNumber,
					"ServiceName": serviceName,
				}).Errorf("Error while transitioning State %v", err)
			}
			dhcpLogger.WithFields(log.Fields{
				"OnuId":       onuId,
				"IntfId":      ponPortId,
				"OnuSn":       serialNumber,
				"ServiceName": serviceName,
			}).Infof("DHCP State machine completed")
		}
		// NOTE do we need to care about DHCPMsgTypeRelease??
	} else {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":       onuId,
			"IntfId":      ponPortId,
			"OnuSn":       serialNumber,
			"ServiceName": serviceName,
		}).Warnf("Unsupported DHCP Operation: %s", dhcpLayer.Operation.String())
	}

	return nil
}

// This method handle the BBR DHCP Packets
// BBR does not need to do anything but forward the packets in the correct direction
func HandleNextBbrPacket(onuId uint32, ponPortId uint32, serialNumber string, doneChannel chan bool, pkt gopacket.Packet, client openolt.OpenoltClient) error {

	// check if the packet is going:
	// - outgouing: toward the DHCP
	// - incoming: toward the ONU
	isIncoming := packetHandlers.IsIncomingPacket(pkt)
	dhcpLogger.Tracef("Is Incoming: %t", isIncoming)

	pkt, err := packetHandlers.PopSingleTag(pkt)
	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
			"error":  err,
		}).Fatalf("Can't untag packet")
	}

	dhcpType, err := GetDhcpPacketType(pkt)
	if err != nil {
		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
			"error":  err,
		}).Fatalf("Can't find DHCP type for packet")
	}

	srcMac, _ := packetHandlers.GetSrcMacAddressFromPacket(pkt)
	dstMac, _ := packetHandlers.GetDstMacAddressFromPacket(pkt)

	if isIncoming {

		onuPacket := openolt.OnuPacket{
			IntfId:    ponPortId,
			OnuId:     onuId,
			PortNo:    onuId,
			GemportId: 1,
			Pkt:       pkt.Data(),
		}

		if _, err := client.OnuPacketOut(context.Background(), &onuPacket); err != nil {
			dhcpLogger.WithFields(log.Fields{
				"OnuId":  onuId,
				"IntfId": ponPortId,
				"OnuSn":  serialNumber,
				"Type":   dhcpType,
				"error":  err,
			}).Error("Failed to send DHCP packet to the ONU")
		}

		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
			"Type":   dhcpType,
			"DstMac": dstMac,
			"SrcMac": srcMac,
		}).Infof("Sent DHCP packet to the ONU")

		dhcpLayer, _ := GetDhcpLayer(pkt)
		dhcpMessageType, _ := GetDhcpMessageType(dhcpLayer)
		if dhcpMessageType == layers.DHCPMsgTypeAck {
			doneChannel <- true
		}

	} else {
		// double tag the packet and send it to the NNI
		// we don't really care about the tags as they are stripped before
		// the packet is sent to the DHCP server
		// in BBR we don't care about the pBit
		doubleTaggedPkt, err := packetHandlers.PushDoubleTag(900, 900, pkt, 0)
		if err != nil {
			dhcpLogger.WithFields(log.Fields{
				"OnuId":  onuId,
				"IntfId": ponPortId,
				"OnuSn":  serialNumber,
				"Type":   dhcpType,
				"error":  err,
			}).Error("Failed to add double tag to packet")
		}

		pkt := openolt.UplinkPacket{
			IntfId: 0, // BBSim does not care about which NNI, it has only one
			Pkt:    doubleTaggedPkt.Data(),
		}
		if _, err := client.UplinkPacketOut(context.Background(), &pkt); err != nil {
			dhcpLogger.WithFields(log.Fields{
				"OnuId":  onuId,
				"IntfId": ponPortId,
				"OnuSn":  serialNumber,
				"Type":   dhcpType,
				"error":  err,
			}).Error("Failed to send DHCP packet out of the NNI Port")
			return err
		}
		dhcpLogger.WithFields(log.Fields{
			"OnuId":  onuId,
			"IntfId": ponPortId,
			"OnuSn":  serialNumber,
			"Type":   dhcpType,
			"DstMac": dstMac,
			"SrcMac": srcMac,
		}).Infof("Sent DHCP packet out of the NNI Port")
	}
	return nil
}
