drm: Add a rotation parameter to connectors.

Some connectors, particularly writeback, can implement flip
or transpose operations as writing back to memory.

Add a connector rotation property to control this.

Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.com>
This commit is contained in:
Dave Stevenson
2024-10-22 17:22:40 +01:00
committed by Dom Cobley
parent 8d1b6526b4
commit a9a246fcb4
4 changed files with 60 additions and 10 deletions

View File

@@ -792,6 +792,8 @@ static int drm_atomic_connector_set_property(struct drm_connector *connector,
state->privacy_screen_sw_state = val;
} else if (property == connector->broadcast_rgb_property) {
state->hdmi.broadcast_rgb = val;
} else if (property == connector->rotation_property) {
state->rotation = val;
} else if (connector->funcs->atomic_set_property) {
return connector->funcs->atomic_set_property(connector,
state, property, val);
@@ -883,6 +885,8 @@ drm_atomic_connector_get_property(struct drm_connector *connector,
*val = state->privacy_screen_sw_state;
} else if (property == connector->broadcast_rgb_property) {
*val = state->hdmi.broadcast_rgb;
} else if (property == connector->rotation_property) {
*val = state->rotation;
} else if (connector->funcs->atomic_get_property) {
return connector->funcs->atomic_get_property(connector,
state, property, val);

View File

@@ -241,6 +241,16 @@ int drm_plane_create_alpha_property(struct drm_plane *plane)
}
EXPORT_SYMBOL(drm_plane_create_alpha_property);
static const struct drm_prop_enum_list drm_rotate_props[] = {
{ __builtin_ffs(DRM_MODE_ROTATE_0) - 1, "rotate-0" },
{ __builtin_ffs(DRM_MODE_ROTATE_90) - 1, "rotate-90" },
{ __builtin_ffs(DRM_MODE_ROTATE_180) - 1, "rotate-180" },
{ __builtin_ffs(DRM_MODE_ROTATE_270) - 1, "rotate-270" },
{ __builtin_ffs(DRM_MODE_REFLECT_X) - 1, "reflect-x" },
{ __builtin_ffs(DRM_MODE_REFLECT_Y) - 1, "reflect-y" },
{ __builtin_ffs(DRM_MODE_TRANSPOSE) - 1, "transpose" },
};
/**
* drm_plane_create_rotation_property - create a new rotation property
* @plane: drm plane
@@ -281,15 +291,6 @@ int drm_plane_create_rotation_property(struct drm_plane *plane,
unsigned int rotation,
unsigned int supported_rotations)
{
static const struct drm_prop_enum_list props[] = {
{ __builtin_ffs(DRM_MODE_ROTATE_0) - 1, "rotate-0" },
{ __builtin_ffs(DRM_MODE_ROTATE_90) - 1, "rotate-90" },
{ __builtin_ffs(DRM_MODE_ROTATE_180) - 1, "rotate-180" },
{ __builtin_ffs(DRM_MODE_ROTATE_270) - 1, "rotate-270" },
{ __builtin_ffs(DRM_MODE_REFLECT_X) - 1, "reflect-x" },
{ __builtin_ffs(DRM_MODE_REFLECT_Y) - 1, "reflect-y" },
{ __builtin_ffs(DRM_MODE_TRANSPOSE) - 1, "transpose" },
};
struct drm_property *prop;
WARN_ON((supported_rotations & DRM_MODE_ROTATE_MASK) == 0);
@@ -297,7 +298,8 @@ int drm_plane_create_rotation_property(struct drm_plane *plane,
WARN_ON(rotation & ~supported_rotations);
prop = drm_property_create_bitmask(plane->dev, 0, "rotation",
props, ARRAY_SIZE(props),
drm_rotate_props,
ARRAY_SIZE(drm_rotate_props),
supported_rotations);
if (!prop)
return -ENOMEM;
@@ -313,6 +315,34 @@ int drm_plane_create_rotation_property(struct drm_plane *plane,
}
EXPORT_SYMBOL(drm_plane_create_rotation_property);
int drm_connector_create_rotation_property(struct drm_connector *conn,
unsigned int rotation,
unsigned int supported_rotations)
{
struct drm_property *prop;
WARN_ON((supported_rotations & DRM_MODE_ROTATE_MASK) == 0);
WARN_ON(!is_power_of_2(rotation & DRM_MODE_ROTATE_MASK));
WARN_ON(rotation & ~supported_rotations);
prop = drm_property_create_bitmask(conn->dev, 0, "rotation",
drm_rotate_props,
ARRAY_SIZE(drm_rotate_props),
supported_rotations);
if (!prop)
return -ENOMEM;
drm_object_attach_property(&conn->base, prop, rotation);
if (conn->state)
conn->state->rotation = rotation;
conn->rotation_property = prop;
return 0;
}
EXPORT_SYMBOL(drm_connector_create_rotation_property);
/**
* drm_rotation_simplify() - Try to simplify the rotation
* @rotation: Rotation to be simplified

View File

@@ -34,6 +34,7 @@
struct drm_device;
struct drm_atomic_state;
struct drm_plane;
struct drm_connector;
static inline bool drm_rotation_90_or_270(unsigned int rotation)
{
@@ -58,4 +59,8 @@ int drm_atomic_normalize_zpos(struct drm_device *dev,
struct drm_atomic_state *state);
int drm_plane_create_blend_mode_property(struct drm_plane *plane,
unsigned int supported_modes);
int drm_connector_create_rotation_property(struct drm_connector *conn,
unsigned int rotation,
unsigned int supported_rotations);
#endif

View File

@@ -1144,6 +1144,11 @@ struct drm_connector_state {
* @drm_atomic_helper_connector_hdmi_check().
*/
struct drm_connector_hdmi_state hdmi;
/**
* @rotation: Connector property to rotate the maximum output image.
*/
u32 rotation;
};
struct drm_connector_hdmi_audio_funcs {
@@ -2055,6 +2060,12 @@ struct drm_connector {
*/
struct drm_property *broadcast_rgb_property;
/**
* @rotation_property: Optional DRM property controlling rotation of the
* output.
*/
struct drm_property *rotation_property;
#define DRM_CONNECTOR_POLL_HPD (1 << 0)
#define DRM_CONNECTOR_POLL_CONNECT (1 << 1)
#define DRM_CONNECTOR_POLL_DISCONNECT (1 << 2)