Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit ef39830c authored by Sudeep Dutt's avatar Sudeep Dutt Committed by Greg Kroah-Hartman
Browse files

misc: mic: Remove MIC X100 host virtio functionality



This patch deletes the virtio functionality from the MIC X100 host
driver. A subsequent patch will re-enable this functionality by
consolidating the hardware independent logic in a new Virtio over PCIe
(VOP) driver.

Reviewed-by: default avatarAshutosh Dixit <ashutosh.dixit@intel.com>
Signed-off-by: default avatarSudeep Dutt <sudeep.dutt@intel.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 4ddbdbb9
Loading
Loading
Loading
Loading
+0 −2
Original line number Diff line number Diff line
@@ -9,5 +9,3 @@ mic_host-objs += mic_smpt.o
mic_host-objs += mic_intr.o
mic_host-objs += mic_boot.o
mic_host-objs += mic_debugfs.o
mic_host-objs += mic_fops.o
mic_host-objs += mic_virtio.o
+0 −2
Original line number Diff line number Diff line
@@ -28,7 +28,6 @@
#include "../common/mic_dev.h"
#include "mic_device.h"
#include "mic_smpt.h"
#include "mic_virtio.h"

static inline struct mic_device *scdev_to_mdev(struct scif_hw_dev *scdev)
{
@@ -423,7 +422,6 @@ static void _mic_stop(struct cosm_device *cdev, bool force)
	 * will be the first to be registered and the last to be
	 * unregistered.
	 */
	mic_virtio_reset_devices(mdev);
	scif_unregister_device(mdev->scdev);
	mic_free_dma_chans(mdev);
	mbus_unregister_device(mdev->dma_mbdev);
+0 −190
Original line number Diff line number Diff line
@@ -26,7 +26,6 @@
#include "../common/mic_dev.h"
#include "mic_device.h"
#include "mic_smpt.h"
#include "mic_virtio.h"

/* Debugfs parent dir */
static struct dentry *mic_dbg;
@@ -100,190 +99,6 @@ static const struct file_operations post_code_ops = {
	.release = mic_post_code_debug_release
};

static int mic_dp_show(struct seq_file *s, void *pos)
{
	struct mic_device *mdev = s->private;
	struct mic_device_desc *d;
	struct mic_device_ctrl *dc;
	struct mic_vqconfig *vqconfig;
	__u32 *features;
	__u8 *config;
	struct mic_bootparam *bootparam = mdev->dp;
	int i, j;

	seq_printf(s, "Bootparam: magic 0x%x\n",
		   bootparam->magic);
	seq_printf(s, "Bootparam: h2c_config_db %d\n",
		   bootparam->h2c_config_db);
	seq_printf(s, "Bootparam: node_id %d\n",
		   bootparam->node_id);
	seq_printf(s, "Bootparam: c2h_scif_db %d\n",
		   bootparam->c2h_scif_db);
	seq_printf(s, "Bootparam: h2c_scif_db %d\n",
		   bootparam->h2c_scif_db);
	seq_printf(s, "Bootparam: scif_host_dma_addr 0x%llx\n",
		   bootparam->scif_host_dma_addr);
	seq_printf(s, "Bootparam: scif_card_dma_addr 0x%llx\n",
		   bootparam->scif_card_dma_addr);


	for (i = sizeof(*bootparam); i < MIC_DP_SIZE;
	     i += mic_total_desc_size(d)) {
		d = mdev->dp + i;
		dc = (void *)d + mic_aligned_desc_size(d);

		/* end of list */
		if (d->type == 0)
			break;

		if (d->type == -1)
			continue;

		seq_printf(s, "Type %d ", d->type);
		seq_printf(s, "Num VQ %d ", d->num_vq);
		seq_printf(s, "Feature Len %d\n", d->feature_len);
		seq_printf(s, "Config Len %d ", d->config_len);
		seq_printf(s, "Shutdown Status %d\n", d->status);

		for (j = 0; j < d->num_vq; j++) {
			vqconfig = mic_vq_config(d) + j;
			seq_printf(s, "vqconfig[%d]: ", j);
			seq_printf(s, "address 0x%llx ", vqconfig->address);
			seq_printf(s, "num %d ", vqconfig->num);
			seq_printf(s, "used address 0x%llx\n",
				   vqconfig->used_address);
		}

		features = (__u32 *)mic_vq_features(d);
		seq_printf(s, "Features: Host 0x%x ", features[0]);
		seq_printf(s, "Guest 0x%x\n", features[1]);

		config = mic_vq_configspace(d);
		for (j = 0; j < d->config_len; j++)
			seq_printf(s, "config[%d]=%d\n", j, config[j]);

		seq_puts(s, "Device control:\n");
		seq_printf(s, "Config Change %d ", dc->config_change);
		seq_printf(s, "Vdev reset %d\n", dc->vdev_reset);
		seq_printf(s, "Guest Ack %d ", dc->guest_ack);
		seq_printf(s, "Host ack %d\n", dc->host_ack);
		seq_printf(s, "Used address updated %d ",
			   dc->used_address_updated);
		seq_printf(s, "Vdev 0x%llx\n", dc->vdev);
		seq_printf(s, "c2h doorbell %d ", dc->c2h_vdev_db);
		seq_printf(s, "h2c doorbell %d\n", dc->h2c_vdev_db);
	}

	return 0;
}

static int mic_dp_debug_open(struct inode *inode, struct file *file)
{
	return single_open(file, mic_dp_show, inode->i_private);
}

static int mic_dp_debug_release(struct inode *inode, struct file *file)
{
	return single_release(inode, file);
}

static const struct file_operations dp_ops = {
	.owner   = THIS_MODULE,
	.open    = mic_dp_debug_open,
	.read    = seq_read,
	.llseek  = seq_lseek,
	.release = mic_dp_debug_release
};

static int mic_vdev_info_show(struct seq_file *s, void *unused)
{
	struct mic_device *mdev = s->private;
	struct list_head *pos, *tmp;
	struct mic_vdev *mvdev;
	int i, j;

	mutex_lock(&mdev->mic_mutex);
	list_for_each_safe(pos, tmp, &mdev->vdev_list) {
		mvdev = list_entry(pos, struct mic_vdev, list);
		seq_printf(s, "VDEV type %d state %s in %ld out %ld\n",
			   mvdev->virtio_id,
			   mic_vdevup(mvdev) ? "UP" : "DOWN",
			   mvdev->in_bytes,
			   mvdev->out_bytes);
		for (i = 0; i < MIC_MAX_VRINGS; i++) {
			struct vring_desc *desc;
			struct vring_avail *avail;
			struct vring_used *used;
			struct mic_vringh *mvr = &mvdev->mvr[i];
			struct vringh *vrh = &mvr->vrh;
			int num = vrh->vring.num;
			if (!num)
				continue;
			desc = vrh->vring.desc;
			seq_printf(s, "vring i %d avail_idx %d",
				   i, mvr->vring.info->avail_idx & (num - 1));
			seq_printf(s, " vring i %d avail_idx %d\n",
				   i, mvr->vring.info->avail_idx);
			seq_printf(s, "vrh i %d weak_barriers %d",
				   i, vrh->weak_barriers);
			seq_printf(s, " last_avail_idx %d last_used_idx %d",
				   vrh->last_avail_idx, vrh->last_used_idx);
			seq_printf(s, " completed %d\n", vrh->completed);
			for (j = 0; j < num; j++) {
				seq_printf(s, "desc[%d] addr 0x%llx len %d",
					   j, desc->addr, desc->len);
				seq_printf(s, " flags 0x%x next %d\n",
					   desc->flags, desc->next);
				desc++;
			}
			avail = vrh->vring.avail;
			seq_printf(s, "avail flags 0x%x idx %d\n",
				   vringh16_to_cpu(vrh, avail->flags),
				   vringh16_to_cpu(vrh, avail->idx) & (num - 1));
			seq_printf(s, "avail flags 0x%x idx %d\n",
				   vringh16_to_cpu(vrh, avail->flags),
				   vringh16_to_cpu(vrh, avail->idx));
			for (j = 0; j < num; j++)
				seq_printf(s, "avail ring[%d] %d\n",
					   j, avail->ring[j]);
			used = vrh->vring.used;
			seq_printf(s, "used flags 0x%x idx %d\n",
				   vringh16_to_cpu(vrh, used->flags),
				   vringh16_to_cpu(vrh, used->idx) & (num - 1));
			seq_printf(s, "used flags 0x%x idx %d\n",
				   vringh16_to_cpu(vrh, used->flags),
				   vringh16_to_cpu(vrh, used->idx));
			for (j = 0; j < num; j++)
				seq_printf(s, "used ring[%d] id %d len %d\n",
					   j, vringh32_to_cpu(vrh,
							      used->ring[j].id),
					   vringh32_to_cpu(vrh,
							   used->ring[j].len));
		}
	}
	mutex_unlock(&mdev->mic_mutex);

	return 0;
}

static int mic_vdev_info_debug_open(struct inode *inode, struct file *file)
{
	return single_open(file, mic_vdev_info_show, inode->i_private);
}

static int mic_vdev_info_debug_release(struct inode *inode, struct file *file)
{
	return single_release(inode, file);
}

static const struct file_operations vdev_info_ops = {
	.owner   = THIS_MODULE,
	.open    = mic_vdev_info_debug_open,
	.read    = seq_read,
	.llseek  = seq_lseek,
	.release = mic_vdev_info_debug_release
};

static int mic_msi_irq_info_show(struct seq_file *s, void *pos)
{
	struct mic_device *mdev  = s->private;
@@ -367,11 +182,6 @@ void mic_create_debug_dir(struct mic_device *mdev)
	debugfs_create_file("post_code", 0444, mdev->dbg_dir, mdev,
			    &post_code_ops);

	debugfs_create_file("dp", 0444, mdev->dbg_dir, mdev, &dp_ops);

	debugfs_create_file("vdev_info", 0444, mdev->dbg_dir, mdev,
			    &vdev_info_ops);

	debugfs_create_file("msi_irq_info", 0444, mdev->dbg_dir, mdev,
			    &msi_irq_info_ops);
}
+0 −6
Original line number Diff line number Diff line
@@ -64,9 +64,6 @@ extern struct cosm_hw_ops cosm_hw_ops;
 * @bootaddr: MIC boot address.
 * @dp: virtio device page
 * @dp_dma_addr: virtio device page DMA address.
 * @name: name for the misc char device
 * @miscdev: registered misc char device
 * @vdev_list: list of virtio devices.
 * @dma_mbdev: MIC BUS DMA device.
 * @dma_ch - Array of DMA channels
 * @num_dma_ch - Number of DMA channels available
@@ -91,9 +88,6 @@ struct mic_device {
	u32 bootaddr;
	void *dp;
	dma_addr_t dp_dma_addr;
	char name[16];
	struct miscdevice miscdev;
	struct list_head vdev_list;
	struct mbus_device *dma_mbdev;
	struct dma_chan *dma_ch[MIC_MAX_DMA_CHAN];
	int num_dma_ch;

drivers/misc/mic/host/mic_fops.c

deleted100644 → 0
+0 −222
Original line number Diff line number Diff line
/*
 * Intel MIC Platform Software Stack (MPSS)
 *
 * Copyright(c) 2013 Intel Corporation.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License, version 2, as
 * published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * General Public License for more details.
 *
 * The full GNU General Public License is included in this distribution in
 * the file called "COPYING".
 *
 * Intel MIC Host driver.
 *
 */
#include <linux/poll.h>
#include <linux/pci.h>

#include <linux/mic_common.h>
#include "../common/mic_dev.h"
#include "mic_device.h"
#include "mic_fops.h"
#include "mic_virtio.h"

int mic_open(struct inode *inode, struct file *f)
{
	struct mic_vdev *mvdev;
	struct mic_device *mdev = container_of(f->private_data,
		struct mic_device, miscdev);

	mvdev = kzalloc(sizeof(*mvdev), GFP_KERNEL);
	if (!mvdev)
		return -ENOMEM;

	init_waitqueue_head(&mvdev->waitq);
	INIT_LIST_HEAD(&mvdev->list);
	mvdev->mdev = mdev;
	mvdev->virtio_id = -1;

	f->private_data = mvdev;
	return 0;
}

int mic_release(struct inode *inode, struct file *f)
{
	struct mic_vdev *mvdev = (struct mic_vdev *)f->private_data;

	if (-1 != mvdev->virtio_id)
		mic_virtio_del_device(mvdev);
	f->private_data = NULL;
	kfree(mvdev);
	return 0;
}

long mic_ioctl(struct file *f, unsigned int cmd, unsigned long arg)
{
	struct mic_vdev *mvdev = (struct mic_vdev *)f->private_data;
	void __user *argp = (void __user *)arg;
	int ret;

	switch (cmd) {
	case MIC_VIRTIO_ADD_DEVICE:
	{
		ret = mic_virtio_add_device(mvdev, argp);
		if (ret < 0) {
			dev_err(mic_dev(mvdev),
				"%s %d errno ret %d\n",
				__func__, __LINE__, ret);
			return ret;
		}
		break;
	}
	case MIC_VIRTIO_COPY_DESC:
	{
		struct mic_copy_desc copy;

		ret = mic_vdev_inited(mvdev);
		if (ret)
			return ret;

		if (copy_from_user(&copy, argp, sizeof(copy)))
			return -EFAULT;

		dev_dbg(mic_dev(mvdev),
			"%s %d === iovcnt 0x%x vr_idx 0x%x update_used %d\n",
			__func__, __LINE__, copy.iovcnt, copy.vr_idx,
			copy.update_used);

		ret = mic_virtio_copy_desc(mvdev, &copy);
		if (ret < 0) {
			dev_err(mic_dev(mvdev),
				"%s %d errno ret %d\n",
				__func__, __LINE__, ret);
			return ret;
		}
		if (copy_to_user(
			&((struct mic_copy_desc __user *)argp)->out_len,
			&copy.out_len, sizeof(copy.out_len))) {
			dev_err(mic_dev(mvdev), "%s %d errno ret %d\n",
				__func__, __LINE__, -EFAULT);
			return -EFAULT;
		}
		break;
	}
	case MIC_VIRTIO_CONFIG_CHANGE:
	{
		ret = mic_vdev_inited(mvdev);
		if (ret)
			return ret;

		ret = mic_virtio_config_change(mvdev, argp);
		if (ret < 0) {
			dev_err(mic_dev(mvdev),
				"%s %d errno ret %d\n",
				__func__, __LINE__, ret);
			return ret;
		}
		break;
	}
	default:
		return -ENOIOCTLCMD;
	};
	return 0;
}

/*
 * We return POLLIN | POLLOUT from poll when new buffers are enqueued, and
 * not when previously enqueued buffers may be available. This means that
 * in the card->host (TX) path, when userspace is unblocked by poll it
 * must drain all available descriptors or it can stall.
 */
unsigned int mic_poll(struct file *f, poll_table *wait)
{
	struct mic_vdev *mvdev = (struct mic_vdev *)f->private_data;
	int mask = 0;

	poll_wait(f, &mvdev->waitq, wait);

	if (mic_vdev_inited(mvdev)) {
		mask = POLLERR;
	} else if (mvdev->poll_wake) {
		mvdev->poll_wake = 0;
		mask = POLLIN | POLLOUT;
	}

	return mask;
}

static inline int
mic_query_offset(struct mic_vdev *mvdev, unsigned long offset,
		 unsigned long *size, unsigned long *pa)
{
	struct mic_device *mdev = mvdev->mdev;
	unsigned long start = MIC_DP_SIZE;
	int i;

	/*
	 * MMAP interface is as follows:
	 * offset				region
	 * 0x0					virtio device_page
	 * 0x1000				first vring
	 * 0x1000 + size of 1st vring		second vring
	 * ....
	 */
	if (!offset) {
		*pa = virt_to_phys(mdev->dp);
		*size = MIC_DP_SIZE;
		return 0;
	}

	for (i = 0; i < mvdev->dd->num_vq; i++) {
		struct mic_vringh *mvr = &mvdev->mvr[i];
		if (offset == start) {
			*pa = virt_to_phys(mvr->vring.va);
			*size = mvr->vring.len;
			return 0;
		}
		start += mvr->vring.len;
	}
	return -1;
}

/*
 * Maps the device page and virtio rings to user space for readonly access.
 */
int
mic_mmap(struct file *f, struct vm_area_struct *vma)
{
	struct mic_vdev *mvdev = (struct mic_vdev *)f->private_data;
	unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;
	unsigned long pa, size = vma->vm_end - vma->vm_start, size_rem = size;
	int i, err;

	err = mic_vdev_inited(mvdev);
	if (err)
		return err;

	if (vma->vm_flags & VM_WRITE)
		return -EACCES;

	while (size_rem) {
		i = mic_query_offset(mvdev, offset, &size, &pa);
		if (i < 0)
			return -EINVAL;
		err = remap_pfn_range(vma, vma->vm_start + offset,
			pa >> PAGE_SHIFT, size, vma->vm_page_prot);
		if (err)
			return err;
		dev_dbg(mic_dev(mvdev),
			"%s %d type %d size 0x%lx off 0x%lx pa 0x%lx vma 0x%lx\n",
			__func__, __LINE__, mvdev->virtio_id, size, offset,
			pa, vma->vm_start + offset);
		size_rem -= size;
		offset += size;
	}
	return 0;
}
Loading