/*
 * 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.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 *
 * Copyright (C) 2013 Freescale Semiconductor, Inc.
 * Author: Varun Sethi <varun.sethi@freescale.com>
 *
 */

#define pr_fmt(fmt)    "fsl-pamu-domain: %s: " fmt, __func__

#include <linux/init.h>
#include <linux/iommu.h>
#include <linux/notifier.h>
#include <linux/slab.h>
#include <linux/module.h>
#include <linux/types.h>
#include <linux/mm.h>
#include <linux/interrupt.h>
#include <linux/device.h>
#include <linux/of_platform.h>
#include <linux/bootmem.h>
#include <linux/err.h>
#include <asm/io.h>
#include <asm/bitops.h>

#include <asm/pci-bridge.h>
#include <sysdev/fsl_pci.h>

#include "fsl_pamu_domain.h"

/*
 * Global spinlock that needs to be held while
 * configuring PAMU.
 */
static DEFINE_SPINLOCK(iommu_lock);

static struct kmem_cache *fsl_pamu_domain_cache;
static struct kmem_cache *iommu_devinfo_cache;
static DEFINE_SPINLOCK(device_domain_lock);

static int __init iommu_init_mempool(void)
{

	fsl_pamu_domain_cache = kmem_cache_create("fsl_pamu_domain",
					 sizeof(struct fsl_dma_domain),
					 0,
					 SLAB_HWCACHE_ALIGN,

					 NULL);
	if (!fsl_pamu_domain_cache) {
		pr_debug("Couldn't create fsl iommu_domain cache\n");
		return -ENOMEM;
	}

	iommu_devinfo_cache = kmem_cache_create("iommu_devinfo",
					 sizeof(struct device_domain_info),
					 0,
					 SLAB_HWCACHE_ALIGN,
					 NULL);
	if (!iommu_devinfo_cache) {
		pr_debug("Couldn't create devinfo cache\n");
		kmem_cache_destroy(fsl_pamu_domain_cache);
		return -ENOMEM;
	}

	return 0;
}

static phys_addr_t get_phys_addr(struct fsl_dma_domain *dma_domain, dma_addr_t iova)
{
	u32 win_cnt = dma_domain->win_cnt;
	struct dma_window *win_ptr =
				&dma_domain->win_arr[0];
	struct iommu_domain_geometry *geom;

	geom = &dma_domain->iommu_domain->geometry;

	if (!win_cnt || !dma_domain->geom_size) {
		pr_debug("Number of windows/geometry not configured for the domain\n");
		return 0;
	}

	if (win_cnt > 1) {
		u64 subwin_size;
		dma_addr_t subwin_iova;
		u32 wnd;

		subwin_size = dma_domain->geom_size >> ilog2(win_cnt);
		subwin_iova = iova & ~(subwin_size - 1);
		wnd = (subwin_iova - geom->aperture_start) >> ilog2(subwin_size);
		win_ptr = &dma_domain->win_arr[wnd];
	}

	if (win_ptr->valid)
		return (win_ptr->paddr + (iova & (win_ptr->size - 1)));

	return 0;
}

static int map_subwins(int liodn, struct fsl_dma_domain *dma_domain)
{
	struct dma_window *sub_win_ptr =
				&dma_domain->win_arr[0];
	int i, ret;
	unsigned long rpn, flags;

	for (i = 0; i < dma_domain->win_cnt; i++) {
		if (sub_win_ptr[i].valid) {
			rpn = sub_win_ptr[i].paddr >>
				 PAMU_PAGE_SHIFT;
			spin_lock_irqsave(&iommu_lock, flags);
			ret = pamu_config_spaace(liodn, dma_domain->win_cnt, i,
						 sub_win_ptr[i].size,
						 ~(u32)0,
						 rpn,
						 dma_domain->snoop_id,
						 dma_domain->stash_id,
						 (i > 0) ? 1 : 0,
						 sub_win_ptr[i].prot);
			spin_unlock_irqrestore(&iommu_lock, flags);
			if (ret) {
				pr_debug("PAMU SPAACE configuration failed for liodn %d\n",
					 liodn);
				return ret;
			}
		}
	}

	return ret;
}

static int map_win(int liodn, struct fsl_dma_domain *dma_domain)
{
	int ret;
	struct dma_window *wnd = &dma_domain->win_arr[0];
	phys_addr_t wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;
	unsigned long flags;

	spin_lock_irqsave(&iommu_lock, flags);
	ret = pamu_config_ppaace(liodn, wnd_addr,
				 wnd->size,
				 ~(u32)0,
				 wnd->paddr >> PAMU_PAGE_SHIFT,
				 dma_domain->snoop_id, dma_domain->stash_id,
				 0, wnd->prot);
	spin_unlock_irqrestore(&iommu_lock, flags);
	if (ret)
		pr_debug("PAMU PAACE configuration failed for liodn %d\n",
			liodn);

	return ret;
}

/* Map the DMA window corresponding to the LIODN */
static int map_liodn(int liodn, struct fsl_dma_domain *dma_domain)
{
	if (dma_domain->win_cnt > 1)
		return map_subwins(liodn, dma_domain);
	else
		return map_win(liodn, dma_domain);

}

/* Update window/subwindow mapping for the LIODN */
static int update_liodn(int liodn, struct fsl_dma_domain *dma_domain, u32 wnd_nr)
{
	int ret;
	struct dma_window *wnd = &dma_domain->win_arr[wnd_nr];
	unsigned long flags;

	spin_lock_irqsave(&iommu_lock, flags);
	if (dma_domain->win_cnt > 1) {
		ret = pamu_config_spaace(liodn, dma_domain->win_cnt, wnd_nr,
					 wnd->size,
					 ~(u32)0,
					 wnd->paddr >> PAMU_PAGE_SHIFT,
					 dma_domain->snoop_id,
					 dma_domain->stash_id,
					 (wnd_nr > 0) ? 1 : 0,
					 wnd->prot);
		if (ret)
			pr_debug("Subwindow reconfiguration failed for liodn %d\n", liodn);
	} else {
		phys_addr_t wnd_addr;

		wnd_addr = dma_domain->iommu_domain->geometry.aperture_start;

		ret = pamu_config_ppaace(liodn, wnd_addr,
					 wnd->size,
					 ~(u32)0,
					 wnd->paddr >> PAMU_PAGE_SHIFT,
					dma_domain->snoop_id, dma_domain->stash_id,
					0, wnd->prot);
		if (ret)
			pr_debug("Window reconfiguration failed for liodn %d\n", liodn);
	}

	spin_unlock_irqrestore(&iommu_lock, flags);

	return ret;
}

static int update_liodn_stash(int liodn, struct fsl_dma_domain *dma_domain,
				 u32 val)
{
	int ret = 0, i;
	unsigned long flags;

	spin_lock_irqsave(&iommu_lock, flags);
	if (!dma_domain->win_arr) {
		pr_debug("Windows not configured, stash destination update failed for liodn %d\n", liodn);
		spin_unlock_irqrestore(&iommu_lock, flags);
		return -EINVAL;
	}

	for (i = 0; i < dma_domain->win_cnt; i++) {
		ret = pamu_update_paace_stash(liodn, i, val);
		if (ret) {
			pr_debug("Failed to update SPAACE %d field for liodn %d\n ", i, liodn);
			spin_unlock_irqrestore(&iommu_lock, flags);
			return ret;
		}
	}

	spin_unlock_irqrestore(&iommu_lock, flags);

	return ret;
}

/* Set the geometry parameters for a LIODN */
static int pamu_set_liodn(int liodn, struct device *dev,
			   struct fsl_dma_domain *dma_domain,
			   struct iommu_domain_geometry *geom_attr,
			   u32 win_cnt)
{
	phys_addr_t window_addr, window_size;
	phys_addr_t subwin_size;
	int ret = 0, i;
	u32 omi_index = ~(u32)0;
	unsigned long flags;

	/*
	 * Configure the omi_index at the geometry setup time.
	 * This is a static value which depends on the type of
	 * device and would not change thereafter.
	 */
	get_ome_index(&omi_index, dev);

	window_addr = geom_attr->aperture_start;
	window_size = dma_domain->geom_size;

	spin_lock_irqsave(&iommu_lock, flags);
	ret = pamu_disable_liodn(liodn);
	if (!ret)
		ret = pamu_config_ppaace(liodn, window_addr, window_size, omi_index,
					 0, dma_domain->snoop_id,
					 dma_domain->stash_id, win_cnt, 0);
	spin_unlock_irqrestore(&iommu_lock, flags);
	if (ret) {
		pr_debug("PAMU PAACE configuration failed for liodn %d, win_cnt =%d\n", liodn, win_cnt);
		return ret;
	}

	if (win_cnt > 1) {
		subwin_size = window_size >> ilog2(win_cnt);
		for (i = 0; i < win_cnt; i++) {
			spin_lock_irqsave(&iommu_lock, flags);
			ret = pamu_disable_spaace(liodn, i);
			if (!ret)
				ret = pamu_config_spaace(liodn, win_cnt, i,
							 subwin_size, omi_index,
							 0, dma_domain->snoop_id,
							 dma_domain->stash_id,
							 0, 0);
			spin_unlock_irqrestore(&iommu_lock, flags);
			if (ret) {
				pr_debug("PAMU SPAACE configuration failed for liodn %d\n", liodn);
				return ret;
			}
		}
	}

	return ret;
}

static int check_size(u64 size, dma_addr_t iova)
{
	/*
	 * Size must be a power of two and at least be equal
	 * to PAMU page size.
	 */
	if ((size & (size - 1)) || size < PAMU_PAGE_SIZE) {
		pr_debug("%s: size too small or not a power of two\n", __func__);
		return -EINVAL;
	}

	/* iova must be page size aligned*/
	if (iova & (size - 1)) {
		pr_debug("%s: address is not aligned with window size\n", __func__);
		return -EINVAL;
	}

	return 0;
}

static struct fsl_dma_domain *iommu_alloc_dma_domain(void)
{
	struct fsl_dma_domain *domain;

	domain = kmem_cache_zalloc(fsl_pamu_domain_cache, GFP_KERNEL);
	if (!domain)
		return NULL;

	domain->stash_id = ~(u32)0;
	domain->snoop_id = ~(u32)0;
	domain->win_cnt = pamu_get_max_subwin_cnt();
	domain->geom_size = 0;

	INIT_LIST_HEAD(&domain->devices);

	spin_lock_init(&domain->domain_lock);

	return domain;
}

static void remove_device_ref(struct device_domain_info *info, u32 win_cnt)
{
	unsigned long flags;

	list_del(&info->link);
	spin_lock_irqsave(&iommu_lock, flags);
	if (win_cnt > 1)
		pamu_free_subwins(info->liodn);
	pamu_disable_liodn(info->liodn);
	spin_unlock_irqrestore(&iommu_lock, flags);
	spin_lock_irqsave(&device_domain_lock, flags);
	info->dev->archdata.iommu_domain = NULL;
	kmem_cache_free(iommu_devinfo_cache, info);
	spin_unlock_irqrestore(&device_domain_lock, flags);
}

static void detach_device(struct device *dev, struct fsl_dma_domain *dma_domain)
{
	struct device_domain_info *info, *tmp;
	unsigned long flags;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	/* Remove the device from the domain device list */
	list_for_each_entry_safe(info, tmp, &dma_domain->devices, link) {
		if (!dev || (info->dev == dev))
			remove_device_ref(info, dma_domain->win_cnt);
	}
	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
}

static void attach_device(struct fsl_dma_domain *dma_domain, int liodn, struct device *dev)
{
	struct device_domain_info *info, *old_domain_info;
	unsigned long flags;

	spin_lock_irqsave(&device_domain_lock, flags);
	/*
	 * Check here if the device is already attached to domain or not.
	 * If the device is already attached to a domain detach it.
	 */
	old_domain_info = dev->archdata.iommu_domain;
	if (old_domain_info && old_domain_info->domain != dma_domain) {
		spin_unlock_irqrestore(&device_domain_lock, flags);
		detach_device(dev, old_domain_info->domain);
		spin_lock_irqsave(&device_domain_lock, flags);
	}

	info = kmem_cache_zalloc(iommu_devinfo_cache, GFP_ATOMIC);

	info->dev = dev;
	info->liodn = liodn;
	info->domain = dma_domain;

	list_add(&info->link, &dma_domain->devices);
	/*
	 * In case of devices with multiple LIODNs just store
	 * the info for the first LIODN as all
	 * LIODNs share the same domain
	 */
	if (!dev->archdata.iommu_domain)
		dev->archdata.iommu_domain = info;
	spin_unlock_irqrestore(&device_domain_lock, flags);

}

static phys_addr_t fsl_pamu_iova_to_phys(struct iommu_domain *domain,
					    dma_addr_t iova)
{
	struct fsl_dma_domain *dma_domain = domain->priv;

	if ((iova < domain->geometry.aperture_start) ||
		iova > (domain->geometry.aperture_end))
		return 0;

	return get_phys_addr(dma_domain, iova);
}

static bool fsl_pamu_capable(enum iommu_cap cap)
{
	return cap == IOMMU_CAP_CACHE_COHERENCY;
}

static void fsl_pamu_domain_destroy(struct iommu_domain *domain)
{
	struct fsl_dma_domain *dma_domain = domain->priv;

	domain->priv = NULL;

	/* remove all the devices from the device list */
	detach_device(NULL, dma_domain);

	dma_domain->enabled = 0;
	dma_domain->mapped = 0;

	kmem_cache_free(fsl_pamu_domain_cache, dma_domain);
}

static int fsl_pamu_domain_init(struct iommu_domain *domain)
{
	struct fsl_dma_domain *dma_domain;

	dma_domain = iommu_alloc_dma_domain();
	if (!dma_domain) {
		pr_debug("dma_domain allocation failed\n");
		return -ENOMEM;
	}
	domain->priv = dma_domain;
	dma_domain->iommu_domain = domain;
	/* defaul geometry 64 GB i.e. maximum system address */
	domain->geometry.aperture_start = 0;
	domain->geometry.aperture_end = (1ULL << 36) - 1;
	domain->geometry.force_aperture = true;

	return 0;
}

/* Configure geometry settings for all LIODNs associated with domain */
static int pamu_set_domain_geometry(struct fsl_dma_domain *dma_domain,
				    struct iommu_domain_geometry *geom_attr,
				    u32 win_cnt)
{
	struct device_domain_info *info;
	int ret = 0;

	list_for_each_entry(info, &dma_domain->devices, link) {
		ret = pamu_set_liodn(info->liodn, info->dev, dma_domain,
				      geom_attr, win_cnt);
		if (ret)
			break;
	}

	return ret;
}

/* Update stash destination for all LIODNs associated with the domain */
static int update_domain_stash(struct fsl_dma_domain *dma_domain, u32 val)
{
	struct device_domain_info *info;
	int ret = 0;

	list_for_each_entry(info, &dma_domain->devices, link) {
		ret = update_liodn_stash(info->liodn, dma_domain, val);
		if (ret)
			break;
	}

	return ret;
}

/* Update domain mappings for all LIODNs associated with the domain */
static int update_domain_mapping(struct fsl_dma_domain *dma_domain, u32 wnd_nr)
{
	struct device_domain_info *info;
	int ret = 0;

	list_for_each_entry(info, &dma_domain->devices, link) {
		ret = update_liodn(info->liodn, dma_domain, wnd_nr);
		if (ret)
			break;
	}
	return ret;
}

static int disable_domain_win(struct fsl_dma_domain *dma_domain, u32 wnd_nr)
{
	struct device_domain_info *info;
	int ret = 0;

	list_for_each_entry(info, &dma_domain->devices, link) {
		if (dma_domain->win_cnt == 1 && dma_domain->enabled) {
			ret = pamu_disable_liodn(info->liodn);
			if (!ret)
				dma_domain->enabled = 0;
		} else {
			ret = pamu_disable_spaace(info->liodn, wnd_nr);
		}
	}

	return ret;
}

static void fsl_pamu_window_disable(struct iommu_domain *domain, u32 wnd_nr)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	unsigned long flags;
	int ret;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	if (!dma_domain->win_arr) {
		pr_debug("Number of windows not configured\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return;
	}

	if (wnd_nr >= dma_domain->win_cnt) {
		pr_debug("Invalid window index\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return;
	}

	if (dma_domain->win_arr[wnd_nr].valid) {
		ret = disable_domain_win(dma_domain, wnd_nr);
		if (!ret) {
			dma_domain->win_arr[wnd_nr].valid = 0;
			dma_domain->mapped--;
		}
	}

	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

}

static int fsl_pamu_window_enable(struct iommu_domain *domain, u32 wnd_nr,
				  phys_addr_t paddr, u64 size, int prot)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	struct dma_window *wnd;
	int pamu_prot = 0;
	int ret;
	unsigned long flags;
	u64 win_size;

	if (prot & IOMMU_READ)
		pamu_prot |= PAACE_AP_PERMS_QUERY;
	if (prot & IOMMU_WRITE)
		pamu_prot |= PAACE_AP_PERMS_UPDATE;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	if (!dma_domain->win_arr) {
		pr_debug("Number of windows not configured\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -ENODEV;
	}

	if (wnd_nr >= dma_domain->win_cnt) {
		pr_debug("Invalid window index\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -EINVAL;
	}

	win_size = dma_domain->geom_size >> ilog2(dma_domain->win_cnt);
	if (size > win_size) {
		pr_debug("Invalid window size \n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -EINVAL;
	}

	if (dma_domain->win_cnt == 1) {
		if (dma_domain->enabled) {
			pr_debug("Disable the window before updating the mapping\n");
			spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
			return -EBUSY;
		}

		ret = check_size(size, domain->geometry.aperture_start);
		if (ret) {
			pr_debug("Aperture start not aligned to the size\n");
			spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
			return -EINVAL;
		}
	}

	wnd = &dma_domain->win_arr[wnd_nr];
	if (!wnd->valid) {
		wnd->paddr = paddr;
		wnd->size = size;
		wnd->prot = pamu_prot;

		ret = update_domain_mapping(dma_domain, wnd_nr);
		if (!ret) {
			wnd->valid = 1;
			dma_domain->mapped++;
		}
	} else {
		pr_debug("Disable the window before updating the mapping\n");
		ret = -EBUSY;
	}

	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return ret;
}

/*
 * Attach the LIODN to the DMA domain and configure the geometry
 * and window mappings.
 */
static int handle_attach_device(struct fsl_dma_domain *dma_domain,
				 struct device *dev, const u32 *liodn,
				 int num)
{
	unsigned long flags;
	struct iommu_domain *domain = dma_domain->iommu_domain;
	int ret = 0;
	int i;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	for (i = 0; i < num; i++) {

		/* Ensure that LIODN value is valid */
		if (liodn[i] >= PAACE_NUMBER_ENTRIES) {
			pr_debug("Invalid liodn %d, attach device failed for %s\n",
				liodn[i], dev->of_node->full_name);
			ret = -EINVAL;
			break;
		}

		attach_device(dma_domain, liodn[i], dev);
		/*
		 * Check if geometry has already been configured
		 * for the domain. If yes, set the geometry for
		 * the LIODN.
		 */
		if (dma_domain->win_arr) {
			u32 win_cnt = dma_domain->win_cnt > 1 ? dma_domain->win_cnt : 0;
			ret = pamu_set_liodn(liodn[i], dev, dma_domain,
					      &domain->geometry,
					      win_cnt);
			if (ret)
				break;
			if (dma_domain->mapped) {
				/*
				 * Create window/subwindow mapping for
				 * the LIODN.
				 */
				ret = map_liodn(liodn[i], dma_domain);
				if (ret)
					break;
			}
		}
	}
	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return ret;
}

static int fsl_pamu_attach_device(struct iommu_domain *domain,
				  struct device *dev)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	const u32 *liodn;
	u32 liodn_cnt;
	int len, ret = 0;
	struct pci_dev *pdev = NULL;
	struct pci_controller *pci_ctl;

	/*
	 * Use LIODN of the PCI controller while attaching a
	 * PCI device.
	 */
	if (dev_is_pci(dev)) {
		pdev = to_pci_dev(dev);
		pci_ctl = pci_bus_to_host(pdev->bus);
		/*
		 * make dev point to pci controller device
		 * so we can get the LIODN programmed by
		 * u-boot.
		 */
		dev = pci_ctl->parent;
	}

	liodn = of_get_property(dev->of_node, "fsl,liodn", &len);
	if (liodn) {
		liodn_cnt = len / sizeof(u32);
		ret = handle_attach_device(dma_domain, dev,
					 liodn, liodn_cnt);
	} else {
		pr_debug("missing fsl,liodn property at %s\n",
		          dev->of_node->full_name);
			ret = -EINVAL;
	}

	return ret;
}

static void fsl_pamu_detach_device(struct iommu_domain *domain,
				      struct device *dev)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	const u32 *prop;
	int len;
	struct pci_dev *pdev = NULL;
	struct pci_controller *pci_ctl;

	/*
	 * Use LIODN of the PCI controller while detaching a
	 * PCI device.
	 */
	if (dev_is_pci(dev)) {
		pdev = to_pci_dev(dev);
		pci_ctl = pci_bus_to_host(pdev->bus);
		/*
		 * make dev point to pci controller device
		 * so we can get the LIODN programmed by
		 * u-boot.
		 */
		dev = pci_ctl->parent;
	}

	prop = of_get_property(dev->of_node, "fsl,liodn", &len);
	if (prop)
		detach_device(dev, dma_domain);
	else
		pr_debug("missing fsl,liodn property at %s\n",
		          dev->of_node->full_name);
}

static  int configure_domain_geometry(struct iommu_domain *domain, void *data)
{
	struct iommu_domain_geometry *geom_attr = data;
	struct fsl_dma_domain *dma_domain = domain->priv;
	dma_addr_t geom_size;
	unsigned long flags;

	geom_size = geom_attr->aperture_end - geom_attr->aperture_start + 1;
	/*
	 * Sanity check the geometry size. Also, we do not support
	 * DMA outside of the geometry.
	 */
	if (check_size(geom_size, geom_attr->aperture_start) ||
		!geom_attr->force_aperture) {
			pr_debug("Invalid PAMU geometry attributes\n");
			return -EINVAL;
		}

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	if (dma_domain->enabled) {
		pr_debug("Can't set geometry attributes as domain is active\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return  -EBUSY;
	}

	/* Copy the domain geometry information */
	memcpy(&domain->geometry, geom_attr,
	       sizeof(struct iommu_domain_geometry));
	dma_domain->geom_size = geom_size;

	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return 0;
}

/* Set the domain stash attribute */
static int configure_domain_stash(struct fsl_dma_domain *dma_domain, void *data)
{
	struct pamu_stash_attribute *stash_attr = data;
	unsigned long flags;
	int ret;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);

	memcpy(&dma_domain->dma_stash, stash_attr,
		 sizeof(struct pamu_stash_attribute));

	dma_domain->stash_id = get_stash_id(stash_attr->cache,
					    stash_attr->cpu);
	if (dma_domain->stash_id == ~(u32)0) {
		pr_debug("Invalid stash attributes\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -EINVAL;
	}

	ret = update_domain_stash(dma_domain, dma_domain->stash_id);

	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return ret;
}

/* Configure domain dma state i.e. enable/disable DMA*/
static int configure_domain_dma_state(struct fsl_dma_domain *dma_domain, bool enable)
{
	struct device_domain_info *info;
	unsigned long flags;
	int ret;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);

	if (enable && !dma_domain->mapped) {
		pr_debug("Can't enable DMA domain without valid mapping\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -ENODEV;
	}

	dma_domain->enabled = enable;
	list_for_each_entry(info, &dma_domain->devices,
				 link) {
		ret = (enable) ? pamu_enable_liodn(info->liodn) :
			pamu_disable_liodn(info->liodn);
		if (ret)
			pr_debug("Unable to set dma state for liodn %d",
				 info->liodn);
	}
	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return 0;
}

static int fsl_pamu_set_domain_attr(struct iommu_domain *domain,
				 enum iommu_attr attr_type, void *data)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	int ret = 0;


	switch (attr_type) {
	case DOMAIN_ATTR_GEOMETRY:
		ret = configure_domain_geometry(domain, data);
		break;
	case DOMAIN_ATTR_FSL_PAMU_STASH:
		ret = configure_domain_stash(dma_domain, data);
		break;
	case DOMAIN_ATTR_FSL_PAMU_ENABLE:
		ret = configure_domain_dma_state(dma_domain, *(int *)data);
		break;
	default:
		pr_debug("Unsupported attribute type\n");
		ret = -EINVAL;
		break;
	};

	return ret;
}

static int fsl_pamu_get_domain_attr(struct iommu_domain *domain,
				 enum iommu_attr attr_type, void *data)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	int ret = 0;


	switch (attr_type) {
	case DOMAIN_ATTR_FSL_PAMU_STASH:
		memcpy((struct pamu_stash_attribute *) data, &dma_domain->dma_stash,
				 sizeof(struct pamu_stash_attribute));
		break;
	case DOMAIN_ATTR_FSL_PAMU_ENABLE:
		*(int *)data = dma_domain->enabled;
		break;
	case DOMAIN_ATTR_FSL_PAMUV1:
		*(int *)data = DOMAIN_ATTR_FSL_PAMUV1;
		break;
	default:
		pr_debug("Unsupported attribute type\n");
		ret = -EINVAL;
		break;
	};

	return ret;
}

static struct iommu_group *get_device_iommu_group(struct device *dev)
{
	struct iommu_group *group;

	group = iommu_group_get(dev);
	if (!group)
		group = iommu_group_alloc();

	return group;
}

static  bool check_pci_ctl_endpt_part(struct pci_controller *pci_ctl)
{
	u32 version;

	/* Check the PCI controller version number by readding BRR1 register */
	version = in_be32(pci_ctl->cfg_addr + (PCI_FSL_BRR1 >> 2));
	version &= PCI_FSL_BRR1_VER;
	/* If PCI controller version is >= 0x204 we can partition endpoints*/
	if (version >= 0x204)
		return 1;

	return 0;
}

/* Get iommu group information from peer devices or devices on the parent bus */
static struct iommu_group *get_shared_pci_device_group(struct pci_dev *pdev)
{
	struct pci_dev *tmp;
	struct iommu_group *group;
	struct pci_bus *bus = pdev->bus;

	/*
	 * Traverese the pci bus device list to get
	 * the shared iommu group.
	 */
	while (bus) {
		list_for_each_entry(tmp, &bus->devices, bus_list) {
			if (tmp == pdev)
				continue;
			group = iommu_group_get(&tmp->dev);
			if (group)
				return group;
		}

		bus = bus->parent;
	}

	return NULL;
}

static struct iommu_group *get_pci_device_group(struct pci_dev *pdev)
{
	struct pci_controller *pci_ctl;
	bool pci_endpt_partioning;
	struct iommu_group *group = NULL;

	pci_ctl = pci_bus_to_host(pdev->bus);
	pci_endpt_partioning = check_pci_ctl_endpt_part(pci_ctl);
	/* We can partition PCIe devices so assign device group to the device */
	if (pci_endpt_partioning) {
		group = iommu_group_get_for_dev(&pdev->dev);

		/*
		 * PCIe controller is not a paritionable entity
		 * free the controller device iommu_group.
		 */
		if (pci_ctl->parent->iommu_group)
			iommu_group_remove_device(pci_ctl->parent);
	} else {
		/*
		 * All devices connected to the controller will share the
		 * PCI controllers device group. If this is the first
		 * device to be probed for the pci controller, copy the
		 * device group information from the PCI controller device
		 * node and remove the PCI controller iommu group.
		 * For subsequent devices, the iommu group information can
		 * be obtained from sibling devices (i.e. from the bus_devices
		 * link list).
		 */
		if (pci_ctl->parent->iommu_group) {
			group = get_device_iommu_group(pci_ctl->parent);
			iommu_group_remove_device(pci_ctl->parent);
		} else
			group = get_shared_pci_device_group(pdev);
	}

	if (!group)
		group = ERR_PTR(-ENODEV);

	return group;
}

static int fsl_pamu_add_device(struct device *dev)
{
	struct iommu_group *group = ERR_PTR(-ENODEV);
	struct pci_dev *pdev;
	const u32 *prop;
	int ret = 0, len;

	/*
	 * For platform devices we allocate a separate group for
	 * each of the devices.
	 */
	if (dev_is_pci(dev)) {
		pdev = to_pci_dev(dev);
		/* Don't create device groups for virtual PCI bridges */
		if (pdev->subordinate)
			return 0;

		group = get_pci_device_group(pdev);

	} else {
		prop = of_get_property(dev->of_node, "fsl,liodn", &len);
		if (prop)
			group = get_device_iommu_group(dev);
	}

	if (IS_ERR(group))
		return PTR_ERR(group);

	/*
	 * Check if device has already been added to an iommu group.
	 * Group could have already been created for a PCI device in
	 * the iommu_group_get_for_dev path.
	 */
	if (!dev->iommu_group)
		ret = iommu_group_add_device(group, dev);

	iommu_group_put(group);
	return ret;
}

static void fsl_pamu_remove_device(struct device *dev)
{
	iommu_group_remove_device(dev);
}

static int fsl_pamu_set_windows(struct iommu_domain *domain, u32 w_count)
{
	struct fsl_dma_domain *dma_domain = domain->priv;
	unsigned long flags;
	int ret;

	spin_lock_irqsave(&dma_domain->domain_lock, flags);
	/* Ensure domain is inactive i.e. DMA should be disabled for the domain */
	if (dma_domain->enabled) {
		pr_debug("Can't set geometry attributes as domain is active\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return  -EBUSY;
	}

	/* Ensure that the geometry has been set for the domain */
	if (!dma_domain->geom_size) {
		pr_debug("Please configure geometry before setting the number of windows\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -EINVAL;
	}

	/*
	 * Ensure we have valid window count i.e. it should be less than
	 * maximum permissible limit and should be a power of two.
	 */
	if (w_count > pamu_get_max_subwin_cnt() || !is_power_of_2(w_count)) {
		pr_debug("Invalid window count\n");
		spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
		return -EINVAL;
	}

	ret = pamu_set_domain_geometry(dma_domain, &domain->geometry,
				((w_count > 1) ? w_count : 0));
	if (!ret) {
		kfree(dma_domain->win_arr);
		dma_domain->win_arr = kzalloc(sizeof(struct dma_window) *
							  w_count, GFP_ATOMIC);
		if (!dma_domain->win_arr) {
			spin_unlock_irqrestore(&dma_domain->domain_lock, flags);
			return -ENOMEM;
		}
		dma_domain->win_cnt = w_count;
	}
	spin_unlock_irqrestore(&dma_domain->domain_lock, flags);

	return ret;
}

static u32 fsl_pamu_get_windows(struct iommu_domain *domain)
{
	struct fsl_dma_domain *dma_domain = domain->priv;

	return dma_domain->win_cnt;
}

static const struct iommu_ops fsl_pamu_ops = {
	.capable	= fsl_pamu_capable,
	.domain_init	= fsl_pamu_domain_init,
	.domain_destroy = fsl_pamu_domain_destroy,
	.attach_dev	= fsl_pamu_attach_device,
	.detach_dev	= fsl_pamu_detach_device,
	.domain_window_enable = fsl_pamu_window_enable,
	.domain_window_disable = fsl_pamu_window_disable,
	.domain_get_windows = fsl_pamu_get_windows,
	.domain_set_windows = fsl_pamu_set_windows,
	.iova_to_phys	= fsl_pamu_iova_to_phys,
	.domain_set_attr = fsl_pamu_set_domain_attr,
	.domain_get_attr = fsl_pamu_get_domain_attr,
	.add_device	= fsl_pamu_add_device,
	.remove_device	= fsl_pamu_remove_device,
};

int pamu_domain_init(void)
{
	int ret = 0;

	ret = iommu_init_mempool();
	if (ret)
		return ret;

	bus_set_iommu(&platform_bus_type, &fsl_pamu_ops);
	bus_set_iommu(&pci_bus_type, &fsl_pamu_ops);

	return ret;
}
