Ejemplo n.º 1
0
int mdss_iommu_init(void)
{
	struct iommu_domain *domain;
	int domain_idx, i;

	domain_idx = msm_register_domain(&mdp_iommu_layout);
	if (IS_ERR_VALUE(domain_idx))
		return -EINVAL;

	domain = msm_get_iommu_domain(domain_idx);
	if (!domain) {
		pr_err("unable to get iommu domain(%d)\n", domain_idx);
		return -EINVAL;
	}

	iommu_set_fault_handler(domain, mdss_iommu_fault_handler);

	for (i = 0; i < ARRAY_SIZE(mdp_iommu_ctx); i++) {
		mdp_iommu_ctx[i].ctx = msm_iommu_get_ctx(mdp_iommu_ctx[i].name);
		if (!mdp_iommu_ctx[i].ctx) {
			pr_warn("unable to get iommu ctx(%s)\n",
					mdp_iommu_ctx[i].name);
			return -EINVAL;
		}
	}
	mdss_res->iommu_domain = domain_idx;

	return 0;
}
Ejemplo n.º 2
0
/*
 * kgsl_iommu_create_pagetable - Create a IOMMU pagetable
 *
 * Allocate memory to hold a pagetable and allocate the IOMMU
 * domain which is the actual IOMMU pagetable
 * Return - void
 */
void *kgsl_iommu_create_pagetable(void)
{
	struct kgsl_iommu_pt *iommu_pt;

	iommu_pt = kzalloc(sizeof(struct kgsl_iommu_pt), GFP_KERNEL);
	if (!iommu_pt) {
		KGSL_CORE_ERR("kzalloc(%d) failed\n",
				sizeof(struct kgsl_iommu_pt));
		return NULL;
	}
	/* L2 redirect is not stable on IOMMU v2 */
	if (msm_soc_version_supports_iommu_v1())
		iommu_pt->domain = iommu_domain_alloc(&platform_bus_type,
					MSM_IOMMU_DOMAIN_PT_CACHEABLE);
	else
		iommu_pt->domain = iommu_domain_alloc(&platform_bus_type,
					0);
	if (!iommu_pt->domain) {
		KGSL_CORE_ERR("Failed to create iommu domain\n");
		kfree(iommu_pt);
		return NULL;
	} else {
		iommu_set_fault_handler(iommu_pt->domain,
			kgsl_iommu_fault_handler);
	}

	return iommu_pt;
}
Ejemplo n.º 3
0
gceSTATUS
gckIOMMU_Construct(
    IN gckOS Os,
    OUT gckIOMMU * Iommu
    )
{
    gceSTATUS status;
    gckIOMMU iommu = gcvNULL;
    struct device *dev;
    int ret;

    gcmkHEADER();

    dev = &Os->device->platform->device->dev;

    gcmkONERROR(gckOS_Allocate(Os, gcmSIZEOF(gcsIOMMU), (gctPOINTER *)&iommu));

    gckOS_ZeroMemory(iommu, gcmSIZEOF(gcsIOMMU));

    iommu->domain = iommu_domain_alloc(&platform_bus_type);

    if (!iommu->domain)
    {
        gcmkTRACE_ZONE(gcvLEVEL_INFO, gcvZONE_OS, "iommu_domain_alloc() fail");

        gcmkONERROR(gcvSTATUS_NOT_SUPPORTED);
    }

    iommu_set_fault_handler(iommu->domain, _IOMMU_Fault_Handler, dev);

    ret = iommu_attach_device(iommu->domain, dev);

    if (ret)
    {
        gcmkTRACE_ZONE(
            gcvLEVEL_INFO, gcvZONE_OS, "iommu_attach_device() fail %d", ret);

        gcmkONERROR(gcvSTATUS_NOT_SUPPORTED);
    }

    iommu->device = dev;

    _FlatMapping(iommu);

    *Iommu = iommu;

    gcmkFOOTER_NO();
    return gcvSTATUS_OK;

OnError:

    gckIOMMU_Destory(Os, iommu);

    gcmkFOOTER();
    return status;
}
Ejemplo n.º 4
0
struct msm_mmu *msm_iommu_new(struct device *dev, struct iommu_domain *domain)
{
	struct msm_iommu *iommu;

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

	iommu->domain = domain;
	msm_mmu_init(&iommu->base, dev, &funcs);
	iommu_set_fault_handler(domain, msm_fault_handler, iommu);

	return &iommu->base;
}
Ejemplo n.º 5
0
int mdss_iommu_init(struct mdss_data_type *mdata)
{
    struct msm_iova_layout layout;
    struct iommu_domain *domain;
    struct mdss_iommu_map_type *iomap;
    int i;

    if (mdata->iommu_map) {
        pr_warn("iommu already initialized\n");
        return 0;
    }

    for (i = 0; i < MDSS_IOMMU_MAX_DOMAIN; i++) {
        iomap = &mdss_iommu_map[i];

        layout.client_name = iomap->client_name;
        layout.partitions = iomap->partitions;
        layout.npartitions = iomap->npartitions;
        layout.is_secure = (i == MDSS_IOMMU_DOMAIN_SECURE);

        iomap->domain_idx = msm_register_domain(&layout);
        if (IS_ERR_VALUE(iomap->domain_idx))
            return -EINVAL;

        domain = msm_get_iommu_domain(iomap->domain_idx);
        if (!domain) {
            pr_err("unable to get iommu domain(%d)\n",
                   iomap->domain_idx);
            return -EINVAL;
        }
        iommu_set_fault_handler(domain, mdss_iommu_fault_handler, NULL);

        iomap->ctx = msm_iommu_get_ctx(iomap->ctx_name);
        if (!iomap->ctx) {
            pr_warn("unable to get iommu ctx(%s)\n",
                    iomap->ctx_name);
            return -EINVAL;
        }
    }

    mdata->iommu_map = mdss_iommu_map;

    return 0;
}
Ejemplo n.º 6
0
/*
 * kgsl_iommu_create_pagetable - Create a IOMMU pagetable
 *
 * Allocate memory to hold a pagetable and allocate the IOMMU
 * domain which is the actual IOMMU pagetable
 * Return - void
 */
void *kgsl_iommu_create_pagetable(void)
{
	struct kgsl_iommu_pt *iommu_pt;

	iommu_pt = kzalloc(sizeof(struct kgsl_iommu_pt), GFP_KERNEL);
	if (!iommu_pt) {
		KGSL_CORE_ERR("kzalloc(%d) failed\n",
				sizeof(struct kgsl_iommu_pt));
		return NULL;
	}
	iommu_pt->domain = iommu_domain_alloc(&platform_bus_type,
										  MSM_IOMMU_DOMAIN_PT_CACHEABLE);
	if (!iommu_pt->domain) {
		KGSL_CORE_ERR("Failed to create iommu domain\n");
		kfree(iommu_pt);
		return NULL;
	} else {
		iommu_set_fault_handler(iommu_pt->domain,
			kgsl_iommu_fault_handler);
	}

	return iommu_pt;
}
Ejemplo n.º 7
0
static struct msm_panel_common_pdata *mdss_mdp_populate_pdata(
	struct device *dev)
{
	struct msm_panel_common_pdata *pdata;
	struct msm_iova_layout layout;
	struct iommu_domain *domain;
	struct mdss_iommu_map_type *iomap;
	int i;

	if (mdata->iommu_map) {
		pr_warn("iommu already initialized\n");
		return 0;
	}

	for (i = 0; i < MDSS_IOMMU_MAX_DOMAIN; i++) {
		iomap = &mdss_iommu_map[i];

		layout.client_name = iomap->client_name;
		layout.partitions = iomap->partitions;
		layout.npartitions = iomap->npartitions;
		layout.is_secure = (i == MDSS_IOMMU_DOMAIN_SECURE);

		iomap->domain_idx = msm_register_domain(&layout);
		if (IS_ERR_VALUE(iomap->domain_idx))
			return -EINVAL;

		domain = msm_get_iommu_domain(iomap->domain_idx);
		if (!domain) {
			pr_err("unable to get iommu domain(%d)\n",
				iomap->domain_idx);
			return -EINVAL;
		}
		iommu_set_fault_handler(domain, mdss_iommu_fault_handler, NULL);

	pdata = devm_kzalloc(dev, sizeof(*pdata), GFP_KERNEL);
	if (!pdata)
		dev_err(dev, "could not allocate memory for pdata\n");
	return pdata;
}

static u32 mdss_mdp_res_init(struct platform_device *pdev)
{
	u32 rc;

	rc = mdss_mdp_irq_clk_setup(pdev);
	if (rc)
		return rc;

	mdss_res->clk_ctrl_wq = create_singlethread_workqueue("mdp_clk_wq");
	INIT_DELAYED_WORK(&mdss_res->clk_ctrl_worker,
			  mdss_mdp_clk_ctrl_workqueue_handler);

	mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_ON, false);
	mdss_res->rev = MDSS_MDP_REG_READ(MDSS_REG_HW_VERSION);
	mdss_res->mdp_rev = MDSS_MDP_REG_READ(MDSS_MDP_REG_HW_VERSION);
	mdss_mdp_clk_ctrl(MDP_BLOCK_POWER_OFF, false);

	mdss_res->smp_mb_cnt = MDSS_MDP_SMP_MMB_BLOCKS;
	mdss_res->smp_mb_size = MDSS_MDP_SMP_MMB_SIZE;
	mdss_res->pipe_type_map = mdss_mdp_pipe_type_map;
	mdss_res->mixer_type_map = mdss_mdp_mixer_type_map;

	pr_info("mdss_revision=%x\n", mdss_res->rev);
	pr_info("mdp_hw_revision=%x\n", mdss_res->mdp_rev);

	mdss_res->res_init = true;
	mdss_res->timeout = HZ/20;
	mdss_res->clk_ena = false;
	mdss_res->irq_mask = MDSS_MDP_DEFAULT_INTR_MASK;
	mdss_res->suspend = false;
	mdss_res->prim_ptype = NO_PANEL;
	mdss_res->irq_ena = false;

	return 0;
}