ionic: Add netdev-event handling

When the netdev gets a new name from userland, pass that name
down to the NIC for internal tracking.

Signed-off-by: Shannon Nelson <snelson@pensando.io>
Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
Shannon Nelson 2019-09-03 15:28:18 -07:00 коммит произвёл David S. Miller
Родитель 0f3154e6bc
Коммит 1a371ea1b7
2 изменённых файлов: 64 добавлений и 0 удалений

Просмотреть файл

@ -44,6 +44,8 @@ struct ionic {
DECLARE_BITMAP(lifbits, IONIC_LIFS_MAX);
unsigned int nintrs;
DECLARE_BITMAP(intrs, IONIC_INTR_CTRL_REGS_MAX);
struct work_struct nb_work;
struct notifier_block nb;
};
struct ionic_admin_ctx {

Просмотреть файл

@ -1955,10 +1955,66 @@ int ionic_lifs_init(struct ionic *ionic)
return 0;
}
static void ionic_lif_notify_work(struct work_struct *ws)
{
}
static void ionic_lif_set_netdev_info(struct ionic_lif *lif)
{
struct ionic_admin_ctx ctx = {
.work = COMPLETION_INITIALIZER_ONSTACK(ctx.work),
.cmd.lif_setattr = {
.opcode = IONIC_CMD_LIF_SETATTR,
.index = cpu_to_le16(lif->index),
.attr = IONIC_LIF_ATTR_NAME,
},
};
strlcpy(ctx.cmd.lif_setattr.name, lif->netdev->name,
sizeof(ctx.cmd.lif_setattr.name));
ionic_adminq_post_wait(lif, &ctx);
}
static struct ionic_lif *ionic_netdev_lif(struct net_device *netdev)
{
if (!netdev || netdev->netdev_ops->ndo_start_xmit != ionic_start_xmit)
return NULL;
return netdev_priv(netdev);
}
static int ionic_lif_notify(struct notifier_block *nb,
unsigned long event, void *info)
{
struct net_device *ndev = netdev_notifier_info_to_dev(info);
struct ionic *ionic = container_of(nb, struct ionic, nb);
struct ionic_lif *lif = ionic_netdev_lif(ndev);
if (!lif || lif->ionic != ionic)
return NOTIFY_DONE;
switch (event) {
case NETDEV_CHANGENAME:
ionic_lif_set_netdev_info(lif);
break;
}
return NOTIFY_DONE;
}
int ionic_lifs_register(struct ionic *ionic)
{
int err;
INIT_WORK(&ionic->nb_work, ionic_lif_notify_work);
ionic->nb.notifier_call = ionic_lif_notify;
err = register_netdevice_notifier(&ionic->nb);
if (err)
ionic->nb.notifier_call = NULL;
/* only register LIF0 for now */
err = register_netdev(ionic->master_lif->netdev);
if (err) {
@ -1974,6 +2030,12 @@ int ionic_lifs_register(struct ionic *ionic)
void ionic_lifs_unregister(struct ionic *ionic)
{
if (ionic->nb.notifier_call) {
unregister_netdevice_notifier(&ionic->nb);
cancel_work_sync(&ionic->nb_work);
ionic->nb.notifier_call = NULL;
}
/* There is only one lif ever registered in the
* current model, so don't bother searching the
* ionic->lif for candidates to unregister