struct mtk_drm_gem_obj *mtk_drm_gem_create(struct drm_device *dev,
		unsigned long size, bool alloc_kmap)
{
	struct mtk_drm_gem_obj *mtk_gem;
	struct drm_gem_object *obj;
	int ret;

	mtk_gem = mtk_drm_gem_init(dev, size);
	if (IS_ERR(mtk_gem))
		return ERR_CAST(mtk_gem);

	obj = &mtk_gem->base;

	init_dma_attrs(&mtk_gem->dma_attrs);
	dma_set_attr(DMA_ATTR_WRITE_COMBINE, &mtk_gem->dma_attrs);

	if (!alloc_kmap)
		dma_set_attr(DMA_ATTR_NO_KERNEL_MAPPING, &mtk_gem->dma_attrs);

	mtk_gem->kvaddr = dma_alloc_attrs(dev->dev, obj->size,
			(dma_addr_t *)&mtk_gem->dma_addr, GFP_KERNEL,
			&mtk_gem->dma_attrs);
	if (!mtk_gem->kvaddr) {
		DRM_ERROR("failed to allocate %zx byte dma buffer", obj->size);
		ret = -ENOMEM;
		goto err_dma;
	}

	{
		mtk_gem->sgt = kzalloc(sizeof(*mtk_gem->sgt), GFP_KERNEL);
		if (!mtk_gem->sgt) {
			ret = -ENOMEM;
			goto err_sgt;
		}

		ret = dma_get_sgtable_attrs(dev->dev, mtk_gem->sgt,
			mtk_gem->kvaddr, mtk_gem->dma_addr, obj->size,
			&mtk_gem->dma_attrs);
		if (ret) {
			DRM_ERROR("failed to allocate sgt, %d\n", ret);
			goto err_get_sgtable;
		}
	}

	DRM_INFO("kvaddr = %p dma_addr = %pad\n",
			mtk_gem->kvaddr, &mtk_gem->dma_addr);

	return mtk_gem;
err_get_sgtable:
	kfree(mtk_gem->sgt);
err_sgt:
	dma_free_attrs(dev->dev, obj->size, mtk_gem->kvaddr, mtk_gem->dma_addr,
			&mtk_gem->dma_attrs);
err_dma:
	kfree(mtk_gem);
	return ERR_PTR(ret);
}
Пример #2
0
int msenc_read_ucode(struct platform_device *dev, const char *fw_name)
{
    struct msenc *m = get_msenc(dev);
    const struct firmware *ucode_fw;
    int err;

    m->phys = 0;
    m->mapped = NULL;
    init_dma_attrs(&m->attrs);

    ucode_fw  = nvhost_client_request_firmware(dev, fw_name);
    if (!ucode_fw) {
        dev_err(&dev->dev, "failed to get msenc firmware\n");
        err = -ENOENT;
        return err;
    }

    m->size = ucode_fw->size;
    dma_set_attr(DMA_ATTR_READ_ONLY, &m->attrs);

    m->mapped = dma_alloc_attrs(&dev->dev,
                                m->size, &m->phys,
                                GFP_KERNEL, &m->attrs);
    if (!m->mapped) {
        dev_err(&dev->dev, "dma memory allocation failed");
        err = -ENOMEM;
        goto clean_up;
    }

    err = msenc_setup_ucode_image(dev, m->mapped, ucode_fw);
    if (err) {
        dev_err(&dev->dev, "failed to parse firmware image\n");
        goto clean_up;
    }

    m->valid = true;

    release_firmware(ucode_fw);

    return 0;

clean_up:
    if (m->mapped) {
        dma_free_attrs(&dev->dev,
                       m->size, m->mapped,
                       m->phys, &m->attrs);
        m->mapped = NULL;
    }
    release_firmware(ucode_fw);
    return err;
}
Пример #3
0
static int rockchip_gem_alloc_buf(struct rockchip_gem_object *rk_obj,
                                  bool alloc_kmap)
{
    struct drm_gem_object *obj = &rk_obj->base;
    struct drm_device *drm = obj->dev;

    init_dma_attrs(&rk_obj->dma_attrs);
    dma_set_attr(DMA_ATTR_WRITE_COMBINE, &rk_obj->dma_attrs);

    if (!alloc_kmap)
        dma_set_attr(DMA_ATTR_NO_KERNEL_MAPPING, &rk_obj->dma_attrs);

    rk_obj->kvaddr = dma_alloc_attrs(drm->dev, obj->size,
                                     &rk_obj->dma_addr, GFP_KERNEL,
                                     &rk_obj->dma_attrs);
    if (!rk_obj->kvaddr) {
        DRM_ERROR("failed to allocate %#x byte dma buffer", obj->size);
        return -ENOMEM;
    }

    return 0;
}
Пример #4
0
static int __devinit gpu_probe(struct platform_device *pdev)
#endif
{
    int ret = -ENODEV;
    struct resource* res;
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,0)
	struct contiguous_mem_pool *pool;
	struct reset_control *rstc;
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
	struct device_node *dn =pdev->dev.of_node;
	const u32 *prop;
#else
	struct viv_gpu_platform_data *pdata;
#endif
    gcmkHEADER();

    res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "phys_baseaddr");
    if (res)
        baseAddress = res->start;

    res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "irq_3d");
    if (res)
        irqLine = res->start;

    res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "iobase_3d");
    if (res)
    {
        registerMemBase = res->start;
        registerMemSize = res->end - res->start + 1;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "irq_2d");
    if (res)
        irqLine2D = res->start;

    res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "iobase_2d");
    if (res)
    {
        registerMemBase2D = res->start;
        registerMemSize2D = res->end - res->start + 1;
    }

    res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, "irq_vg");
    if (res)
        irqLineVG = res->start;

    res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "iobase_vg");
    if (res)
    {
        registerMemBaseVG = res->start;
        registerMemSizeVG = res->end - res->start + 1;
    }

#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,0)
	pool = devm_kzalloc(&pdev->dev, sizeof(*pool), GFP_KERNEL);
	if (!pool)
		return -ENOMEM;
	pool->size = contiguousSize;
	init_dma_attrs(&pool->attrs);
	dma_set_attr(DMA_ATTR_WRITE_COMBINE, &pool->attrs);
	pool->virt = dma_alloc_attrs(&pdev->dev, pool->size, &pool->phys,
				     GFP_KERNEL, &pool->attrs);
	if (!pool->virt) {
		dev_err(&pdev->dev, "Failed to allocate contiguous memory\n");
		return -ENOMEM;
	}
	contiguousBase = pool->phys;
	dev_set_drvdata(&pdev->dev, pool);
#elif LINUX_VERSION_CODE >= KERNEL_VERSION(3,5,0)
	prop = of_get_property(dn, "contiguousbase", NULL);
	if(prop)
		contiguousBase = *prop;
	of_property_read_u32(dn,"contiguoussize", (u32 *)&contiguousSize);
#else
    pdata = pdev->dev.platform_data;
    if (pdata) {
        contiguousBase = pdata->reserved_mem_base;
        contiguousSize = pdata->reserved_mem_size;
     }
#endif
    if (contiguousSize == 0)
       gckOS_Print("Warning: No contiguous memory is reserverd for gpu.!\n ");
    ret = drv_init(&pdev->dev);

    if (!ret)
    {
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,0)
	rstc = devm_reset_control_get(&pdev->dev, "gpu3d");
	galDevice->rstc[gcvCORE_MAJOR] = IS_ERR(rstc) ? NULL : rstc;

	rstc = devm_reset_control_get(&pdev->dev, "gpu2d");
	galDevice->rstc[gcvCORE_2D] = IS_ERR(rstc) ? NULL : rstc;

	rstc = devm_reset_control_get(&pdev->dev, "gpuvg");
	galDevice->rstc[gcvCORE_VG] = IS_ERR(rstc) ? NULL : rstc;
#endif
        platform_set_drvdata(pdev, galDevice);

#if gcdENABLE_FSCALE_VAL_ADJUST
        if (galDevice->kernels[gcvCORE_MAJOR])
            REG_THERMAL_NOTIFIER(&thermal_hot_pm_notifier);
#endif
        gcmkFOOTER_NO();
        return ret;
    }
#if gcdENABLE_FSCALE_VAL_ADJUST
    UNREG_THERMAL_NOTIFIER(&thermal_hot_pm_notifier);
#endif
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,10,0)
	dma_free_attrs(&pdev->dev, pool->size, pool->virt, pool->phys,
		       &pool->attrs);
#endif
    gcmkFOOTER_ARG(KERN_INFO "Failed to register gpu driver: %d\n", ret);
    return ret;
}
Пример #5
0
static int lowlevel_buffer_allocate(struct drm_device *dev,
		unsigned int flags, struct rockchip_drm_gem_buf *buf)
{
	int ret = 0;
	enum dma_attr attr;
	unsigned int nr_pages;

	DRM_DEBUG_KMS("%s\n", __FILE__);

	if (buf->dma_addr) {
		DRM_DEBUG_KMS("already allocated.\n");
		return 0;
	}

	init_dma_attrs(&buf->dma_attrs);

	/*
	 * if ROCKCHIP_BO_CONTIG, fully physically contiguous memory
	 * region will be allocated else physically contiguous
	 * as possible.
	 */
	if (!(flags & ROCKCHIP_BO_NONCONTIG))
		dma_set_attr(DMA_ATTR_FORCE_CONTIGUOUS, &buf->dma_attrs);

	/*
	 * if ROCKCHIP_BO_WC or ROCKCHIP_BO_NONCACHABLE, writecombine mapping
	 * else cachable mapping.
	 */
	if (flags & ROCKCHIP_BO_WC || !(flags & ROCKCHIP_BO_CACHABLE))
		attr = DMA_ATTR_WRITE_COMBINE;
	else
		attr = DMA_ATTR_NON_CONSISTENT;

	dma_set_attr(attr, &buf->dma_attrs);
	dma_set_attr(DMA_ATTR_NO_KERNEL_MAPPING, &buf->dma_attrs);

	nr_pages = buf->size >> PAGE_SHIFT;

	if (!is_drm_iommu_supported(dev)) {
		dma_addr_t start_addr;
		unsigned int i = 0;

		buf->pages = kzalloc(sizeof(struct page) * nr_pages,
					GFP_KERNEL);
		if (!buf->pages) {
			DRM_ERROR("failed to allocate pages.\n");
			return -ENOMEM;
		}

		buf->kvaddr = dma_alloc_attrs(dev->dev, buf->size,
					&buf->dma_addr, GFP_KERNEL,
					&buf->dma_attrs);
		if (!buf->kvaddr) {
			DRM_ERROR("failed to allocate buffer.\n");
			kfree(buf->pages);
			return -ENOMEM;
		}

		start_addr = buf->dma_addr;
		while (i < nr_pages) {
			buf->pages[i] = phys_to_page(start_addr);
			start_addr += PAGE_SIZE;
			i++;
		}
	} else {

		buf->pages = dma_alloc_attrs(dev->dev, buf->size,
					&buf->dma_addr, GFP_KERNEL,
					&buf->dma_attrs);
		if (!buf->pages) {
			DRM_ERROR("failed to allocate buffer.\n");
			return -ENOMEM;
		}
	}

	buf->sgt = drm_prime_pages_to_sg(buf->pages, nr_pages);
	if (!buf->sgt) {
		DRM_ERROR("failed to get sg table.\n");
		ret = -ENOMEM;
		goto err_free_attrs;
	}

	DRM_DEBUG_KMS("dma_addr(0x%lx), size(0x%lx)\n",
			(unsigned long)buf->dma_addr,
			buf->size);

	return ret;

err_free_attrs:
	dma_free_attrs(dev->dev, buf->size, buf->pages,
			(dma_addr_t)buf->dma_addr, &buf->dma_attrs);
	buf->dma_addr = (dma_addr_t)NULL;

	if (!is_drm_iommu_supported(dev))
		kfree(buf->pages);

	return ret;
}
Пример #6
0
int pil_mss_reset_load_mba(struct pil_desc *pil)
{
	struct q6v5_data *drv = container_of(pil, struct q6v5_data, desc);
	struct modem_data *md = dev_get_drvdata(pil->dev);
	const struct firmware *fw;
	char fw_name_legacy[10] = "mba.b00";
	char fw_name[10] = "mba.mbn";
	char *fw_name_p;
	void *mba_virt;
	dma_addr_t mba_phys, mba_phys_end;
	int ret, count;
	const u8 *data;

	fw_name_p = drv->non_elf_image ? fw_name_legacy : fw_name;
	/* Load and authenticate mba image */
	ret = request_firmware(&fw, fw_name_p, pil->dev);
	if (ret) {
		dev_err(pil->dev, "Failed to locate %s\n",
						fw_name_p);
		return ret;
	}

	drv->mba_size = SZ_1M;
	md->mba_mem_dev.coherent_dma_mask =
		DMA_BIT_MASK(sizeof(dma_addr_t) * 8);
	init_dma_attrs(&md->attrs_dma);
	dma_set_attr(DMA_ATTR_STRONGLY_ORDERED, &md->attrs_dma);
	mba_virt = dma_alloc_attrs(&md->mba_mem_dev, drv->mba_size,
			&mba_phys, GFP_KERNEL, &md->attrs_dma);
	if (!mba_virt) {
		dev_err(pil->dev, "MBA metadata buffer allocation failed\n");
		ret = -ENOMEM;
		goto err_dma_alloc;
	}

	drv->mba_phys = mba_phys;
	drv->mba_virt = mba_virt;
	mba_phys_end = mba_phys + drv->mba_size;

	dev_info(pil->dev, "MBA: loading from %pa to %pa\n", &mba_phys,
								&mba_phys_end);
	/* Load the MBA image into memory */
	data = fw ? fw->data : NULL;
	if (!data) {
		dev_err(pil->dev, "MBA data is NULL\n");
		ret = -ENOMEM;
		goto err_mss_reset;
	}
	count = fw->size;
	memcpy(mba_virt, data, count);
	wmb();

	ret = pil_mss_reset(pil);
	if (ret) {
		dev_err(pil->dev, "MBA boot failed.\n");
		goto err_mss_reset;
	}

	release_firmware(fw);

	return 0;

err_mss_reset:
	dma_free_attrs(&md->mba_mem_dev, drv->mba_size, drv->mba_virt,
				drv->mba_phys, &md->attrs_dma);
	drv->mba_virt = NULL;
err_dma_alloc:
	release_firmware(fw);
	return ret;
}
Пример #7
0
/**
    * scsi_dma_set_skip_cpu_sync - skip operations for cache coherency
    */
void scsi_dma_set_skip_cpu_sync(void)
{
	init_dma_attrs(&scsi_direct_attrs);
	dma_set_attr(DMA_ATTR_SKIP_CPU_SYNC, &scsi_direct_attrs);
}