| From dcbd4209c29fb5365e011e621a0e52dfddc9d2a4 Mon Sep 17 00:00:00 2001 |
| From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= <ville.syrjala@linux.intel.com> |
| Date: Wed, 24 Apr 2013 18:52:34 +0300 |
| Subject: drm: Add struct drm_rect and assorted utility functions |
| MIME-Version: 1.0 |
| Content-Type: text/plain; charset=UTF-8 |
| Content-Transfer-Encoding: 8bit |
| |
| struct drm_rect represents a simple rectangle. The utility |
| functions are there to help driver writers. |
| |
| v2: Moved the region stuff into its own file, made the smaller funcs |
| static inline, used 64bit maths in the scaled clipping function to |
| avoid overflows (instead it will saturate to INT_MIN or INT_MAX). |
| v3: Renamed drm_region to drm_rect, drm_region_clip to |
| drm_rect_intersect, and drm_region_subsample to drm_rect_downscale. |
| v4: Renamed some function parameters, improve kernel-doc comments a bit, |
| and actually generate documentation for drm_rect.[ch]. |
| v5: s/RETUTRNS/RETURNS/ |
| |
| Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> |
| Reviewed-by: Chris Wilson <chris@chris-wilson.co.uk> |
| Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com> |
| Acked-by: Dave Airlie <airlied@gmail.com> |
| Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch> |
| (cherry picked from commit 3512f976d252bd5d07d04e9e157f0cd210c959a0) |
| Signed-off-by: Darren Hart <dvhart@linux.intel.com> |
| --- |
| Documentation/DocBook/drm.tmpl | 2 + |
| drivers/gpu/drm/Makefile | 3 +- |
| drivers/gpu/drm/drm_rect.c | 96 ++++++++++++++++++++++++++++++ |
| include/drm/drm_rect.h | 132 +++++++++++++++++++++++++++++++++++++++++ |
| 4 files changed, 232 insertions(+), 1 deletion(-) |
| create mode 100644 drivers/gpu/drm/drm_rect.c |
| create mode 100644 include/drm/drm_rect.h |
| |
| diff --git a/Documentation/DocBook/drm.tmpl b/Documentation/DocBook/drm.tmpl |
| index f9df3b872c16..7c7af25b330c 100644 |
| --- a/Documentation/DocBook/drm.tmpl |
| +++ b/Documentation/DocBook/drm.tmpl |
| @@ -1653,6 +1653,8 @@ void intel_crt_init(struct drm_device *dev) |
| <sect2> |
| <title>KMS API Functions</title> |
| !Edrivers/gpu/drm/drm_crtc.c |
| +!Edrivers/gpu/drm/drm_rect.c |
| +!Finclude/drm/drm_rect.h |
| </sect2> |
| </sect1> |
| |
| diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile |
| index 1c9f24396002..1ecbe5b7312d 100644 |
| --- a/drivers/gpu/drm/Makefile |
| +++ b/drivers/gpu/drm/Makefile |
| @@ -12,7 +12,8 @@ drm-y := drm_auth.o drm_buffer.o drm_bufs.o drm_cache.o \ |
| drm_platform.o drm_sysfs.o drm_hashtab.o drm_mm.o \ |
| drm_crtc.o drm_modes.o drm_edid.o \ |
| drm_info.o drm_debugfs.o drm_encoder_slave.o \ |
| - drm_trace_points.o drm_global.o drm_prime.o |
| + drm_trace_points.o drm_global.o drm_prime.o \ |
| + drm_rect.o |
| |
| drm-$(CONFIG_COMPAT) += drm_ioc32.o |
| drm-$(CONFIG_DRM_GEM_CMA_HELPER) += drm_gem_cma_helper.o |
| diff --git a/drivers/gpu/drm/drm_rect.c b/drivers/gpu/drm/drm_rect.c |
| new file mode 100644 |
| index 000000000000..22091ecdbff4 |
| --- /dev/null |
| +++ b/drivers/gpu/drm/drm_rect.c |
| @@ -0,0 +1,96 @@ |
| +/* |
| + * Copyright (C) 2011-2013 Intel Corporation |
| + * |
| + * Permission is hereby granted, free of charge, to any person obtaining a |
| + * copy of this software and associated documentation files (the "Software"), |
| + * to deal in the Software without restriction, including without limitation |
| + * the rights to use, copy, modify, merge, publish, distribute, sublicense, |
| + * and/or sell copies of the Software, and to permit persons to whom the |
| + * Software is furnished to do so, subject to the following conditions: |
| + * |
| + * The above copyright notice and this permission notice (including the next |
| + * paragraph) shall be included in all copies or substantial portions of the |
| + * Software. |
| + * |
| + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
| + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
| + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
| + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
| + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
| + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE |
| + * SOFTWARE. |
| + */ |
| + |
| +#include <linux/errno.h> |
| +#include <linux/export.h> |
| +#include <linux/kernel.h> |
| +#include <drm/drm_rect.h> |
| + |
| +/** |
| + * drm_rect_intersect - intersect two rectangles |
| + * @r1: first rectangle |
| + * @r2: second rectangle |
| + * |
| + * Calculate the intersection of rectangles @r1 and @r2. |
| + * @r1 will be overwritten with the intersection. |
| + * |
| + * RETURNS: |
| + * %true if rectangle @r1 is still visible after the operation, |
| + * %false otherwise. |
| + */ |
| +bool drm_rect_intersect(struct drm_rect *r1, const struct drm_rect *r2) |
| +{ |
| + r1->x1 = max(r1->x1, r2->x1); |
| + r1->y1 = max(r1->y1, r2->y1); |
| + r1->x2 = min(r1->x2, r2->x2); |
| + r1->y2 = min(r1->y2, r2->y2); |
| + |
| + return drm_rect_visible(r1); |
| +} |
| +EXPORT_SYMBOL(drm_rect_intersect); |
| + |
| +/** |
| + * drm_rect_clip_scaled - perform a scaled clip operation |
| + * @src: source window rectangle |
| + * @dst: destination window rectangle |
| + * @clip: clip rectangle |
| + * @hscale: horizontal scaling factor |
| + * @vscale: vertical scaling factor |
| + * |
| + * Clip rectangle @dst by rectangle @clip. Clip rectangle @src by the |
| + * same amounts multiplied by @hscale and @vscale. |
| + * |
| + * RETURNS: |
| + * %true if rectangle @dst is still visible after being clipped, |
| + * %false otherwise |
| + */ |
| +bool drm_rect_clip_scaled(struct drm_rect *src, struct drm_rect *dst, |
| + const struct drm_rect *clip, |
| + int hscale, int vscale) |
| +{ |
| + int diff; |
| + |
| + diff = clip->x1 - dst->x1; |
| + if (diff > 0) { |
| + int64_t tmp = src->x1 + (int64_t) diff * hscale; |
| + src->x1 = clamp_t(int64_t, tmp, INT_MIN, INT_MAX); |
| + } |
| + diff = clip->y1 - dst->y1; |
| + if (diff > 0) { |
| + int64_t tmp = src->y1 + (int64_t) diff * vscale; |
| + src->y1 = clamp_t(int64_t, tmp, INT_MIN, INT_MAX); |
| + } |
| + diff = dst->x2 - clip->x2; |
| + if (diff > 0) { |
| + int64_t tmp = src->x2 - (int64_t) diff * hscale; |
| + src->x2 = clamp_t(int64_t, tmp, INT_MIN, INT_MAX); |
| + } |
| + diff = dst->y2 - clip->y2; |
| + if (diff > 0) { |
| + int64_t tmp = src->y2 - (int64_t) diff * vscale; |
| + src->y2 = clamp_t(int64_t, tmp, INT_MIN, INT_MAX); |
| + } |
| + |
| + return drm_rect_intersect(dst, clip); |
| +} |
| +EXPORT_SYMBOL(drm_rect_clip_scaled); |
| diff --git a/include/drm/drm_rect.h b/include/drm/drm_rect.h |
| new file mode 100644 |
| index 000000000000..2b7278c1bc42 |
| --- /dev/null |
| +++ b/include/drm/drm_rect.h |
| @@ -0,0 +1,132 @@ |
| +/* |
| + * Copyright (C) 2011-2013 Intel Corporation |
| + * |
| + * Permission is hereby granted, free of charge, to any person obtaining a |
| + * copy of this software and associated documentation files (the "Software"), |
| + * to deal in the Software without restriction, including without limitation |
| + * the rights to use, copy, modify, merge, publish, distribute, sublicense, |
| + * and/or sell copies of the Software, and to permit persons to whom the |
| + * Software is furnished to do so, subject to the following conditions: |
| + * |
| + * The above copyright notice and this permission notice (including the next |
| + * paragraph) shall be included in all copies or substantial portions of the |
| + * Software. |
| + * |
| + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR |
| + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, |
| + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL |
| + * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER |
| + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, |
| + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE |
| + * SOFTWARE. |
| + */ |
| + |
| +#ifndef DRM_RECT_H |
| +#define DRM_RECT_H |
| + |
| +/** |
| + * drm_rect - two dimensional rectangle |
| + * @x1: horizontal starting coordinate (inclusive) |
| + * @x2: horizontal ending coordinate (exclusive) |
| + * @y1: vertical starting coordinate (inclusive) |
| + * @y2: vertical ending coordinate (exclusive) |
| + */ |
| +struct drm_rect { |
| + int x1, y1, x2, y2; |
| +}; |
| + |
| +/** |
| + * drm_rect_adjust_size - adjust the size of the rectangle |
| + * @r: rectangle to be adjusted |
| + * @dw: horizontal adjustment |
| + * @dh: vertical adjustment |
| + * |
| + * Change the size of rectangle @r by @dw in the horizontal direction, |
| + * and by @dh in the vertical direction, while keeping the center |
| + * of @r stationary. |
| + * |
| + * Positive @dw and @dh increase the size, negative values decrease it. |
| + */ |
| +static inline void drm_rect_adjust_size(struct drm_rect *r, int dw, int dh) |
| +{ |
| + r->x1 -= dw >> 1; |
| + r->y1 -= dh >> 1; |
| + r->x2 += (dw + 1) >> 1; |
| + r->y2 += (dh + 1) >> 1; |
| +} |
| + |
| +/** |
| + * drm_rect_translate - translate the rectangle |
| + * @r: rectangle to be tranlated |
| + * @dx: horizontal translation |
| + * @dy: vertical translation |
| + * |
| + * Move rectangle @r by @dx in the horizontal direction, |
| + * and by @dy in the vertical direction. |
| + */ |
| +static inline void drm_rect_translate(struct drm_rect *r, int dx, int dy) |
| +{ |
| + r->x1 += dx; |
| + r->y1 += dy; |
| + r->x2 += dx; |
| + r->y2 += dy; |
| +} |
| + |
| +/** |
| + * drm_rect_downscale - downscale a rectangle |
| + * @r: rectangle to be downscaled |
| + * @horz: horizontal downscale factor |
| + * @vert: vertical downscale factor |
| + * |
| + * Divide the coordinates of rectangle @r by @horz and @vert. |
| + */ |
| +static inline void drm_rect_downscale(struct drm_rect *r, int horz, int vert) |
| +{ |
| + r->x1 /= horz; |
| + r->y1 /= vert; |
| + r->x2 /= horz; |
| + r->y2 /= vert; |
| +} |
| + |
| +/** |
| + * drm_rect_width - determine the rectangle width |
| + * @r: rectangle whose width is returned |
| + * |
| + * RETURNS: |
| + * The width of the rectangle. |
| + */ |
| +static inline int drm_rect_width(const struct drm_rect *r) |
| +{ |
| + return r->x2 - r->x1; |
| +} |
| + |
| +/** |
| + * drm_rect_height - determine the rectangle height |
| + * @r: rectangle whose height is returned |
| + * |
| + * RETURNS: |
| + * The height of the rectangle. |
| + */ |
| +static inline int drm_rect_height(const struct drm_rect *r) |
| +{ |
| + return r->y2 - r->y1; |
| +} |
| + |
| +/** |
| + * drm_rect_visible - determine if the the rectangle is visible |
| + * @r: rectangle whose visibility is returned |
| + * |
| + * RETURNS: |
| + * %true if the rectangle is visible, %false otherwise. |
| + */ |
| +static inline bool drm_rect_visible(const struct drm_rect *r) |
| +{ |
| + return drm_rect_width(r) > 0 && drm_rect_height(r) > 0; |
| +} |
| + |
| +bool drm_rect_intersect(struct drm_rect *r, const struct drm_rect *clip); |
| +bool drm_rect_clip_scaled(struct drm_rect *src, struct drm_rect *dst, |
| + const struct drm_rect *clip, |
| + int hscale, int vscale); |
| + |
| +#endif |
| -- |
| 1.8.5.rc3 |
| |