Ejemplo n.º 1
0
/* unpin, no longer being scanned out: */
int omap_framebuffer_unpin(struct drm_framebuffer *fb)
{
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);
	int ret, i, n = drm_format_num_planes(fb->pixel_format);

	for (i = 0; i < n; i++) {
		struct plane *plane = &omap_fb->planes[i];
		ret = omap_gem_put_paddr(plane->bo);
		if (ret)
			goto fail;
		plane->paddr = 0;
	}

	return 0;

fail:
	return ret;
}
Ejemplo n.º 2
0
static void omap_framebuffer_destroy(struct drm_framebuffer *fb)
{
	struct drm_device *dev = fb->dev;
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);

	DBG("destroy: FB ID: %d (%p)", fb->base.id, fb);

	drm_framebuffer_cleanup(fb);

	if (omap_gem_put_paddr(omap_fb->bo)) {
		dev_err(dev->dev, "could not unmap!\n");
	}

	if (omap_fb->bo) {
		drm_gem_object_unreference_unlocked(omap_fb->bo);
	}

	kfree(omap_fb);
}
Ejemplo n.º 3
0
/* unpin, no longer being scanned out: */
void omap_framebuffer_unpin(struct drm_framebuffer *fb)
{
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);
	int i, n = drm_format_num_planes(fb->pixel_format);

	mutex_lock(&omap_fb->lock);

	omap_fb->pin_count--;

	if (omap_fb->pin_count > 0) {
		mutex_unlock(&omap_fb->lock);
		return;
	}

	for (i = 0; i < n; i++) {
		struct plane *plane = &omap_fb->planes[i];
		omap_gem_put_paddr(plane->bo);
		plane->paddr = 0;
	}

	mutex_unlock(&omap_fb->lock);
}
Ejemplo n.º 4
0
/* pin, prepare for scanout: */
int omap_framebuffer_pin(struct drm_framebuffer *fb)
{
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);
	int ret, i, n = drm_format_num_planes(fb->pixel_format);

	mutex_lock(&omap_fb->lock);

	if (omap_fb->pin_count > 0) {
		omap_fb->pin_count++;
		mutex_unlock(&omap_fb->lock);
		return 0;
	}

	for (i = 0; i < n; i++) {
		struct plane *plane = &omap_fb->planes[i];
		ret = omap_gem_get_paddr(plane->bo, &plane->paddr, true);
		if (ret)
			goto fail;
		omap_gem_dma_sync(plane->bo, DMA_TO_DEVICE);
	}

	omap_fb->pin_count++;

	mutex_unlock(&omap_fb->lock);

	return 0;

fail:
	for (i--; i >= 0; i--) {
		struct plane *plane = &omap_fb->planes[i];
		omap_gem_put_paddr(plane->bo);
		plane->paddr = 0;
	}

	mutex_unlock(&omap_fb->lock);

	return ret;
}
Ejemplo n.º 5
0
/* update ovl info for scanout, handles cases of multi-planar fb's, etc.
 */
void omap_framebuffer_update_scanout(struct drm_framebuffer *fb,
		struct omap_drm_window *win, struct omap_overlay_info *info)
{
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);
	const struct format *format = omap_fb->format;
	struct plane *plane = &omap_fb->planes[0];
	uint32_t x, y, orient = 0;

	info->color_mode = format->dss_format;

	info->pos_x      = win->crtc_x;
	info->pos_y      = win->crtc_y;
	info->out_width  = win->crtc_w;
	info->out_height = win->crtc_h;
	info->width      = win->src_w;
	info->height     = win->src_h;

	x = win->src_x;
	y = win->src_y;

	if (omap_gem_flags(plane->bo) & OMAP_BO_TILED) {
		uint32_t w = win->src_w;
		uint32_t h = win->src_h;

		switch (win->rotation & 0xf) {
		default:
			dev_err(fb->dev->dev, "invalid rotation: %02x",
					(uint32_t)win->rotation);
			/* fallthru to default to no rotation */
		case 0:
		case BIT(DRM_ROTATE_0):
			orient = 0;
			break;
		case BIT(DRM_ROTATE_90):
			orient = MASK_XY_FLIP | MASK_X_INVERT;
			break;
		case BIT(DRM_ROTATE_180):
			orient = MASK_X_INVERT | MASK_Y_INVERT;
			break;
		case BIT(DRM_ROTATE_270):
			orient = MASK_XY_FLIP | MASK_Y_INVERT;
			break;
		}

		if (win->rotation & BIT(DRM_REFLECT_X))
			orient ^= MASK_X_INVERT;

		if (win->rotation & BIT(DRM_REFLECT_Y))
			orient ^= MASK_Y_INVERT;

		/* adjust x,y offset for flip/invert: */
		if (orient & MASK_XY_FLIP)
			swap(w, h);
		if (orient & MASK_Y_INVERT)
			y += h - 1;
		if (orient & MASK_X_INVERT)
			x += w - 1;

		omap_gem_rotated_paddr(plane->bo, orient, x, y, &info->paddr);
		info->rotation_type = OMAP_DSS_ROT_TILER;
		info->screen_width  = omap_gem_tiled_stride(plane->bo, orient);
	} else {
		info->paddr         = get_linear_addr(plane, format, 0, x, y);
		info->rotation_type = OMAP_DSS_ROT_DMA;
		info->screen_width  = plane->pitch;
	}

	/* convert to pixels: */
	info->screen_width /= format->planes[0].stride_bpp;

	if (format->dss_format == OMAP_DSS_COLOR_NV12) {
		plane = &omap_fb->planes[1];

		if (info->rotation_type == OMAP_DSS_ROT_TILER) {
			WARN_ON(!(omap_gem_flags(plane->bo) & OMAP_BO_TILED));
			omap_gem_rotated_paddr(plane->bo, orient,
					x/2, y/2, &info->p_uv_addr);
		} else {
			info->p_uv_addr = get_linear_addr(plane, format, 1, x, y);
		}
	} else {
		info->p_uv_addr = 0;
	}
}
Ejemplo n.º 6
0
struct drm_gem_object *omap_framebuffer_bo(struct drm_framebuffer *fb)
{
	struct omap_framebuffer *omap_fb = to_omap_framebuffer(fb);
	return omap_fb->bo;
}