// SPDX-License-Identifier: GPL-2.0+
/* Microchip Sparx5 Switch driver
 *
 * Copyright (c) 2021 Microchip Technology Inc. and its subsidiaries.
 */

#include <linux/module.h>
#include <linux/phylink.h>
#include <linux/device.h>
#include <linux/netdevice.h>
#include <linux/sfp.h>

#include "sparx5_main_regs.h"
#include "sparx5_main.h"
#include "sparx5_port.h"

static bool port_conf_has_changed(struct sparx5_port_config *a, struct sparx5_port_config *b)
{
	if (a->speed != b->speed ||
	    a->portmode != b->portmode ||
	    a->autoneg != b->autoneg ||
	    a->pause_adv != b->pause_adv ||
	    a->power_down != b->power_down ||
	    a->media != b->media)
		return true;
	return false;
}

static void sparx5_phylink_mac_config(struct phylink_config *config,
				      unsigned int mode,
				      const struct phylink_link_state *state)
{
	/* Currently not used */
}

static void sparx5_phylink_mac_link_up(struct phylink_config *config,
				       struct phy_device *phy,
				       unsigned int mode,
				       phy_interface_t interface,
				       int speed, int duplex,
				       bool tx_pause, bool rx_pause)
{
	struct sparx5_port *port = netdev_priv(to_net_dev(config->dev));
	struct sparx5_port_config conf;
	int err;

	conf = port->conf;
	conf.duplex = duplex;
	conf.pause = 0;
	conf.pause |= tx_pause ? MLO_PAUSE_TX : 0;
	conf.pause |= rx_pause ? MLO_PAUSE_RX : 0;
	conf.speed = speed;
	/* Configure the port to speed/duplex/pause */
	err = sparx5_port_config(port->sparx5, port, &conf);
	if (err)
		netdev_err(port->ndev, "port config failed: %d\n", err);
}

static void sparx5_phylink_mac_link_down(struct phylink_config *config,
					 unsigned int mode,
					 phy_interface_t interface)
{
	/* Currently not used */
}

static struct sparx5_port *sparx5_pcs_to_port(struct phylink_pcs *pcs)
{
	return container_of(pcs, struct sparx5_port, phylink_pcs);
}

static void sparx5_pcs_get_state(struct phylink_pcs *pcs,
				 struct phylink_link_state *state)
{
	struct sparx5_port *port = sparx5_pcs_to_port(pcs);
	struct sparx5_port_status status;

	sparx5_get_port_status(port->sparx5, port, &status);
	state->link = status.link && !status.link_down;
	state->an_complete = status.an_complete;
	state->speed = status.speed;
	state->duplex = status.duplex;
	state->pause = status.pause;
}

static int sparx5_pcs_config(struct phylink_pcs *pcs,
			     unsigned int mode,
			     phy_interface_t interface,
			     const unsigned long *advertising,
			     bool permit_pause_to_mac)
{
	struct sparx5_port *port = sparx5_pcs_to_port(pcs);
	struct sparx5_port_config conf;
	int ret = 0;

	conf = port->conf;
	conf.power_down = false;
	conf.portmode = interface;
	conf.inband = phylink_autoneg_inband(mode);
	conf.autoneg = phylink_test(advertising, Autoneg);
	conf.pause_adv = 0;
	if (phylink_test(advertising, Pause))
		conf.pause_adv |= ADVERTISE_1000XPAUSE;
	if (phylink_test(advertising, Asym_Pause))
		conf.pause_adv |= ADVERTISE_1000XPSE_ASYM;
	if (sparx5_is_baser(interface)) {
		if (phylink_test(advertising, FIBRE))
			conf.media = PHY_MEDIA_SR;
		else
			conf.media = PHY_MEDIA_DAC;
	}
	if (!port_conf_has_changed(&port->conf, &conf))
		return ret;
	/* Enable the PCS matching this interface type */
	ret = sparx5_port_pcs_set(port->sparx5, port, &conf);
	if (ret)
		netdev_err(port->ndev, "port PCS config failed: %d\n", ret);
	return ret;
}

static void sparx5_pcs_aneg_restart(struct phylink_pcs *pcs)
{
	/* Currently not used */
}

const struct phylink_pcs_ops sparx5_phylink_pcs_ops = {
	.pcs_get_state = sparx5_pcs_get_state,
	.pcs_config = sparx5_pcs_config,
	.pcs_an_restart = sparx5_pcs_aneg_restart,
};

const struct phylink_mac_ops sparx5_phylink_mac_ops = {
	.validate = phylink_generic_validate,
	.mac_config = sparx5_phylink_mac_config,
	.mac_link_down = sparx5_phylink_mac_link_down,
	.mac_link_up = sparx5_phylink_mac_link_up,
};
