File Index
Files and directories
Sign in
FILE

vmwgfx_kms.h

File preview with syntax highlighting.

linux-6.19.14/drivers/gpu/drm/vmwgfx/vmwgfx_kms.h C
  1/* SPDX-License-Identifier: GPL-2.0 OR MIT */
  2/**************************************************************************
  3 *
  4 * Copyright (c) 2009-2025 Broadcom. All Rights Reserved. The term
  5 * “Broadcom” refers to Broadcom Inc. and/or its subsidiaries.
  6 *
  7 **************************************************************************/
  8
  9#ifndef VMWGFX_KMS_H_
 10#define VMWGFX_KMS_H_
 11
 12#include "vmwgfx_cursor_plane.h"
 13#include "vmwgfx_drv.h"
 14
 15#include <drm/drm_encoder.h>
 16#include <drm/drm_framebuffer.h>
 17#include <drm/drm_probe_helper.h>
 18
 19/**
 20 * struct vmw_du_update_plane - Closure structure for vmw_du_helper_plane_update
 21 * @plane: Plane which is being updated.
 22 * @old_state: Old state of plane.
 23 * @dev_priv: Device private.
 24 * @du: Display unit on which to update the plane.
 25 * @vfb: Framebuffer which is blitted to display unit.
 26 * @out_fence: Out fence for resource finish.
 27 * @mutex: The mutex used to protect resource reservation.
 28 * @cpu_blit: True if need cpu blit.
 29 * @intr: Whether to perform waits interruptible if possible.
 30 *
 31 * This structure loosely represent the set of operations needed to perform a
 32 * plane update on a display unit. Implementer will define that functionality
 33 * according to the function callbacks for this structure. In brief it involves
 34 * surface/buffer object validation, populate FIFO commands and command
 35 * submission to the device.
 36 */
 37struct vmw_du_update_plane {
 38	/**
 39	 * @calc_fifo_size: Calculate fifo size.
 40	 *
 41	 * Determine fifo size for the commands needed for update. The number of
 42	 * damage clips on display unit @num_hits will be passed to allocate
 43	 * sufficient fifo space.
 44	 *
 45	 * Return: Fifo size needed
 46	 */
 47	uint32_t (*calc_fifo_size)(struct vmw_du_update_plane *update,
 48				   uint32_t num_hits);
 49
 50	/**
 51	 * @post_prepare: Populate fifo for resource preparation.
 52	 *
 53	 * Some surface resource or buffer object need some extra cmd submission
 54	 * like update GB image for proxy surface and define a GMRFB for screen
 55	 * object. That should be done here as this callback will be
 56	 * called after FIFO allocation with the address of command buufer.
 57	 *
 58	 * This callback is optional.
 59	 *
 60	 * Return: Size of commands populated to command buffer.
 61	 */
 62	uint32_t (*post_prepare)(struct vmw_du_update_plane *update, void *cmd);
 63
 64	/**
 65	 * @pre_clip: Populate fifo before clip.
 66	 *
 67	 * This is where pre clip related command should be populated like
 68	 * surface copy/DMA, etc.
 69	 *
 70	 * This callback is optional.
 71	 *
 72	 * Return: Size of commands populated to command buffer.
 73	 */
 74	uint32_t (*pre_clip)(struct vmw_du_update_plane *update, void *cmd,
 75			     uint32_t num_hits);
 76
 77	/**
 78	 * @clip: Populate fifo for clip.
 79	 *
 80	 * This is where to populate clips for surface copy/dma or blit commands
 81	 * if needed. This will be called times have damage in display unit,
 82	 * which is one if doing full update. @clip is the damage in destination
 83	 * coordinates which is crtc/DU and @src_x, @src_y is damage clip src in
 84	 * framebuffer coordinate.
 85	 *
 86	 * This callback is optional.
 87	 *
 88	 * Return: Size of commands populated to command buffer.
 89	 */
 90	uint32_t (*clip)(struct vmw_du_update_plane *update, void *cmd,
 91			 struct drm_rect *clip, uint32_t src_x, uint32_t src_y);
 92
 93	/**
 94	 * @post_clip: Populate fifo after clip.
 95	 *
 96	 * This is where to populate display unit update commands or blit
 97	 * commands.
 98	 *
 99	 * Return: Size of commands populated to command buffer.
100	 */
101	uint32_t (*post_clip)(struct vmw_du_update_plane *update, void *cmd,
102				    struct drm_rect *bb);
103
104	struct drm_plane *plane;
105	struct drm_plane_state *old_state;
106	struct vmw_private *dev_priv;
107	struct vmw_display_unit *du;
108	struct vmw_framebuffer *vfb;
109	struct vmw_fence_obj **out_fence;
110	struct mutex *mutex;
111	bool intr;
112};
113
114/**
115 * struct vmw_du_update_plane_surface - closure structure for surface
116 * @base: base closure structure.
117 * @cmd_start: FIFO command start address (used by SOU only).
118 */
119struct vmw_du_update_plane_surface {
120	struct vmw_du_update_plane base;
121	/* This member is to handle special case SOU surface update */
122	void *cmd_start;
123};
124
125/**
126 * struct vmw_du_update_plane_buffer - Closure structure for buffer object
127 * @base: Base closure structure.
128 * @fb_left: x1 for fb damage bounding box.
129 * @fb_top: y1 for fb damage bounding box.
130 */
131struct vmw_du_update_plane_buffer {
132	struct vmw_du_update_plane base;
133	int fb_left, fb_top;
134};
135
136/**
137 * struct vmw_kms_dirty - closure structure for the vmw_kms_helper_dirty
138 * function.
139 *
140 * @fifo_commit: Callback that is called once for each display unit after
141 * all clip rects. This function must commit the fifo space reserved by the
142 * helper. Set up by the caller.
143 * @clip: Callback that is called for each cliprect on each display unit.
144 * Set up by the caller.
145 * @fifo_reserve_size: Fifo size that the helper should try to allocat for
146 * each display unit. Set up by the caller.
147 * @dev_priv: Pointer to the device private. Set up by the helper.
148 * @unit: The current display unit. Set up by the helper before a call to @clip.
149 * @cmd: The allocated fifo space. Set up by the helper before the first @clip
150 * call.
151 * @crtc: The crtc for which to build dirty commands.
152 * @num_hits: Number of clip rect commands for this display unit.
153 * Cleared by the helper before the first @clip call. Updated by the @clip
154 * callback.
155 * @fb_x: Clip rect left side in framebuffer coordinates.
156 * @fb_y: Clip rect right side in framebuffer coordinates.
157 * @unit_x1: Clip rect left side in crtc coordinates.
158 * @unit_y1: Clip rect top side in crtc coordinates.
159 * @unit_x2: Clip rect right side in crtc coordinates.
160 * @unit_y2: Clip rect bottom side in crtc coordinates.
161 *
162 * The clip rect coordinates are updated by the helper for each @clip call.
163 * Note that this may be derived from if more info needs to be passed between
164 * helper caller and helper callbacks.
165 */
166struct vmw_kms_dirty {
167	void (*fifo_commit)(struct vmw_kms_dirty *);
168	void (*clip)(struct vmw_kms_dirty *);
169	size_t fifo_reserve_size;
170	struct vmw_private *dev_priv;
171	struct vmw_display_unit *unit;
172	void *cmd;
173	struct drm_crtc *crtc;
174	u32 num_hits;
175	s32 fb_x;
176	s32 fb_y;
177	s32 unit_x1;
178	s32 unit_y1;
179	s32 unit_x2;
180	s32 unit_y2;
181};
182
183#define vmw_framebuffer_to_vfb(x) \
184	container_of(x, struct vmw_framebuffer, base)
185#define vmw_framebuffer_to_vfbs(x) \
186	container_of(x, struct vmw_framebuffer_surface, base.base)
187#define vmw_framebuffer_to_vfbd(x) \
188	container_of(x, struct vmw_framebuffer_bo, base.base)
189
190/**
191 * Base class for framebuffers
192 *
193 * @pin is called the when ever a crtc uses this framebuffer
194 * @unpin is called
195 */
196struct vmw_framebuffer {
197	struct drm_framebuffer base;
198	bool bo;
199};
200
201struct vmw_framebuffer_surface {
202	struct vmw_framebuffer base;
203	struct vmw_user_object uo;
204};
205
206struct vmw_framebuffer_bo {
207	struct vmw_framebuffer base;
208	struct vmw_bo *buffer;
209};
210
211
212static const uint32_t __maybe_unused vmw_primary_plane_formats[] = {
213	DRM_FORMAT_XRGB8888,
214	DRM_FORMAT_ARGB8888,
215	DRM_FORMAT_RGB565,
216	DRM_FORMAT_XRGB1555,
217};
218
219
220#define vmw_crtc_state_to_vcs(x) container_of(x, struct vmw_crtc_state, base)
221#define vmw_plane_state_to_vps(x) container_of(x, struct vmw_plane_state, base)
222#define vmw_connector_state_to_vcs(x) \
223		container_of(x, struct vmw_connector_state, base)
224
225/**
226 * Derived class for crtc state object
227 *
228 * @base DRM crtc object
229 */
230struct vmw_crtc_state {
231	struct drm_crtc_state base;
232};
233
234
235/**
236 * Derived class for plane state object
237 *
238 * @base DRM plane object
239 * @surf Display surface for STDU
240 * @bo display bo for SOU
241 * @content_fb_type Used by STDU.
242 * @bo_size Size of the bo, used by Screen Object Display Unit
243 * @pinned pin count for STDU display surface
244 */
245struct vmw_plane_state {
246	struct drm_plane_state base;
247	struct vmw_user_object uo;
248
249	int content_fb_type;
250	unsigned long bo_size;
251
252	int pinned;
253
254	/* For CPU Blit */
255	unsigned int cpp;
256
257	struct vmw_cursor_plane_state cursor;
258};
259
260
261/**
262 * Derived class for connector state object
263 *
264 * @base DRM connector object
265 * @is_implicit connector property
266 *
267 */
268struct vmw_connector_state {
269	struct drm_connector_state base;
270
271	/**
272	 * @gui_x:
273	 *
274	 * vmwgfx connector property representing the x position of this display
275	 * unit (connector is synonymous to display unit) in overall topology.
276	 * This is what the device expect as xRoot while creating screen.
277	 */
278	int gui_x;
279
280	/**
281	 * @gui_y:
282	 *
283	 * vmwgfx connector property representing the y position of this display
284	 * unit (connector is synonymous to display unit) in overall topology.
285	 * This is what the device expect as yRoot while creating screen.
286	 */
287	int gui_y;
288};
289
290
291/**
292 * Base class display unit.
293 *
294 * Since the SVGA hw doesn't have a concept of a crtc, encoder or connector
295 * so the display unit is all of them at the same time. This is true for both
296 * legacy multimon and screen objects.
297 */
298struct vmw_display_unit {
299	struct drm_crtc crtc;
300	struct drm_encoder encoder;
301	struct drm_connector connector;
302	struct drm_plane primary;
303	struct vmw_cursor_plane cursor;
304
305	unsigned unit;
306
307	/*
308	 * Prefered mode tracking.
309	 */
310	unsigned pref_width;
311	unsigned pref_height;
312	bool pref_active;
313
314	/*
315	 * Gui positioning
316	 */
317	int gui_x;
318	int gui_y;
319	bool is_implicit;
320	int set_gui_x;
321	int set_gui_y;
322
323	struct {
324		struct work_struct crc_generator_work;
325		struct hrtimer timer;
326		ktime_t period_ns;
327
328		/* protects concurrent access to the vblank handler */
329		atomic_t atomic_lock;
330		/* protected by @atomic_lock */
331		bool crc_enabled;
332		struct vmw_surface *surface;
333
334		/* protects concurrent access to the crc worker */
335		spinlock_t crc_state_lock;
336		/* protected by @crc_state_lock */
337		bool crc_pending;
338		u64 frame_start;
339		u64 frame_end;
340	} vkms;
341};
342
343#define vmw_crtc_to_du(x) \
344	container_of(x, struct vmw_display_unit, crtc)
345#define vmw_connector_to_du(x) \
346	container_of(x, struct vmw_display_unit, connector)
347
348
349/*
350 * Shared display unit functions - vmwgfx_kms.c
351 */
352void vmw_du_init(struct vmw_display_unit *du);
353void vmw_du_cleanup(struct vmw_display_unit *du);
354int vmw_du_crtc_gamma_set(struct drm_crtc *crtc,
355			   u16 *r, u16 *g, u16 *b,
356			   uint32_t size,
357			   struct drm_modeset_acquire_ctx *ctx);
358int vmw_du_connector_set_property(struct drm_connector *connector,
359				  struct drm_property *property,
360				  uint64_t val);
361int vmw_du_connector_atomic_set_property(struct drm_connector *connector,
362					 struct drm_connector_state *state,
363					 struct drm_property *property,
364					 uint64_t val);
365int
366vmw_du_connector_atomic_get_property(struct drm_connector *connector,
367				     const struct drm_connector_state *state,
368				     struct drm_property *property,
369				     uint64_t *val);
370int vmw_du_connector_dpms(struct drm_connector *connector, int mode);
371void vmw_du_connector_save(struct drm_connector *connector);
372void vmw_du_connector_restore(struct drm_connector *connector);
373enum drm_connector_status
374vmw_du_connector_detect(struct drm_connector *connector, bool force);
375int vmw_kms_helper_dirty(struct vmw_private *dev_priv,
376			 struct vmw_framebuffer *framebuffer,
377			 const struct drm_clip_rect *clips,
378			 const struct drm_vmw_rect *vclips,
379			 s32 dest_x, s32 dest_y,
380			 int num_clips,
381			 int increment,
382			 struct vmw_kms_dirty *dirty);
383enum drm_mode_status vmw_connector_mode_valid(struct drm_connector *connector,
384					      const struct drm_display_mode *mode);
385int vmw_connector_get_modes(struct drm_connector *connector);
386
387void vmw_kms_helper_validation_finish(struct vmw_private *dev_priv,
388				      struct drm_file *file_priv,
389				      struct vmw_validation_context *ctx,
390				      struct vmw_fence_obj **out_fence,
391				      struct drm_vmw_fence_rep __user *
392				      user_fence_rep);
393int vmw_kms_readback(struct vmw_private *dev_priv,
394		     struct drm_file *file_priv,
395		     struct vmw_framebuffer *vfb,
396		     struct drm_vmw_fence_rep __user *user_fence_rep,
397		     struct drm_vmw_rect *vclips,
398		     uint32_t num_clips);
399struct vmw_framebuffer *
400vmw_kms_new_framebuffer(struct vmw_private *dev_priv,
401			struct vmw_user_object *uo,
402			const struct drm_format_info *info,
403			const struct drm_mode_fb_cmd2 *mode_cmd);
404void vmw_guess_mode_timing(struct drm_display_mode *mode);
405void vmw_kms_update_implicit_fb(struct vmw_private *dev_priv);
406void vmw_kms_create_implicit_placement_property(struct vmw_private *dev_priv);
407
408/* Universal Plane Helpers */
409void vmw_du_primary_plane_destroy(struct drm_plane *plane);
410
411/* Atomic Helpers */
412int vmw_du_primary_plane_atomic_check(struct drm_plane *plane,
413				      struct drm_atomic_state *state);
414void vmw_du_plane_cleanup_fb(struct drm_plane *plane,
415			     struct drm_plane_state *old_state);
416void vmw_du_plane_reset(struct drm_plane *plane);
417struct drm_plane_state *vmw_du_plane_duplicate_state(struct drm_plane *plane);
418void vmw_du_plane_destroy_state(struct drm_plane *plane,
419				struct drm_plane_state *state);
420void vmw_du_plane_unpin_surf(struct vmw_plane_state *vps);
421
422int vmw_du_crtc_atomic_check(struct drm_crtc *crtc,
423			     struct drm_atomic_state *state);
424void vmw_du_crtc_atomic_begin(struct drm_crtc *crtc,
425			      struct drm_atomic_state *state);
426void vmw_du_crtc_reset(struct drm_crtc *crtc);
427struct drm_crtc_state *vmw_du_crtc_duplicate_state(struct drm_crtc *crtc);
428void vmw_du_crtc_destroy_state(struct drm_crtc *crtc,
429				struct drm_crtc_state *state);
430void vmw_du_connector_reset(struct drm_connector *connector);
431struct drm_connector_state *
432vmw_du_connector_duplicate_state(struct drm_connector *connector);
433
434void vmw_du_connector_destroy_state(struct drm_connector *connector,
435				    struct drm_connector_state *state);
436
437/*
438 * Legacy display unit functions - vmwgfx_ldu.c
439 */
440int vmw_kms_ldu_init_display(struct vmw_private *dev_priv);
441int vmw_kms_ldu_close_display(struct vmw_private *dev_priv);
442int vmw_kms_update_proxy(struct vmw_resource *res,
443			 const struct drm_clip_rect *clips,
444			 unsigned num_clips,
445			 int increment);
446
447/*
448 * Screen Objects display functions - vmwgfx_scrn.c
449 */
450int vmw_kms_sou_init_display(struct vmw_private *dev_priv);
451int vmw_kms_sou_do_surface_dirty(struct vmw_private *dev_priv,
452				 struct vmw_framebuffer *framebuffer,
453				 struct drm_clip_rect *clips,
454				 struct drm_vmw_rect *vclips,
455				 struct vmw_resource *srf,
456				 s32 dest_x,
457				 s32 dest_y,
458				 unsigned num_clips, int inc,
459				 struct vmw_fence_obj **out_fence,
460				 struct drm_crtc *crtc);
461int vmw_kms_sou_do_bo_dirty(struct vmw_private *dev_priv,
462			    struct vmw_framebuffer *framebuffer,
463			    struct drm_clip_rect *clips,
464			    struct drm_vmw_rect *vclips,
465			    unsigned int num_clips, int increment,
466			    bool interruptible,
467			    struct vmw_fence_obj **out_fence,
468			    struct drm_crtc *crtc);
469int vmw_kms_sou_readback(struct vmw_private *dev_priv,
470			 struct drm_file *file_priv,
471			 struct vmw_framebuffer *vfb,
472			 struct drm_vmw_fence_rep __user *user_fence_rep,
473			 struct drm_vmw_rect *vclips,
474			 uint32_t num_clips,
475			 struct drm_crtc *crtc);
476
477/*
478 * Screen Target Display Unit functions - vmwgfx_stdu.c
479 */
480int vmw_kms_stdu_init_display(struct vmw_private *dev_priv);
481int vmw_kms_stdu_surface_dirty(struct vmw_private *dev_priv,
482			       struct vmw_framebuffer *framebuffer,
483			       struct drm_clip_rect *clips,
484			       struct drm_vmw_rect *vclips,
485			       struct vmw_resource *srf,
486			       s32 dest_x,
487			       s32 dest_y,
488			       unsigned num_clips, int inc,
489			       struct vmw_fence_obj **out_fence,
490			       struct drm_crtc *crtc);
491int vmw_kms_stdu_readback(struct vmw_private *dev_priv,
492			  struct drm_file *file_priv,
493			  struct vmw_framebuffer *vfb,
494			  struct drm_vmw_fence_rep __user *user_fence_rep,
495			  struct drm_clip_rect *clips,
496			  struct drm_vmw_rect *vclips,
497			  uint32_t num_clips,
498			  int increment,
499			  struct drm_crtc *crtc);
500
501int vmw_du_helper_plane_update(struct vmw_du_update_plane *update);
502
503/**
504 * vmw_du_translate_to_crtc - Translate a rect from framebuffer to crtc
505 * @state: Plane state.
506 * @r: Rectangle to translate.
507 */
508static inline void vmw_du_translate_to_crtc(struct drm_plane_state *state,
509					    struct drm_rect *r)
510{
511	int translate_crtc_x = -((state->src_x >> 16) - state->crtc_x);
512	int translate_crtc_y = -((state->src_y >> 16) - state->crtc_y);
513
514	drm_rect_translate(r, translate_crtc_x, translate_crtc_y);
515}
516
517#endif
~/ Read-only file preview.