Re: [PATCH v5 3/3] drm: protect drm_master pointers in drm_lease.c
On 30/6/21 12:07 am, Daniel Vetter wrote: On Tue, Jun 29, 2021 at 11:37:06AM +0800, Desmond Cheong Zhi Xi wrote: Currently, direct copies of drm_file->master pointers should be protected by drm_device.master_mutex when being dereferenced. This is because drm_file->master is not invariant for the lifetime of drm_file. If drm_file is not the creator of master, then drm_file->is_master is false, and a call to drm_setmaster_ioctl will invoke drm_new_set_master, which then allocates a new master for drm_file and puts the old master. Thus, without holding drm_device.master_mutex, the old value of drm_file->master could be freed while it is being used by another concurrent process. In drm_lease.c, there are multiple instances where drm_file->master is accessed and dereferenced while drm_device.master_mutex is not held. This makes drm_lease.c vulnerable to use-after-free bugs. We address this issue in 3 ways: 1. Clarify in the kerneldoc that drm_file->master is protected by drm_device.master_mutex. 2. Add a new drm_file_get_master() function that calls drm_master_get on drm_file->master while holding on to drm_device.master_mutex. Since drm_master_get increments the reference count of master, this prevents master from being freed until we unreference it with drm_master_put. 3. In each case where drm_file->master is directly accessed and eventually dereferenced in drm_lease.c, we wrap the access in a call to the new drm_file_get_master function, then unreference the master pointer once we are done using it. Reported-by: Daniel Vetter Signed-off-by: Desmond Cheong Zhi Xi Series looks very nice, let's see what intel-gfx-ci says. You should get a mail, but results are also here: https://patchwork.freedesktop.org/series/91969/#rev2 One tiny comment below. --- drivers/gpu/drm/drm_auth.c | 25 drivers/gpu/drm/drm_lease.c | 77 +++-- include/drm/drm_auth.h | 1 + include/drm/drm_file.h | 15 ++-- 4 files changed, 95 insertions(+), 23 deletions(-) diff --git a/drivers/gpu/drm/drm_auth.c b/drivers/gpu/drm/drm_auth.c index ab1863c5a5a0..c36a0b72be26 100644 --- a/drivers/gpu/drm/drm_auth.c +++ b/drivers/gpu/drm/drm_auth.c @@ -384,6 +384,31 @@ struct drm_master *drm_master_get(struct drm_master *master) } EXPORT_SYMBOL(drm_master_get); +/** + * drm_file_get_master - reference &drm_file.master of @file_priv + * @file_priv: DRM file private + * + * Increments the reference count of @file_priv's &drm_file.master and returns + * the &drm_file.master. If @file_priv has no &drm_file.master, returns NULL. + * + * Master pointers returned from this function should be unreferenced using + * drm_master_put(). + */ +struct drm_master *drm_file_get_master(struct drm_file *file_priv) +{ + struct drm_master *master = NULL; + + mutex_lock(&file_priv->minor->dev->master_mutex); + if (!file_priv->master) + goto unlock; + master = drm_master_get(file_priv->master); + +unlock: + mutex_unlock(&file_priv->minor->dev->master_mutex); + return master; +} +EXPORT_SYMBOL(drm_file_get_master); + static void drm_master_destroy(struct kref *kref) { struct drm_master *master = container_of(kref, struct drm_master, refcount); diff --git a/drivers/gpu/drm/drm_lease.c b/drivers/gpu/drm/drm_lease.c index 00fb433bcef1..cdcc87fa9685 100644 --- a/drivers/gpu/drm/drm_lease.c +++ b/drivers/gpu/drm/drm_lease.c @@ -106,10 +106,19 @@ static bool _drm_has_leased(struct drm_master *master, int id) */ bool _drm_lease_held(struct drm_file *file_priv, int id) { - if (!file_priv || !file_priv->master) + bool ret; + struct drm_master *master; + + if (!file_priv) return true; - return _drm_lease_held_master(file_priv->master, id); + master = drm_file_get_master(file_priv); + if (master == NULL) + return true; + ret = _drm_lease_held_master(master, id); + drm_master_put(&master); + + return ret; } /** @@ -128,13 +137,20 @@ bool drm_lease_held(struct drm_file *file_priv, int id) struct drm_master *master; bool ret; - if (!file_priv || !file_priv->master || !file_priv->master->lessor) + if (!file_priv) return true; - master = file_priv->master; + master = drm_file_get_master(file_priv); + if (master == NULL) + return true; + if (!master->lessor) { + drm_master_put(&master); + return true; + } mutex_lock(&master->dev->mode_config.idr_mutex); ret = _drm_lease_held_master(master, id); mutex_unlock(&master->dev->mode_config.idr_mutex); + drm_master_put(&master); return ret; } @@ -154,10 +170,16 @@ uint32_t drm_lease_filter_crtcs(struct drm_file *file_priv, uint32_t crtcs_in) int count_in, count_out; uint32_t crtcs_out = 0; - if (!file_priv || !file_priv-
Re: [Intel-gfx] [PATCH 0/2] GuC submission / DRM scheduler integration plan + new uAPI
On Tue, Jun 29, 2021 at 12:35:09PM -0700, Matthew Brost wrote: > Subject and patches say it all. > > v2: Address comments, patches have details of changes > v3: Address comments, patches have details of changes > v4: Address comments, patches have details of changes > v5: Fix checkpatch and docs warnings > > Signed-off-by: Matthew Brost Pushed to drm-intel-gt-next, thanks a lot! -Daniel > > Matthew Brost (2): > drm/doc/rfc: i915 GuC submission / DRM scheduler > drm/doc/rfc: i915 new parallel submission uAPI plan > > Documentation/gpu/rfc/i915_parallel_execbuf.h | 122 +++ > Documentation/gpu/rfc/i915_scheduler.rst | 148 ++ > Documentation/gpu/rfc/index.rst | 4 + > 3 files changed, 274 insertions(+) > create mode 100644 Documentation/gpu/rfc/i915_parallel_execbuf.h > create mode 100644 Documentation/gpu/rfc/i915_scheduler.rst > > -- > 2.28.0 > > ___ > Intel-gfx mailing list > intel-...@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/intel-gfx -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
Re: [PATCH v5 3/3] drm: protect drm_master pointers in drm_lease.c
On Wed, Jun 30, 2021 at 9:18 AM Desmond Cheong Zhi Xi wrote: > > On 30/6/21 12:07 am, Daniel Vetter wrote: > > On Tue, Jun 29, 2021 at 11:37:06AM +0800, Desmond Cheong Zhi Xi wrote: > >> Currently, direct copies of drm_file->master pointers should be > >> protected by drm_device.master_mutex when being dereferenced. This is > >> because drm_file->master is not invariant for the lifetime of > >> drm_file. If drm_file is not the creator of master, then > >> drm_file->is_master is false, and a call to drm_setmaster_ioctl will > >> invoke drm_new_set_master, which then allocates a new master for > >> drm_file and puts the old master. > >> > >> Thus, without holding drm_device.master_mutex, the old value of > >> drm_file->master could be freed while it is being used by another > >> concurrent process. > >> > >> In drm_lease.c, there are multiple instances where drm_file->master is > >> accessed and dereferenced while drm_device.master_mutex is not > >> held. This makes drm_lease.c vulnerable to use-after-free bugs. > >> > >> We address this issue in 3 ways: > >> > >> 1. Clarify in the kerneldoc that drm_file->master is protected by > >> drm_device.master_mutex. > >> > >> 2. Add a new drm_file_get_master() function that calls drm_master_get > >> on drm_file->master while holding on to drm_device.master_mutex. Since > >> drm_master_get increments the reference count of master, this > >> prevents master from being freed until we unreference it with > >> drm_master_put. > >> > >> 3. In each case where drm_file->master is directly accessed and > >> eventually dereferenced in drm_lease.c, we wrap the access in a call > >> to the new drm_file_get_master function, then unreference the master > >> pointer once we are done using it. > >> > >> Reported-by: Daniel Vetter > >> Signed-off-by: Desmond Cheong Zhi Xi > > > > Series looks very nice, let's see what intel-gfx-ci says. You should get a > > mail, but results are also here: > > > > https://patchwork.freedesktop.org/series/91969/#rev2 > > > > One tiny comment below. > > > >> --- > >> drivers/gpu/drm/drm_auth.c | 25 > >> drivers/gpu/drm/drm_lease.c | 77 +++-- > >> include/drm/drm_auth.h | 1 + > >> include/drm/drm_file.h | 15 ++-- > >> 4 files changed, 95 insertions(+), 23 deletions(-) > >> > >> diff --git a/drivers/gpu/drm/drm_auth.c b/drivers/gpu/drm/drm_auth.c > >> index ab1863c5a5a0..c36a0b72be26 100644 > >> --- a/drivers/gpu/drm/drm_auth.c > >> +++ b/drivers/gpu/drm/drm_auth.c > >> @@ -384,6 +384,31 @@ struct drm_master *drm_master_get(struct drm_master > >> *master) > >> } > >> EXPORT_SYMBOL(drm_master_get); > >> > >> +/** > >> + * drm_file_get_master - reference &drm_file.master of @file_priv > >> + * @file_priv: DRM file private > >> + * > >> + * Increments the reference count of @file_priv's &drm_file.master and > >> returns > >> + * the &drm_file.master. If @file_priv has no &drm_file.master, returns > >> NULL. > >> + * > >> + * Master pointers returned from this function should be unreferenced > >> using > >> + * drm_master_put(). > >> + */ > >> +struct drm_master *drm_file_get_master(struct drm_file *file_priv) > >> +{ > >> +struct drm_master *master = NULL; > >> + > >> +mutex_lock(&file_priv->minor->dev->master_mutex); > >> +if (!file_priv->master) > >> +goto unlock; > >> +master = drm_master_get(file_priv->master); > >> + > >> +unlock: > >> +mutex_unlock(&file_priv->minor->dev->master_mutex); > >> +return master; > >> +} > >> +EXPORT_SYMBOL(drm_file_get_master); > >> + > >> static void drm_master_destroy(struct kref *kref) > >> { > >> struct drm_master *master = container_of(kref, struct drm_master, > >> refcount); > >> diff --git a/drivers/gpu/drm/drm_lease.c b/drivers/gpu/drm/drm_lease.c > >> index 00fb433bcef1..cdcc87fa9685 100644 > >> --- a/drivers/gpu/drm/drm_lease.c > >> +++ b/drivers/gpu/drm/drm_lease.c > >> @@ -106,10 +106,19 @@ static bool _drm_has_leased(struct drm_master > >> *master, int id) > >>*/ > >> bool _drm_lease_held(struct drm_file *file_priv, int id) > >> { > >> -if (!file_priv || !file_priv->master) > >> +bool ret; > >> +struct drm_master *master; > >> + > >> +if (!file_priv) > >> return true; > >> > >> -return _drm_lease_held_master(file_priv->master, id); > >> +master = drm_file_get_master(file_priv); > >> +if (master == NULL) > >> +return true; > >> +ret = _drm_lease_held_master(master, id); > >> +drm_master_put(&master); > >> + > >> +return ret; > >> } > >> > >> /** > >> @@ -128,13 +137,20 @@ bool drm_lease_held(struct drm_file *file_priv, int > >> id) > >> struct drm_master *master; > >> bool ret; > >> > >> -if (!file_priv || !file_priv->master || !file_priv->master->lessor) > >> +if (!file_priv) > >> return true; > >> > >> -master = file_priv->master; > >> +master = drm_file_get_master(f
Re: [PATCH 1/2] drm/doc/rfc: i915 GuC submission / DRM scheduler
On 29/06/2021 22:35, Matthew Brost wrote: Add entry for i915 GuC submission / DRM scheduler integration plan. Follow up patch with details of new parallel submission uAPI to come. v2: (Daniel Vetter) - Expand explaination of why bonding isn't supported for GuC submission - CC some of the DRM scheduler maintainers - Add priority inheritance / boosting use case - Add reasoning for removing in order assumptions (Daniel Stone) - Add links to priority spec v4: (Tvrtko) - Add TODOs section (Daniel Vetter) - Pull in 1 line from following patch v5: (Checkpatch) - Fix typos Cc: Christian König Cc: Luben Tuikov Cc: Alex Deucher Cc: Steven Price Cc: Jon Bloomfield Cc: Dave Airlie Cc: Daniel Vetter Cc: Jason Ekstrand Cc: dri-devel@lists.freedesktop.org Signed-off-by: Matthew Brost Reviewed-by: Daniel Vetter Acked-by: Dave Airlie --- Documentation/gpu/rfc/i915_scheduler.rst | 91 Documentation/gpu/rfc/index.rst | 4 ++ 2 files changed, 95 insertions(+) create mode 100644 Documentation/gpu/rfc/i915_scheduler.rst diff --git a/Documentation/gpu/rfc/i915_scheduler.rst b/Documentation/gpu/rfc/i915_scheduler.rst new file mode 100644 index ..7acd386a6b49 --- /dev/null +++ b/Documentation/gpu/rfc/i915_scheduler.rst @@ -0,0 +1,91 @@ += +I915 GuC Submission/DRM Scheduler Section += + +Upstream plan += +For upstream the overall plan for landing GuC submission and integrating the +i915 with the DRM scheduler is: + +* Merge basic GuC submission + * Basic submission support for all gen11+ platforms + * Not enabled by default on any current platforms but can be enabled via + modparam enable_guc Just a quick reminder that a lot of users have this parameter set in their grub command line because of the incorrect assumption that quick sync requires the HuC which requires the GuC command submission. Just bear that in mind and make sure there is a minimum of quality in the GuC backend before allowing users to use the GuC, even behind this kernel parameter. Maybe a warning in the kernel logs saying that this feature is experimental, and use "enable_guc=1" for the fullest quick sync support will improve the user satisfaction, and save you some time handling unwanted bugs. + * Lots of rework will need to be done to integrate with DRM scheduler so + no need to nit pick everything in the code, it just should be + functional, no major coding style / layering errors, and not regress + execlists + * Update IGTs / selftests as needed to work with GuC submission + * Enable CI on supported platforms for a baseline What's the plan to keep the comparison between GuC and execlists? The CI machines cannot just test the GuC as it would expose users to regressions in the default mode, and machines are hard to come by in the CI lab. + * Rework / get CI heathly for GuC submission in place as needed +* Merge new parallel submission uAPI + * Bonding uAPI completely incompatible with GuC submission, plus it has + severe design issues in general, which is why we want to retire it no + matter what + * New uAPI adds I915_CONTEXT_ENGINES_EXT_PARALLEL context setup step + which configures a slot with N contexts + * After I915_CONTEXT_ENGINES_EXT_PARALLEL a user can submit N batches to + a slot in a single execbuf IOCTL and the batches run on the GPU in + paralllel FYI, this is a typo + * Initially only for GuC submission but execlists can be supported if + needed +* Convert the i915 to use the DRM scheduler + * GuC submission backend fully integrated with DRM scheduler + * All request queues removed from backend (e.g. all backpressure + handled in DRM scheduler) + * Resets / cancels hook in DRM scheduler + * Watchdog hooks into DRM scheduler + * Lots of complexity of the GuC backend can be pulled out once + integrated with DRM scheduler (e.g. state machine gets + simplier, locking gets simplier, etc...) As much as I would like more consistency in the English language, simplier is not a word in the dictionary. + * Execlists backend will minimum required to hook in the DRM scheduler Can't parse this sentence. How about: "Minimum integration of the execlists backend in the DRM scheduler"? Other than these typographical nitpicks, I think the plan is sane provided that you can find enough CI machines and add the warning. + * Legacy interface + * Features like timeslicing / preemption / virtual engines would + be difficult to integrate with the DRM scheduler and these + features are not required for GuC submission as the
Re: [PATCH v4 03/17] drm/uAPI: Add "active bpc" as feedback channel for "max bpc" drm property
On Tue, 29 Jun 2021 13:02:05 +0200 Werner Sembach wrote: > Am 28.06.21 um 19:03 schrieb Werner Sembach: > > Am 18.06.21 um 11:11 schrieb Werner Sembach: > >> Add a new general drm property "active bpc" which can be used by graphic > >> drivers to report the applied bit depth per pixel back to userspace. > >> > >> While "max bpc" can be used to change the color depth, there was no way to > >> check which one actually got used. While in theory the driver chooses the > >> best/highest color depth within the max bpc setting a user might not be > >> fully aware what his hardware is or isn't capable off. This is meant as a > >> quick way to double check the setup. > >> > >> In the future, automatic color calibration for screens might also depend on > >> this information being available. > >> > >> Signed-off-by: Werner Sembach > >> --- > >> drivers/gpu/drm/drm_connector.c | 51 + > >> include/drm/drm_connector.h | 8 ++ > >> 2 files changed, 59 insertions(+) > >> > >> diff --git a/drivers/gpu/drm/drm_connector.c > >> b/drivers/gpu/drm/drm_connector.c > >> index da39e7ff6965..943f6b61053b 100644 > >> --- a/drivers/gpu/drm/drm_connector.c > >> +++ b/drivers/gpu/drm/drm_connector.c > >> @@ -1197,6 +1197,14 @@ static const struct drm_prop_enum_list > >> dp_colorspaces[] = { > >> *drm_connector_attach_max_bpc_property() to create and attach the > >> *property to the connector during initialization. > >> * > >> + * active bpc: > >> + *This read-only range property tells userspace the pixel color > >> bit depth > >> + *actually used by the hardware display engine on "the cable" on a > >> + *connector. The chosen value depends on hardware capabilities, > >> both > >> + *display engine and connected monitor, and the "max bpc" > >> property. > >> + *Drivers shall use drm_connector_attach_active_bpc_property() to > >> install > >> + *this property. > >> + * > > Regarding "on the cable" and dithering: As far as I can tell, what the > > dithering option does, is setting a hardware > > register here: > > > > - > > https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4534 > > > > - > > https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4571 > > > > So dithering seems to be calculated by fixed purpose hardware/firmware > > outside of the driver? > > > > The Intel driver does not seem to set a target bpc/bpp for this hardware so > > I guess it defaults to 6 or 8 bpc? > > Never mind it does. This switch-case does affect the dithering output: > https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4537 Hi, I obviously do not know the intel driver or hardware at all, but to me that just looks like translating from bits per pixel to bits per channel in RGB mapping? > As found in this documentation p.548: > https://01.org/sites/default/files/documentation/intel-gfx-prm-osrc-lkf-vol02c-commandreference-registers-part2.pdf > > So max bpc and active bpc are affecting/affected by the bpc after dithering. By definition, if the cable carries N bpc, then dithering does not change that. The cable still carries N bpc, but due to spatial or temporal dithering, the *observed* color resolution may or may not be higher than the cable bpc. Of course, if the cable bpc is 8, and dithering targets 6 bpc, then 2 LSB on the cable are always zero, right? Maybe one would want to do that if the monitor has a 6 bit panel and it simply ignored the 2 LSB, and the cable cannot go down to 6 bpc. So, what does "max bpc" mean right now? It seems like dither on/off is insufficient information, one would also need to control the dithering target bpc. I suppose the driver has a policy on how it chooses the target bpc, but what is that policy? Is the dither target bpc the cable bpc or the sink bpc? Needless to say, I'm quite confused. Thanks, pq > > > > Similar things happen on amd. Here the output dither depth seems to be > > written to a fixed value however: > > > > - > > https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/amd/display/dc/dce/dce_transform.c#L828 > > > > - > > https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/amd/display/dc/dce/dce_transform.c#L769 > > > > Does anyone know about a resource where I can read up on the used registers > > and what this hardware actually does? > Searching now for a similar register reference for AMD GPUs. > > > > My proposal for now: "max bpc" affects what happens before dither, so I > > would keep "active bpc" the same and add another > > drm property "dither active: true/false". No additional property to control > > dither, as amdgpu does have one already > > (which isn't always active?) and Intel driver does only seem prepared for > > dithering at 6bpc (albeit I don't know why to > > dither at 6bpc and what depth to dither to?).
Re: [PATCH 47/47] drm/i915/guc: Unblock GuC submission on Gen11+
On 24/06/2021 10:05, Matthew Brost wrote: From: Daniele Ceraolo Spurio Unblock GuC submission on Gen11+ platforms. Signed-off-by: Michal Wajdeczko Signed-off-by: Daniele Ceraolo Spurio Signed-off-by: Matthew Brost --- drivers/gpu/drm/i915/gt/uc/intel_guc.h| 1 + drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c | 8 drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h | 3 +-- drivers/gpu/drm/i915/gt/uc/intel_uc.c | 14 +- 4 files changed, 19 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc.h b/drivers/gpu/drm/i915/gt/uc/intel_guc.h index fae01dc8e1b9..77981788204f 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc.h @@ -54,6 +54,7 @@ struct intel_guc { struct ida guc_ids; struct list_head guc_id_list; + bool submission_supported; bool submission_selected; struct i915_vma *ads_vma; diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c index a427336ce916..405339202280 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c @@ -2042,6 +2042,13 @@ void intel_guc_submission_disable(struct intel_guc *guc) /* Note: By the time we're here, GuC may have already been reset */ } +static bool __guc_submission_supported(struct intel_guc *guc) +{ + /* GuC submission is unavailable for pre-Gen11 */ + return intel_guc_is_supported(guc) && + INTEL_GEN(guc_to_gt(guc)->i915) >= 11; +} + static bool __guc_submission_selected(struct intel_guc *guc) { struct drm_i915_private *i915 = guc_to_gt(guc)->i915; @@ -2054,6 +2061,7 @@ static bool __guc_submission_selected(struct intel_guc *guc) void intel_guc_submission_init_early(struct intel_guc *guc) { + guc->submission_supported = __guc_submission_supported(guc); guc->submission_selected = __guc_submission_selected(guc); } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h index a2a3fad72be1..be767eb6ff71 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h @@ -37,8 +37,7 @@ int intel_guc_wait_for_pending_msg(struct intel_guc *guc, static inline bool intel_guc_submission_is_supported(struct intel_guc *guc) { - /* XXX: GuC submission is unavailable for now */ - return false; + return guc->submission_supported; } static inline bool intel_guc_submission_is_wanted(struct intel_guc *guc) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc.c b/drivers/gpu/drm/i915/gt/uc/intel_uc.c index 7a69c3c027e9..61be0aa81492 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_uc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc.c @@ -34,8 +34,15 @@ static void uc_expand_default_options(struct intel_uc *uc) return; } - /* Default: enable HuC authentication only */ - i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; + /* Intermediate platforms are HuC authentication only */ + if (IS_DG1(i915) || IS_ALDERLAKE_S(i915)) { + drm_dbg(&i915->drm, "Disabling GuC only due to old platform\n"); This comment does not seem accurate, given that DG1 is barely out, and ADL is not out yet. How about: "Disabling GuC on untested platforms"? + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; + return; + } + + /* Default: enable HuC authentication and GuC submission */ + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC | ENABLE_GUC_SUBMISSION; This seems to be in contradiction with the GuC submission plan which states: "Not enabled by default on any current platforms but can be enabled via modparam enable_guc". When you rework the patch, could you please add a warning when the user force-enables the GuC Command Submission? Something like: "WARNING: The user force-enabled the experimental GuC command submission backend using i915.enable_guc. Please disable it if experiencing stability issues. No bug reports will be accepted on this backend". This should allow you to work on the backend, while communicating clearly to users that it is not ready just yet. Once it has matured, the warning can be removed. Cheers, Martin } /* Reset GuC providing us with fresh state for both GuC and HuC. @@ -313,9 +320,6 @@ static int __uc_init(struct intel_uc *uc) if (i915_inject_probe_failure(uc_to_gt(uc)->i915)) return -ENOMEM; - /* XXX: GuC submission is unavailable for now */ - GEM_BUG_ON(intel_uc_uses_guc_submission(uc)); - ret = intel_guc_init(guc); if (ret) return ret;
[PATCH v2 0/2] drm/i915: IRQ fixes
(was: drm/i915: Drop all references to DRM IRQ midlayer) Fix a bug in the usage of IRQs and cleanup references to the DRM IRQ midlayer. Preferably this patchset would be merged through drm-misc-next. Thomas Zimmermann (2): drm/i915: Use the correct IRQ during resume drm/i915: Drop all references to DRM IRQ midlayer drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- drivers/gpu/drm/i915/i915_drv.c | 1 - drivers/gpu/drm/i915/i915_irq.c | 10 +- drivers/gpu/drm/i915/i915_irq.h | 1 + 4 files changed, 7 insertions(+), 7 deletions(-) base-commit: 67f5a18128770817e4218a9e496d2bf5047c51e8 -- 2.32.0
[PATCH v2 1/2] drm/i915: Use the correct IRQ during resume
The code in xcs_resume() probably didn't work as intended. It uses struct drm_device.irq, which is allocated to 0, but never initialized by i915 to the device's interrupt number. v2: * wrap irq code in intel_synchronize_hardirq() (Ville) Signed-off-by: Thomas Zimmermann Fixes: 536f77b1caa0 ("drm/i915/gt: Call stop_ring() from ring resume, again") Cc: Chris Wilson Cc: Mika Kuoppala Cc: Daniel Vetter Cc: Rodrigo Vivi Cc: Joonas Lahtinen Cc: Maarten Lankhorst Cc: Lucas De Marchi --- drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- drivers/gpu/drm/i915/i915_irq.c | 5 + drivers/gpu/drm/i915/i915_irq.h | 1 + 3 files changed, 7 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/gt/intel_ring_submission.c b/drivers/gpu/drm/i915/gt/intel_ring_submission.c index 5d42a12ef3d6..1b5a22a83db6 100644 --- a/drivers/gpu/drm/i915/gt/intel_ring_submission.c +++ b/drivers/gpu/drm/i915/gt/intel_ring_submission.c @@ -185,7 +185,7 @@ static int xcs_resume(struct intel_engine_cs *engine) ring->head, ring->tail); /* Double check the ring is empty & disabled before we resume */ - synchronize_hardirq(engine->i915->drm.irq); + intel_synchronize_hardirq(engine->i915); if (!stop_ring(engine)) goto err; diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 7d0ce8b9f8ed..2203dca19895 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -4575,3 +4575,8 @@ void intel_synchronize_irq(struct drm_i915_private *i915) { synchronize_irq(to_pci_dev(i915->drm.dev)->irq); } + +void intel_synchronize_hardirq(struct drm_i915_private *i915) +{ + synchronize_hardirq(to_pci_dev(i915->drm.dev)->irq); +} diff --git a/drivers/gpu/drm/i915/i915_irq.h b/drivers/gpu/drm/i915/i915_irq.h index db34d5dbe402..e43b6734f21b 100644 --- a/drivers/gpu/drm/i915/i915_irq.h +++ b/drivers/gpu/drm/i915/i915_irq.h @@ -94,6 +94,7 @@ void intel_runtime_pm_disable_interrupts(struct drm_i915_private *dev_priv); void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv); bool intel_irqs_enabled(struct drm_i915_private *dev_priv); void intel_synchronize_irq(struct drm_i915_private *i915); +void intel_synchronize_hardirq(struct drm_i915_private *i915); int intel_get_crtc_scanline(struct intel_crtc *crtc); void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, -- 2.32.0
[PATCH v2 2/2] drm/i915: Drop all references to DRM IRQ midlayer
Remove all references to DRM's IRQ midlayer. i915 uses Linux' interrupt functions directly. v2: * also remove an outdated comment * move IRQ fix into separate patch * update Fixes tag (Daniel) Signed-off-by: Thomas Zimmermann Fixes: b318b82455bd ("drm/i915: Nuke drm_driver irq vfuncs") Cc: Ville Syrjälä Cc: Chris Wilson Cc: Jani Nikula Cc: Joonas Lahtinen Cc: Rodrigo Vivi Cc: intel-...@lists.freedesktop.org Cc: # v5.4+ --- drivers/gpu/drm/i915/i915_drv.c | 1 - drivers/gpu/drm/i915/i915_irq.c | 5 - 2 files changed, 6 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 850b499c71c8..73de45472f60 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -42,7 +42,6 @@ #include #include #include -#include #include #include diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 2203dca19895..1d4c683c9de9 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -33,7 +33,6 @@ #include #include -#include #include "display/intel_de.h" #include "display/intel_display_types.h" @@ -4564,10 +4563,6 @@ void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv) bool intel_irqs_enabled(struct drm_i915_private *dev_priv) { - /* -* We only use drm_irq_uninstall() at unload and VT switch, so -* this is the only thing we need to check. -*/ return dev_priv->runtime_pm.irqs_enabled; } -- 2.32.0
Re: [PATCH v4 12/17] drm/uAPI: Add "preferred color format" drm property as setting for userspace
On Tue, 29 Jun 2021 13:39:18 +0200 Werner Sembach wrote: > Am 29.06.21 um 13:17 schrieb Pekka Paalanen: > > On Tue, 29 Jun 2021 08:12:54 + > > Simon Ser wrote: > > > >> On Tuesday, June 22nd, 2021 at 09:15, Pekka Paalanen > >> wrote: > >> > >>> yes, I think this makes sense, even if it is a property that one can't > >>> tell for sure what it does before hand. > >>> > >>> Using a pair of properties, preference and active, to ask for something > >>> and then check what actually worked is good for reducing the > >>> combinatorial explosion caused by needing to "atomic TEST_ONLY commit" > >>> test different KMS configurations. Userspace has a better chance of > >>> finding a configuration that is possible. > >>> > >>> OTOH, this has the problem than in UI one cannot tell the user in > >>> advance which options are truly possible. Given that KMS properties are > >>> rarely completely independent, and in this case known to depend on > >>> several other KMS properties, I think it is good enough to know after > >>> the fact. > >>> > >>> If a driver does not use what userspace prefers, there is no way to > >>> understand why, or what else to change to make it happen. That problem > >>> exists anyway, because TEST_ONLY commits do not give useful feedback > >>> but only a yes/no. > >> By submitting incremental atomic reqs with TEST_ONLY (i.e. only changing > >> one > >> property at a time), user-space can discover which property makes the > >> atomic > >> commit fail. > > That works if the properties are independent of each other. Color > > range, color format, bpc and more may all be interconnected, > > allowing only certain combinations to work. > > > > If all these properties have "auto" setting too, then it would be > > possible to probe each property individually, but that still does not > > tell which combinations are valid. > > > > If you probe towards a certain configuration by setting the properties > > one by one, then depending on the order you pick the properties, you > > may come to a different conclusion on which property breaks the > > configuration. > > My mind crossed another point that must be considered: When plugin in > a Monitor a list of possible Resolutions+Framerate combinations is > created for xrandr and other userspace (I guess by atomic checks? but > I don't know). Hi, I would not think so, but I hope to be corrected if I'm wrong. My belief is that the driver collects a list of modes from EDID, some standard modes, and maybe some other hardcoded modes, and then validates each entry against all the known limitations like vertical and horizontal frequency limits, discarding modes that do not fit. Not all limitations are known during that phase, which is why KMS property "link-status" exists. When userspace actually programs a mode (not a TEST_ONLY commit), the link training may fail. The kernel prunes the mode from the list and sets the link status property to signal failure, and sends a hotplug uevent. Userspace needs to re-check the mode list and try again. That is a generic escape hatch for when TEST_ONLY commit succeeds, but in reality the hardware cannot do it, you just cannot know until you actually try for real. It causes end user visible flicker if it happens on an already running connector, but since it usually happens when turning a connector on to begin with, there is no flicker to be seen, just a small delay in finding a mode that works. > During this drm > properties are already considered, which is no problem atm because as > far as i can tell there is currently no drm property that would make > a certain Resolutions+Framerate combination unreachable that would be > possible with everything on default. I would not expect KMS properties to be considered at all. It would reject modes that are actually possible if the some KMS properties were changed. So at least going forward, current KMS property values cannot factor in. > However for example forcing YCbCr420 encoding would limit the > available resolutions (my screen for example only supports YCbCr420 > on 4k@60 and @50Hz and on no other resolution or frequency (native is > 2560x1440@144Hz). > > So would a "force color format" that does not get resetted on > repluging/reenabling a monitor break the output, for example, of an > not updated xrandr, unaware of this new property? Yes, not because the mode list would be missing the mode, but because actually setting the mode would fail. RandR in particular is problematic, because it does not actually understand any KMS properties, it is merely a relay. So anything that *uses* RandR protocol or xrandr command would also need to be patched to understand the new properties. The kernel automatically resetting *some* properties in *some* occasions seems really fragile and complicated to me, which is why I'm a lot more keen to see a "reset everything to sensible defaults" generic mechanism added to KMS. Thanks, pq pgpL4ow74KRZo.pgp Description: Open
Re: [PATCH] drm/i915: Force DPCD backlight mode for Samsung 16727 panel
On Wed, Jun 30, 2021 at 12:29:05PM +0800, Aaron Ma wrote: > Hi Greg: > > Could this patch get a chance to be applied on stable kernel? > It only for 5.11- kernel, not for Linus' tree. What is the git commit id for it in Linus's tree? And if this is not for Linus's tree, please resubmit it and document the heck out of why it is not valid for Linus's tree and exactly what stable trees you want this applied to (hint, 5.11 is long end-of-life and 5.12 only has about 1-2 more weeks left...) thanks, greg k-h
Re: [PATCH v9 1/5] drm: Add a sharable drm page-pool implementation
Am 30.06.21 um 03:34 schrieb John Stultz: This adds a shrinker controlled page pool, extracted out of the ttm_pool logic, and abstracted out a bit so it can be used by other non-ttm drivers. Cc: Daniel Vetter Cc: Christian Koenig Cc: Sumit Semwal Cc: Liam Mark Cc: Chris Goldsworthy Cc: Laura Abbott Cc: Brian Starkey Cc: Hridya Valsaraju Cc: Suren Baghdasaryan Cc: Sandeep Patil Cc: Daniel Mentz Cc: Ørjan Eide Cc: Robin Murphy Cc: Ezequiel Garcia Cc: Simon Ser Cc: James Jones Cc: linux-me...@vger.kernel.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: John Stultz --- v8: * Completely rewritten from scratch, using only the ttm_pool logic so it can be dual licensed. v9: * Add Kerneldoc comments similar to tmm implementation as suggested by ChristianK * Mark some functions static as suggested by ChristianK * Fix locking issue ChristianK pointed out * Add methods to block the shrinker so users can make atomic calculations across multiple pools, as suggested by ChristianK * Fix up Kconfig dependency issue as Reported-by: kernel test robot --- drivers/gpu/drm/Kconfig | 3 + drivers/gpu/drm/Makefile| 2 + drivers/gpu/drm/page_pool.c | 297 include/drm/page_pool.h | 68 + 4 files changed, 370 insertions(+) create mode 100644 drivers/gpu/drm/page_pool.c create mode 100644 include/drm/page_pool.h diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig index 3c16bd1afd87..52d9ba92b35e 100644 --- a/drivers/gpu/drm/Kconfig +++ b/drivers/gpu/drm/Kconfig @@ -177,6 +177,9 @@ config DRM_DP_CEC Note: not all adapters support this feature, and even for those that do support this they often do not hook up the CEC pin. +config DRM_PAGE_POOL + bool + config DRM_TTM tristate depends on DRM && MMU diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile index 5279db4392df..affa4ca3a08e 100644 --- a/drivers/gpu/drm/Makefile +++ b/drivers/gpu/drm/Makefile @@ -39,6 +39,8 @@ obj-$(CONFIG_DRM_VRAM_HELPER) += drm_vram_helper.o drm_ttm_helper-y := drm_gem_ttm_helper.o obj-$(CONFIG_DRM_TTM_HELPER) += drm_ttm_helper.o +drm-$(CONFIG_DRM_PAGE_POOL) += page_pool.o + drm_kms_helper-y := drm_bridge_connector.o drm_crtc_helper.o drm_dp_helper.o \ drm_dsc.o drm_probe_helper.o \ drm_plane_helper.o drm_dp_mst_topology.o drm_atomic_helper.o \ diff --git a/drivers/gpu/drm/page_pool.c b/drivers/gpu/drm/page_pool.c new file mode 100644 index ..c07bbe3afc32 --- /dev/null +++ b/drivers/gpu/drm/page_pool.c @@ -0,0 +1,297 @@ +// SPDX-License-Identifier: GPL-2.0 OR MIT +/* + * Sharable page pool implementation + * + * Extracted from drivers/gpu/drm/ttm/ttm_pool.c + * Copyright 2020 Advanced Micro Devices, Inc. + * Copyright 2021 Linaro Ltd. + * + * 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 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 COPYRIGHT HOLDER(S) OR AUTHOR(S) 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. + * + * Authors: Christian König, John Stultz + */ + +#include +#include +#include +#include + +static unsigned long page_pool_size; /* max size of the pool */ + +MODULE_PARM_DESC(page_pool_size, "Number of pages in the drm page pool"); +module_param(page_pool_size, ulong, 0644); + +static atomic_long_t nr_managed_pages; + +static struct mutex shrinker_lock; +static struct list_head shrinker_list; +static struct shrinker mm_shrinker; + +/** + * drm_page_pool_set_max - Sets maximum size of all pools + * + * Sets the maximum number of pages allows in all pools. + * This can only be set once, and the first caller wins. + */ +void drm_page_pool_set_max(unsigned long max) +{ + if (!page_pool_size) + page_pool_size = max; +} + +/** + * drm_page_pool_get_max - Maximum size of all pools + * + * Return the maximum number of pages allows in all pools + */ +unsigned long drm_page_pool_get_max(void) +{ + return page_pool_size; +} Well in general I don't think it is a good idea to have getters/sette
Re: [PATCH 2/2] drm/doc/rfc: i915 new parallel submission uAPI plan
On 29/06/2021 22:35, Matthew Brost wrote: Add entry for i915 new parallel submission uAPI plan. v2: (Daniel Vetter): - Expand logical order explaination - Add dummy header - Only allow N BBs in execbuf IOCTL - Configure parallel submission per slot not per gem context v3: (Marcin Ślusarz): - Lot's of typos / bad english fixed (Tvrtko Ursulin): - Consistent pseudo code, clean up wording in descriptions v4: (Daniel Vetter) - Drop flags - Add kernel doc - Reword a few things / fix typos (Tvrtko) - Reword a few things / fix typos v5: (Checkpatch) - Fix typos (Docs) - Fix warning Cc: Tvrtko Ursulin Cc: Tony Ye CC: Carl Zhang Cc: Daniel Vetter Cc: Jason Ekstrand Signed-off-by: Matthew Brost Acked-by: Daniel Vetter Acked-by: Tony Ye --- Documentation/gpu/rfc/i915_parallel_execbuf.h | 122 ++ Documentation/gpu/rfc/i915_scheduler.rst | 59 - 2 files changed, 180 insertions(+), 1 deletion(-) create mode 100644 Documentation/gpu/rfc/i915_parallel_execbuf.h diff --git a/Documentation/gpu/rfc/i915_parallel_execbuf.h b/Documentation/gpu/rfc/i915_parallel_execbuf.h new file mode 100644 index ..8cbe2c4e0172 --- /dev/null +++ b/Documentation/gpu/rfc/i915_parallel_execbuf.h @@ -0,0 +1,122 @@ +/* SPDX-License-Identifier: MIT */ +/* + * Copyright © 2021 Intel Corporation + */ + +#define I915_CONTEXT_ENGINES_EXT_PARALLEL_SUBMIT 2 /* see i915_context_engines_parallel_submit */ + +/** + * struct drm_i915_context_engines_parallel_submit - Configure engine for + * parallel submission. + * + * Setup a slot in the context engine map to allow multiple BBs to be submitted + * in a single execbuf IOCTL. Those BBs will then be scheduled to run on the GPU + * in parallel. Multiple hardware contexts are created internally in the i915 + * run these BBs. The previous sentence makes little sense. Once a slot is configured for N BBs only N BBs can be + * submitted in each execbuf IOCTL and this is implicit behavior e.g. The user + * doesn't tell the execbuf IOCTL there are N BBs, the execbuf IOCTL knows how + * many BBs there are based on the slot's configuration. The N BBs are the last + * N buffer objects or first N if I915_EXEC_BATCH_FIRST is set. + * + * The default placement behavior is to create implicit bonds between each + * context if each context maps to more than 1 physical engine (e.g. context is + * a virtual engine). Also we only allow contexts of same engine class and these + * contexts must be in logically contiguous order. Examples of the placement + * behavior described below. Lastly, the default is to not allow BBs to + * preempted mid BB rather insert coordinated preemption on all hardware + * contexts between each set of BBs. Flags may be added in the future to change + * both of these default behaviors. + * + * Returns -EINVAL if hardware context placement configuration is invalid or if + * the placement configuration isn't supported on the platform / submission + * interface. + * Returns -ENODEV if extension isn't supported on the platform / submission + * interface. + * + * .. code-block:: none + * + * Example 1 pseudo code: + * CS[X] = generic engine of same class, logical instance X + * INVALID = I915_ENGINE_CLASS_INVALID, I915_ENGINE_CLASS_INVALID_NONE + * set_engines(INVALID) + * set_parallel(engine_index=0, width=2, num_siblings=1, + * engines=CS[0],CS[1]) + * + * Results in the following valid placement: + * CS[0], CS[1] + * + * Example 2 pseudo code: + * CS[X] = generic engine of same class, logical instance X + * INVALID = I915_ENGINE_CLASS_INVALID, I915_ENGINE_CLASS_INVALID_NONE + * set_engines(INVALID) + * set_parallel(engine_index=0, width=2, num_siblings=2, + * engines=CS[0],CS[2],CS[1],CS[3]) + * + * Results in the following valid placements: + * CS[0], CS[1] + * CS[2], CS[3] + * + * This can also be thought of as 2 virtual engines described by 2-D array + * in the engines the field with bonds placed between each index of the + * virtual engines. e.g. CS[0] is bonded to CS[1], CS[2] is bonded to + * CS[3]. + * VE[0] = CS[0], CS[2] + * VE[1] = CS[1], CS[3] + * + * Example 3 pseudo code: + * CS[X] = generic engine of same class, logical instance X + * INVALID = I915_ENGINE_CLASS_INVALID, I915_ENGINE_CLASS_INVALID_NONE + * set_engines(INVALID) + * set_parallel(engine_index=0, width=2, num_siblings=2, + * engines=CS[0],CS[1],CS[1],CS[3]) + * + * Results in the following valid and invalid placements: + * CS[0], CS[1] + * CS[1], CS[3] - Not logical contiguous, return -EINVAL + */ +struct drm_i915_context_engines_parallel_submit { + /** +* @base: base user extension. +*/ + struct i915_user_extension base; + + /** +* @engine_index: slot for parallel engine +*/ + __u16 engine_in
Re: [PATCH v9 0/5] Generic page pool & deferred freeing for system dmabuf hea
Am 30.06.21 um 03:34 schrieb John Stultz: After an unfortunately long pause (covid work-schedule burnout), I wanted to revive and resubmit this series. As before, the point of this series is trying to add both a page pool as well as deferred-freeingto the DMA-BUF system heap to improve allocation performance (so that it can match or beat the old ION system heaps performance). The combination of the page pool along with deferred freeing allows us to offload page-zeroing out of the allocation hot path. This was done originally with ION and this patch series allows the DMA-BUF system heap to match ION's system heap allocation performance in a simple microbenchmark [1] (ION re-added to the kernel for comparision, running on an x86 vm image): ./dmabuf-heap-bench -i 0 1 system Testing dmabuf system vs ion heaptype 0 (flags: 0x1) - dmabuf heap: alloc 4096 bytes 5000 times in 79314244 ns 15862 ns/call ion heap:alloc 4096 bytes 5000 times in 107390769 ns 21478 ns/call dmabuf heap: alloc 1048576 bytes 5000 times in 259083419 ns 51816 ns/call ion heap:alloc 1048576 bytes 5000 times in 340497344 ns 68099 ns/call dmabuf heap: alloc 8388608 bytes 5000 times in 2603105563 ns 520621 ns/call ion heap:alloc 8388608 bytes 5000 times in 3613592860 ns 722718 ns/call dmabuf heap: alloc 33554432 bytes 5000 times in 12212492979 ns 2442498 ns/call ion heap:alloc 33554432 bytes 5000 times in 14584157792 ns 2916831 ns/call Daniel didn't like earlier attempts to re-use the network page-pool code to achieve this, and suggested the ttm_pool be used instead, so this series pulls the page pool functionality out of the ttm_pool logic and creates a generic page pool that can be shared. New in v9: * Tried to address Christian König's feedback on the page pool changes (Kerneldoc, static functions, locking issues, duplicative order tracking) * Fix up Kconfig dependency issue as Reported-by: kernel test robot * Fix compiler warning Reported-by: kernel test robot I know Christian had some less specific feedback on the deferred free work that I'd like to revisit, but I wanted to restart the discussion with this new series, rather then trying to dregdge up and reply to a ~4mo old thread. I was already wondering where this was left :) The kernel test robot pointed out quite a number of bugs. I suggest to fix those first and then take a look at my comments on patch #1. Regards, Christian. Input would be greatly appreciated. Testing as well, as I don't have any development hardware that utilizes the ttm pool. Thanks -john [1] https://nam11.safelinks.protection.outlook.com/?url=https%3A%2F%2Fandroid.googlesource.com%2Fplatform%2Fsystem%2Fmemory%2Flibdmabufheap%2F%2B%2Frefs%2Fheads%2Fmaster%2Ftests%2Fdmabuf_heap_bench.c&data=04%7C01%7Cchristian.koenig%40amd.com%7C6d982c8c584d4fb914f208d93b673549%7C3dd8961fe4884e608e11a82d994e183d%7C0%7C0%7C637606136750178732%7CUnknown%7CTWFpbGZsb3d8eyJWIjoiMC4wLjAwMDAiLCJQIjoiV2luMzIiLCJBTiI6Ik1haWwiLCJXVCI6Mn0%3D%7C1000&sdata=iNOuK8umbpkC4oYSM%2FaM3Ybx45FUWQsoRxPDjznBw70%3D&reserved=0 Cc: Daniel Vetter Cc: Christian Koenig Cc: Sumit Semwal Cc: Liam Mark Cc: Chris Goldsworthy Cc: Laura Abbott Cc: Brian Starkey Cc: Hridya Valsaraju Cc: Suren Baghdasaryan Cc: Sandeep Patil Cc: Daniel Mentz Cc: Ørjan Eide Cc: Robin Murphy Cc: Ezequiel Garcia Cc: Simon Ser Cc: James Jones Cc: linux-me...@vger.kernel.org Cc: dri-devel@lists.freedesktop.org John Stultz (5): drm: Add a sharable drm page-pool implementation drm: ttm_pool: Rework ttm_pool to use drm_page_pool dma-buf: system_heap: Add drm pagepool support to system heap dma-buf: heaps: Add deferred-free-helper library code dma-buf: system_heap: Add deferred freeing to the system heap drivers/dma-buf/heaps/Kconfig| 5 + drivers/dma-buf/heaps/Makefile | 1 + drivers/dma-buf/heaps/deferred-free-helper.c | 138 + drivers/dma-buf/heaps/deferred-free-helper.h | 55 drivers/dma-buf/heaps/system_heap.c | 46 ++- drivers/gpu/drm/Kconfig | 4 + drivers/gpu/drm/Makefile | 2 + drivers/gpu/drm/page_pool.c | 297 +++ drivers/gpu/drm/ttm/ttm_pool.c | 167 ++- include/drm/page_pool.h | 68 + include/drm/ttm/ttm_pool.h | 14 +- 11 files changed, 643 insertions(+), 154 deletions(-) create mode 100644 drivers/dma-buf/heaps/deferred-free-helper.c create mode 100644 drivers/dma-buf/heaps/deferred-free-helper.h create mode 100644 drivers/gpu/drm/page_pool.c create mode 100644 include/drm/page_pool.h
Re: [PATCH v15 06/12] swiotlb: Use is_swiotlb_force_bounce for swiotlb data bouncing
On Wed, Jun 30, 2021 at 9:43 AM Nathan Chancellor wrote: > > On Thu, Jun 24, 2021 at 11:55:20PM +0800, Claire Chang wrote: > > Propagate the swiotlb_force into io_tlb_default_mem->force_bounce and > > use it to determine whether to bounce the data or not. This will be > > useful later to allow for different pools. > > > > Signed-off-by: Claire Chang > > Reviewed-by: Christoph Hellwig > > Tested-by: Stefano Stabellini > > Tested-by: Will Deacon > > Acked-by: Stefano Stabellini > > This patch as commit af452ec1b1a3 ("swiotlb: Use is_swiotlb_force_bounce > for swiotlb data bouncing") causes my Ryzen 3 4300G system to fail to > get to an X session consistently (although not every single time), > presumably due to a crash in the AMDGPU driver that I see in dmesg. > > I have attached logs at af452ec1b1a3 and f127c9556a8e and I am happy > to provide any further information, debug, or test patches as necessary. Are you using swiotlb=force? or the swiotlb_map is called because of !dma_capable? (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/kernel/dma/direct.h#n93) `BUG: unable to handle page fault for address: 003a8290` and the fact it crashed at `_raw_spin_lock_irqsave` look like the memory (maybe dev->dma_io_tlb_mem) was corrupted? The dev->dma_io_tlb_mem should be set here (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/drivers/pci/probe.c#n2528) through device_initialize. I can't tell what happened from the logs, but maybe we could try KASAN to see if it provides more clue. Thanks, Claire > > Cheers, > Nathan
Re: [PATCH v4 12/17] drm/uAPI: Add "preferred color format" drm property as setting for userspace
Am 30.06.21 um 10:41 schrieb Pekka Paalanen: On Tue, 29 Jun 2021 13:39:18 +0200 Werner Sembach wrote: Am 29.06.21 um 13:17 schrieb Pekka Paalanen: On Tue, 29 Jun 2021 08:12:54 + Simon Ser wrote: On Tuesday, June 22nd, 2021 at 09:15, Pekka Paalanen wrote: yes, I think this makes sense, even if it is a property that one can't tell for sure what it does before hand. Using a pair of properties, preference and active, to ask for something and then check what actually worked is good for reducing the combinatorial explosion caused by needing to "atomic TEST_ONLY commit" test different KMS configurations. Userspace has a better chance of finding a configuration that is possible. OTOH, this has the problem than in UI one cannot tell the user in advance which options are truly possible. Given that KMS properties are rarely completely independent, and in this case known to depend on several other KMS properties, I think it is good enough to know after the fact. If a driver does not use what userspace prefers, there is no way to understand why, or what else to change to make it happen. That problem exists anyway, because TEST_ONLY commits do not give useful feedback but only a yes/no. By submitting incremental atomic reqs with TEST_ONLY (i.e. only changing one property at a time), user-space can discover which property makes the atomic commit fail. That works if the properties are independent of each other. Color range, color format, bpc and more may all be interconnected, allowing only certain combinations to work. If all these properties have "auto" setting too, then it would be possible to probe each property individually, but that still does not tell which combinations are valid. If you probe towards a certain configuration by setting the properties one by one, then depending on the order you pick the properties, you may come to a different conclusion on which property breaks the configuration. My mind crossed another point that must be considered: When plugin in a Monitor a list of possible Resolutions+Framerate combinations is created for xrandr and other userspace (I guess by atomic checks? but I don't know). Hi, I would not think so, but I hope to be corrected if I'm wrong. My belief is that the driver collects a list of modes from EDID, some standard modes, and maybe some other hardcoded modes, and then validates each entry against all the known limitations like vertical and horizontal frequency limits, discarding modes that do not fit. Not all limitations are known during that phase, which is why KMS property "link-status" exists. When userspace actually programs a mode (not a TEST_ONLY commit), the link training may fail. The kernel prunes the mode from the list and sets the link status property to signal failure, and sends a hotplug uevent. Userspace needs to re-check the mode list and try again. That is a generic escape hatch for when TEST_ONLY commit succeeds, but in reality the hardware cannot do it, you just cannot know until you actually try for real. It causes end user visible flicker if it happens on an already running connector, but since it usually happens when turning a connector on to begin with, there is no flicker to be seen, just a small delay in finding a mode that works. During this drm properties are already considered, which is no problem atm because as far as i can tell there is currently no drm property that would make a certain Resolutions+Framerate combination unreachable that would be possible with everything on default. I would not expect KMS properties to be considered at all. It would reject modes that are actually possible if the some KMS properties were changed. So at least going forward, current KMS property values cannot factor in. At least the debugfs variable "force_yuv420_output" did change the available modes here: https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c#L5165 before my patch https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=68eb3ae3c63708f823aeeb63bb15197c727bd9bf Forcing a color format via a DRM property in this function would reintroduce the problem. And I think i915 driver works similar in this regard. However for example forcing YCbCr420 encoding would limit the available resolutions (my screen for example only supports YCbCr420 on 4k@60 and @50Hz and on no other resolution or frequency (native is 2560x1440@144Hz). So would a "force color format" that does not get resetted on repluging/reenabling a monitor break the output, for example, of an not updated xrandr, unaware of this new property? Yes, not because the mode list would be missing the mode, but because actually setting the mode would fail. Well, like described above, I think the mode would actually be missing, which is also an unexpected behavior from a user perspective. RandR in particular is problematic, because it does not actually understand any KMS properties, it is
[RESEND][PATCH] drm/i915: Force DPCD backlight mode for Samsung 16727 panel
Another Samsung OLED panel needs DPCD to get control of backlight. Kernel 5.12+ support the backlight via: commit: <4a8d79901d5b> ("drm/i915/dp: Enable Intel's HDR backlight interface (only SDR for now)") Only make backlight work on lower versions of kernel. Closes: https://gitlab.freedesktop.org/drm/intel/-/issues/3474 Cc: sta...@vger.kernel.org # 5.11- Signed-off-by: Aaron Ma --- drivers/gpu/drm/drm_dp_helper.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c index 5bd0934004e3..7b91d8a76cd6 100644 --- a/drivers/gpu/drm/drm_dp_helper.c +++ b/drivers/gpu/drm/drm_dp_helper.c @@ -1960,6 +1960,7 @@ static const struct edid_quirk edid_quirk_list[] = { { MFG(0x4d, 0x10), PROD_ID(0xe6, 0x14), BIT(DP_QUIRK_FORCE_DPCD_BACKLIGHT) }, { MFG(0x4c, 0x83), PROD_ID(0x47, 0x41), BIT(DP_QUIRK_FORCE_DPCD_BACKLIGHT) }, { MFG(0x09, 0xe5), PROD_ID(0xde, 0x08), BIT(DP_QUIRK_FORCE_DPCD_BACKLIGHT) }, + { MFG(0x4c, 0x83), PROD_ID(0x57, 0x41), BIT(DP_QUIRK_FORCE_DPCD_BACKLIGHT) }, }; #undef MFG -- 2.32.0
Re: [PATCH v4 03/17] drm/uAPI: Add "active bpc" as feedback channel for "max bpc" drm property
Am 30.06.21 um 10:21 schrieb Pekka Paalanen: On Tue, 29 Jun 2021 13:02:05 +0200 Werner Sembach wrote: Am 28.06.21 um 19:03 schrieb Werner Sembach: Am 18.06.21 um 11:11 schrieb Werner Sembach: Add a new general drm property "active bpc" which can be used by graphic drivers to report the applied bit depth per pixel back to userspace. While "max bpc" can be used to change the color depth, there was no way to check which one actually got used. While in theory the driver chooses the best/highest color depth within the max bpc setting a user might not be fully aware what his hardware is or isn't capable off. This is meant as a quick way to double check the setup. In the future, automatic color calibration for screens might also depend on this information being available. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_connector.c | 51 + include/drm/drm_connector.h | 8 ++ 2 files changed, 59 insertions(+) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index da39e7ff6965..943f6b61053b 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -1197,6 +1197,14 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { *drm_connector_attach_max_bpc_property() to create and attach the *property to the connector during initialization. * + * active bpc: + * This read-only range property tells userspace the pixel color bit depth + * actually used by the hardware display engine on "the cable" on a + * connector. The chosen value depends on hardware capabilities, both + * display engine and connected monitor, and the "max bpc" property. + * Drivers shall use drm_connector_attach_active_bpc_property() to install + * this property. + * Regarding "on the cable" and dithering: As far as I can tell, what the dithering option does, is setting a hardware register here: - https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4534 - https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4571 So dithering seems to be calculated by fixed purpose hardware/firmware outside of the driver? The Intel driver does not seem to set a target bpc/bpp for this hardware so I guess it defaults to 6 or 8 bpc? Never mind it does. This switch-case does affect the dithering output: https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/i915/display/intel_display.c#L4537 Hi, I obviously do not know the intel driver or hardware at all, but to me that just looks like translating from bits per pixel to bits per channel in RGB mapping? No, if i understand the documentation correctly: Writing bit depth here with dithering enabled sets the dithering target bpc. As found in this documentation p.548: https://01.org/sites/default/files/documentation/intel-gfx-prm-osrc-lkf-vol02c-commandreference-registers-part2.pdf So max bpc and active bpc are affecting/affected by the bpc after dithering. By definition, if the cable carries N bpc, then dithering does not change that. The cable still carries N bpc, but due to spatial or temporal dithering, the *observed* color resolution may or may not be higher than the cable bpc. Yes, and max bpc and active bpc tell the cable bpc ist not the *observed* bpc. Of course, if the cable bpc is 8, and dithering targets 6 bpc, then 2 LSB on the cable are always zero, right? I would assume that in this case only 6 bpc are actually send? Isn't the whole thing of dithering that you can't send, for example, 8 bpc? Maybe one would want to do that if the monitor has a 6 bit panel and it simply ignored the 2 LSB, and the cable cannot go down to 6 bpc. Is there dithering actually doing this? aka is my assumption above wrong? AMD code that confused me before, is hinting that you might be right: https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/amd/display/dc/dce/dce_transform.c#L826 there is a set_clamp depth and a separate DCP_SPATIAL_DITHER_DEPTH_30BPP So, what does "max bpc" mean right now? It seems like dither on/off is insufficient information, one would also need to control the dithering target bpc. I suppose the driver has a policy on how it chooses the target bpc, but what is that policy? Is the dither target bpc the cable bpc or the sink bpc? Needless to say, I'm quite confused. ... We need someone who knows what dithering on intel and amd gpu actually means. But I don't want this to become a blocker for this patchset, because if there is no dithering, which seems to be the norm, the active bpc property is already really usefull as it is. So add a note to the docs that the value might be invalid when dithering is active for now? Thanks, pq Similar things happen on amd. Here the output dither depth seems to be written to a fixed value however: - https://elixir.bootlin.com/linux/v5.13/source/drivers/gpu/drm/amd/display/
[PATCH v3 0/2] drm/i915: IRQ fixes
Fix a bug in the usage of IRQs and cleanup references to the DRM IRQ midlayer. Preferably this patchset would be merged through drm-misc-next. v3: * also use intel_synchronize_hardirq() from other callsite v2: * split patch * also fix comment * add intel_synchronize_hardirq() (Ville) * update Fixes tag (Daniel) Thomas Zimmermann (2): drm/i915: Use the correct IRQ during resume drm/i915: Drop all references to DRM IRQ midlayer drivers/gpu/drm/i915/gt/intel_engine_cs.c | 2 +- drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- drivers/gpu/drm/i915/i915_drv.c | 1 - drivers/gpu/drm/i915/i915_irq.c | 10 +- drivers/gpu/drm/i915/i915_irq.h | 1 + 5 files changed, 8 insertions(+), 8 deletions(-) base-commit: 67f5a18128770817e4218a9e496d2bf5047c51e8 -- 2.32.0
[PATCH v3 1/2] drm/i915: Use the correct IRQ during resume
The code in xcs_resume() probably didn't work as intended. It uses struct drm_device.irq, which is allocated to 0, but never initialized by i915 to the device's interrupt number. v3: * also use intel_synchronize_hardirq() at another callsite v2: * wrap irq code in intel_synchronize_hardirq() (Ville) Signed-off-by: Thomas Zimmermann Fixes: 536f77b1caa0 ("drm/i915/gt: Call stop_ring() from ring resume, again") Cc: Chris Wilson Cc: Mika Kuoppala Cc: Daniel Vetter Cc: Rodrigo Vivi Cc: Joonas Lahtinen Cc: Maarten Lankhorst Cc: Lucas De Marchi --- drivers/gpu/drm/i915/gt/intel_engine_cs.c | 2 +- drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- drivers/gpu/drm/i915/i915_irq.c | 5 + drivers/gpu/drm/i915/i915_irq.h | 1 + 4 files changed, 8 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/gt/intel_engine_cs.c b/drivers/gpu/drm/i915/gt/intel_engine_cs.c index 88694822716a..5ca3d1664335 100644 --- a/drivers/gpu/drm/i915/gt/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/gt/intel_engine_cs.c @@ -1229,7 +1229,7 @@ bool intel_engine_is_idle(struct intel_engine_cs *engine) return true; /* Waiting to drain ELSP? */ - synchronize_hardirq(to_pci_dev(engine->i915->drm.dev)->irq); + intel_synchronize_hardirq(engine->i915); intel_engine_flush_submission(engine); /* ELSP is empty, but there are ready requests? E.g. after reset */ diff --git a/drivers/gpu/drm/i915/gt/intel_ring_submission.c b/drivers/gpu/drm/i915/gt/intel_ring_submission.c index 5d42a12ef3d6..1b5a22a83db6 100644 --- a/drivers/gpu/drm/i915/gt/intel_ring_submission.c +++ b/drivers/gpu/drm/i915/gt/intel_ring_submission.c @@ -185,7 +185,7 @@ static int xcs_resume(struct intel_engine_cs *engine) ring->head, ring->tail); /* Double check the ring is empty & disabled before we resume */ - synchronize_hardirq(engine->i915->drm.irq); + intel_synchronize_hardirq(engine->i915); if (!stop_ring(engine)) goto err; diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 7d0ce8b9f8ed..2203dca19895 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -4575,3 +4575,8 @@ void intel_synchronize_irq(struct drm_i915_private *i915) { synchronize_irq(to_pci_dev(i915->drm.dev)->irq); } + +void intel_synchronize_hardirq(struct drm_i915_private *i915) +{ + synchronize_hardirq(to_pci_dev(i915->drm.dev)->irq); +} diff --git a/drivers/gpu/drm/i915/i915_irq.h b/drivers/gpu/drm/i915/i915_irq.h index db34d5dbe402..e43b6734f21b 100644 --- a/drivers/gpu/drm/i915/i915_irq.h +++ b/drivers/gpu/drm/i915/i915_irq.h @@ -94,6 +94,7 @@ void intel_runtime_pm_disable_interrupts(struct drm_i915_private *dev_priv); void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv); bool intel_irqs_enabled(struct drm_i915_private *dev_priv); void intel_synchronize_irq(struct drm_i915_private *i915); +void intel_synchronize_hardirq(struct drm_i915_private *i915); int intel_get_crtc_scanline(struct intel_crtc *crtc); void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, -- 2.32.0
[PATCH v3 2/2] drm/i915: Drop all references to DRM IRQ midlayer
Remove all references to DRM's IRQ midlayer. i915 uses Linux' interrupt functions directly. v2: * also remove an outdated comment * move IRQ fix into separate patch * update Fixes tag (Daniel) Signed-off-by: Thomas Zimmermann Fixes: b318b82455bd ("drm/i915: Nuke drm_driver irq vfuncs") Cc: Ville Syrjälä Cc: Chris Wilson Cc: Jani Nikula Cc: Joonas Lahtinen Cc: Rodrigo Vivi Cc: intel-...@lists.freedesktop.org Cc: # v5.4+ --- drivers/gpu/drm/i915/i915_drv.c | 1 - drivers/gpu/drm/i915/i915_irq.c | 5 - 2 files changed, 6 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 850b499c71c8..73de45472f60 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -42,7 +42,6 @@ #include #include #include -#include #include #include diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 2203dca19895..1d4c683c9de9 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -33,7 +33,6 @@ #include #include -#include #include "display/intel_de.h" #include "display/intel_display_types.h" @@ -4564,10 +4563,6 @@ void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv) bool intel_irqs_enabled(struct drm_i915_private *dev_priv) { - /* -* We only use drm_irq_uninstall() at unload and VT switch, so -* this is the only thing we need to check. -*/ return dev_priv->runtime_pm.irqs_enabled; } -- 2.32.0
Re: [PATCH v3] drm/radeon: Fix NULL dereference when updating memory stats
Am 24.06.21 um 06:51 schrieb Mikel Rychliski: radeon_ttm_bo_destroy() is attempting to access the resource object to update memory counters. However, the resource object is already freed when ttm calls this function via the destroy callback. This causes an oops when a bo is freed: BUG: kernel NULL pointer dereference, address: 0010 RIP: 0010:radeon_ttm_bo_destroy+0x2c/0x100 [radeon] Call Trace: radeon_bo_unref+0x1a/0x30 [radeon] radeon_gem_object_free+0x33/0x50 [radeon] drm_gem_object_release_handle+0x69/0x70 [drm] drm_gem_handle_delete+0x62/0xa0 [drm] ? drm_mode_destroy_dumb+0x40/0x40 [drm] drm_ioctl_kernel+0xb2/0xf0 [drm] drm_ioctl+0x30a/0x3c0 [drm] ? drm_mode_destroy_dumb+0x40/0x40 [drm] radeon_drm_ioctl+0x49/0x80 [radeon] __x64_sys_ioctl+0x8e/0xd0 Avoid the issue by updating the counters in the delete_mem_notify callback instead. Also, fix memory statistic updating in radeon_bo_move() to identify the source type correctly. The source type needs to be saved before the move, because the moved from object may be altered by the move. Fixes: bfa3357ef9ab ("drm/ttm: allocate resource object instead of embedding it v2") Signed-off-by: Mikel Rychliski So, back from vacation. I've reviewed and pushed the patch to drm-misc-next. Thanks for the help, Christian. --- drivers/gpu/drm/radeon/radeon_object.c | 29 - drivers/gpu/drm/radeon/radeon_object.h | 2 +- drivers/gpu/drm/radeon/radeon_ttm.c| 13 ++--- 3 files changed, 23 insertions(+), 21 deletions(-) diff --git a/drivers/gpu/drm/radeon/radeon_object.c b/drivers/gpu/drm/radeon/radeon_object.c index bfaaa3c969a3..56ede9d63b12 100644 --- a/drivers/gpu/drm/radeon/radeon_object.c +++ b/drivers/gpu/drm/radeon/radeon_object.c @@ -49,23 +49,23 @@ static void radeon_bo_clear_surface_reg(struct radeon_bo *bo); * function are calling it. */ -static void radeon_update_memory_usage(struct radeon_bo *bo, - unsigned mem_type, int sign) +static void radeon_update_memory_usage(struct ttm_buffer_object *bo, + unsigned int mem_type, int sign) { - struct radeon_device *rdev = bo->rdev; + struct radeon_device *rdev = radeon_get_rdev(bo->bdev); switch (mem_type) { case TTM_PL_TT: if (sign > 0) - atomic64_add(bo->tbo.base.size, &rdev->gtt_usage); + atomic64_add(bo->base.size, &rdev->gtt_usage); else - atomic64_sub(bo->tbo.base.size, &rdev->gtt_usage); + atomic64_sub(bo->base.size, &rdev->gtt_usage); break; case TTM_PL_VRAM: if (sign > 0) - atomic64_add(bo->tbo.base.size, &rdev->vram_usage); + atomic64_add(bo->base.size, &rdev->vram_usage); else - atomic64_sub(bo->tbo.base.size, &rdev->vram_usage); + atomic64_sub(bo->base.size, &rdev->vram_usage); break; } } @@ -76,8 +76,6 @@ static void radeon_ttm_bo_destroy(struct ttm_buffer_object *tbo) bo = container_of(tbo, struct radeon_bo, tbo); - radeon_update_memory_usage(bo, bo->tbo.resource->mem_type, -1); - mutex_lock(&bo->rdev->gem.mutex); list_del_init(&bo->list); mutex_unlock(&bo->rdev->gem.mutex); @@ -727,24 +725,21 @@ int radeon_bo_check_tiling(struct radeon_bo *bo, bool has_moved, } void radeon_bo_move_notify(struct ttm_buffer_object *bo, - bool evict, + unsigned int old_type, struct ttm_resource *new_mem) { struct radeon_bo *rbo; + radeon_update_memory_usage(bo, old_type, -1); + if (new_mem) + radeon_update_memory_usage(bo, new_mem->mem_type, 1); + if (!radeon_ttm_bo_is_radeon_bo(bo)) return; rbo = container_of(bo, struct radeon_bo, tbo); radeon_bo_check_tiling(rbo, 0, 1); radeon_vm_bo_invalidate(rbo->rdev, rbo); - - /* update statistics */ - if (!new_mem) - return; - - radeon_update_memory_usage(rbo, bo->resource->mem_type, -1); - radeon_update_memory_usage(rbo, new_mem->mem_type, 1); } vm_fault_t radeon_bo_fault_reserve_notify(struct ttm_buffer_object *bo) diff --git a/drivers/gpu/drm/radeon/radeon_object.h b/drivers/gpu/drm/radeon/radeon_object.h index 1739c6a142cd..1afc7992ef91 100644 --- a/drivers/gpu/drm/radeon/radeon_object.h +++ b/drivers/gpu/drm/radeon/radeon_object.h @@ -161,7 +161,7 @@ extern void radeon_bo_get_tiling_flags(struct radeon_bo *bo, extern int radeon_bo_check_tiling(struct radeon_bo *bo, bool has_moved, bool force_drop); extern void radeon_bo_move_no
Re: [PULL] drm-intel-next-fixes
On Tue, 29 Jun 2021, Rodrigo Vivi wrote: > Hi Dave and Daniel, > > Here goes drm-intel-next-fixes-2021-06-29: > > The biggest fix is the restoration of mmap ioctl for gen12 integrated parts > which lack was breaking ADL-P with media stack. > Besides that a small selftest fix and a theoretical overflow on > i915->pipe_to_crtc_mapping. My last fixes pull for v5.13 fell between the cracks [1]. There was one stable worthy fix, but since it was still in drm-intel-fixes when you ran dim cherry-pick-next-fixes, it was skipped for drm-intel-next-fixes. I've now dropped the commit and pushed v5.13 to drm-intel-fixes, as we're past that point. Subsequent dim cherry-pick-next-fixes should pick it up now. Please do another next fixes pull request with that. (It's okay to pull this one already though, doesn't make a difference.) BR, Jani. [1] https://lore.kernel.org/r/87czsbu15r@intel.com > > Thanks, > Rodrigo. > > The following changes since commit 1bd8a7dc28c1c410f1ceefae1f2a97c06d1a67c2: > > Merge tag 'exynos-drm-next-for-v5.14' of > git://git.kernel.org/pub/scm/linux/kernel/git/daeinki/drm-exynos into > drm-next (2021-06-11 14:19:12 +1000) > > are available in the Git repository at: > > git://anongit.freedesktop.org/drm/drm-intel > tags/drm-intel-next-fixes-2021-06-29 > > for you to fetch changes up to c90c4c6574f3feaf2203b5671db1907a1e15c653: > > drm/i915: Reinstate the mmap ioctl for some platforms (2021-06-28 07:43:56 > -0400) > > > The biggest fix is the restoration of mmap ioctl for gen12 integrated parts > which lack was breaking ADL-P with media stack. > Besides that a small selftest fix and a theoretical overflow on > i915->pipe_to_crtc_mapping. > > > Chris Wilson (1): > drm/i915/selftests: Reorder tasklet_disable vs local_bh_disable > > Jani Nikula (1): > drm/i915/dsc: abstract helpers to get bigjoiner primary/secondary crtc > > Thomas Hellström (1): > drm/i915: Reinstate the mmap ioctl for some platforms > > drivers/gpu/drm/i915/display/intel_display.c | 7 ++- > drivers/gpu/drm/i915/display/intel_display_types.h | 8 > drivers/gpu/drm/i915/display/intel_vdsc.c | 40 +++- > drivers/gpu/drm/i915/display/intel_vdsc.h | 1 + > drivers/gpu/drm/i915/gem/i915_gem_mman.c | 7 +-- > drivers/gpu/drm/i915/gt/selftest_execlists.c | 55 > +- > 6 files changed, 76 insertions(+), 42 deletions(-) -- Jani Nikula, Intel Open Source Graphics Center
Re: [PATCH v3 2/2] drm/i915: Drop all references to DRM IRQ midlayer
On Wed, Jun 30, 2021 at 11:52:28AM +0200, Thomas Zimmermann wrote: > Remove all references to DRM's IRQ midlayer. i915 uses Linux' interrupt > functions directly. > > v2: > * also remove an outdated comment > * move IRQ fix into separate patch > * update Fixes tag (Daniel) > > Signed-off-by: Thomas Zimmermann > Fixes: b318b82455bd ("drm/i915: Nuke drm_driver irq vfuncs") > Cc: Ville Syrjälä > Cc: Chris Wilson > Cc: Jani Nikula > Cc: Joonas Lahtinen > Cc: Rodrigo Vivi > Cc: intel-...@lists.freedesktop.org > Cc: # v5.4+ > --- > drivers/gpu/drm/i915/i915_drv.c | 1 - > drivers/gpu/drm/i915/i915_irq.c | 5 - > 2 files changed, 6 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c > index 850b499c71c8..73de45472f60 100644 > --- a/drivers/gpu/drm/i915/i915_drv.c > +++ b/drivers/gpu/drm/i915/i915_drv.c > @@ -42,7 +42,6 @@ > #include > #include > #include > -#include > #include > #include > > diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c > index 2203dca19895..1d4c683c9de9 100644 > --- a/drivers/gpu/drm/i915/i915_irq.c > +++ b/drivers/gpu/drm/i915/i915_irq.c > @@ -33,7 +33,6 @@ > #include > > #include > -#include > > #include "display/intel_de.h" > #include "display/intel_display_types.h" > @@ -4564,10 +4563,6 @@ void intel_runtime_pm_enable_interrupts(struct > drm_i915_private *dev_priv) > > bool intel_irqs_enabled(struct drm_i915_private *dev_priv) > { > - /* > - * We only use drm_irq_uninstall() at unload and VT switch, so > - * this is the only thing we need to check. > - */ > return dev_priv->runtime_pm.irqs_enabled; > } > > -- > 2.32.0 > How is this a stable-kernel-related fix? thanks, greg k-h
Re: [PATCH 2/3] iommu/io-pgtable-arm: Add IOMMU_LLC page protection flag
Hi Will, On 2021-03-25 23:03, Will Deacon wrote: On Tue, Mar 09, 2021 at 12:10:44PM +0530, Sai Prakash Ranjan wrote: On 2021-02-05 17:38, Sai Prakash Ranjan wrote: > On 2021-02-04 03:16, Will Deacon wrote: > > On Tue, Feb 02, 2021 at 11:56:27AM +0530, Sai Prakash Ranjan wrote: > > > On 2021-02-01 23:50, Jordan Crouse wrote: > > > > On Mon, Feb 01, 2021 at 08:20:44AM -0800, Rob Clark wrote: > > > > > On Mon, Feb 1, 2021 at 3:16 AM Will Deacon wrote: > > > > > > On Fri, Jan 29, 2021 at 03:12:59PM +0530, Sai Prakash Ranjan wrote: > > > > > > > On 2021-01-29 14:35, Will Deacon wrote: > > > > > > > > On Mon, Jan 11, 2021 at 07:45:04PM +0530, Sai Prakash Ranjan wrote: > > > > > > > > > +#define IOMMU_LLC(1 << 6) > > > > > > > > > > > > > > > > On reflection, I'm a bit worried about exposing this because I think it > > > > > > > > will > > > > > > > > introduce a mismatched virtual alias with the CPU (we don't even have a > > > > > > > > MAIR > > > > > > > > set up for this memory type). Now, we also have that issue for the PTW, > > > > > > > > but > > > > > > > > since we always use cache maintenance (i.e. the streaming API) for > > > > > > > > publishing the page-tables to a non-coheren walker, it works out. > > > > > > > > However, > > > > > > > > if somebody expects IOMMU_LLC to be coherent with a DMA API coherent > > > > > > > > allocation, then they're potentially in for a nasty surprise due to the > > > > > > > > mismatched outer-cacheability attributes. > > > > > > > > > > > > > > > > > > > > > > Can't we add the syscached memory type similar to what is done on android? > > > > > > > > > > > > Maybe. How does the GPU driver map these things on the CPU side? > > > > > > > > > > Currently we use writecombine mappings for everything, although there > > > > > are some cases that we'd like to use cached (but have not merged > > > > > patches that would give userspace a way to flush/invalidate) > > > > > > > > > > > > > LLC/system cache doesn't have a relationship with the CPU cache. Its > > > > just a > > > > little accelerator that sits on the connection from the GPU to DDR and > > > > caches > > > > accesses. The hint that Sai is suggesting is used to mark the buffers as > > > > 'no-write-allocate' to prevent GPU write operations from being cached in > > > > the LLC > > > > which a) isn't interesting and b) takes up cache space for read > > > > operations. > > > > > > > > Its easiest to think of the LLC as a bonus accelerator that has no cost > > > > for > > > > us to use outside of the unfortunate per buffer hint. > > > > > > > > We do have to worry about the CPU cache w.r.t I/O coherency (which is a > > > > different hint) and in that case we have all of concerns that Will > > > > identified. > > > > > > > > > > For mismatched outer cacheability attributes which Will > > > mentioned, I was > > > referring to [1] in android kernel. > > > > I've lost track of the conversation here :/ > > > > When the GPU has a buffer mapped with IOMMU_LLC, is the buffer also > > mapped > > into the CPU and with what attributes? Rob said "writecombine for > > everything" -- does that mean ioremap_wc() / MEMREMAP_WC? > > > > Rob answered this. > > > Finally, we need to be careful when we use the word "hint" as > > "allocation > > hint" has a specific meaning in the architecture, and if we only > > mismatch on > > those then we're actually ok. But I think IOMMU_LLC is more than > > just a > > hint, since it actually drives eviction policy (i.e. it enables > > writeback). > > > > Sorry for the pedantry, but I just want to make sure we're all talking > > about the same things! > > > > Sorry for the confusion which probably was caused by my mentioning of > android, NWA(no write allocate) is an allocation hint which we can > ignore > for now as it is not introduced yet in upstream. > Any chance of taking this forward? We do not want to miss out on small fps gain when the product gets released. Do we have a solution to the mismatched virtual alias? Sorry for the long delay on this thread. For mismatched virtual alias question, wasn't this already discussed in stretch when initial support for system cache [1] (which was reverted by you) was added? Excerpt from there, "As seen in downstream kernels there are few non-coherent devices which would not want to allocate in system cache, and therefore would want Inner/Outer non-cached memory. So, we may want to either override the attributes per-device, or as you suggested we may want to introduce another memory type 'sys-cached' that can be added with its separate infra." As for DMA API usage, we do not have any upstream users (video will be one if they decide to upstream that). [1] https://patchwork.kernel.org/project/linux-arm-msm/patch/20180615105329.26800-1-vivek.gau...@codeaurora.org/ Thanks, Sai -- QUALCOMM INDIA, on behalf of Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by The Linux Foundation
Re: [RFC PATCH 2/9] drm: bridge: Add Samsung SEC MIPI DSIM bridge driver
Hi Frieder, Thanks for sharing the details. On Mon, Jun 28, 2021 at 1:49 PM Frieder Schrempf wrote: > > Hi Jagan, > > On 24.06.21 10:30, Krzysztof Kozlowski wrote: > > On 24/06/2021 04:48, Fabio Estevam wrote: > >> Hi Jagan/Laurent, > >> > >> On Wed, Jun 23, 2021 at 7:23 PM Laurent Pinchart > >> wrote: > >> > >>> Looking at the register set, it seems to match the Exynos 5433, > >>> supported by drivers/gpu/drm/exynos/exynos_drm_dsi.c. Can we leverage > >>> that driver instead of adding a new one for the same IP core ? > >> > >> Yes. there was an attempt from Michael in this direction: > >> https://eur04.safelinks.protection.outlook.com/?url=https%3A%2F%2Fpatchwork.kernel.org%2Fproject%2Fdri-devel%2Fcover%2F20200911135413.3654800-1-m.tretter%40pengutronix.de%2F&data=04%7C01%7Cfrieder.schrempf%40kontron.de%7C52db05459ef0462d5a9b08d936eab1ba%7C8c9d3c973fd941c8a2b1646f3942daf1%7C0%7C0%7C637601203901391193%7CUnknown%7CTWFpbGZsb3d8eyJWIjoiMC4wLjAwMDAiLCJQIjoiV2luMzIiLCJBTiI6Ik1haWwiLCJXVCI6Mn0%3D%7C1000&sdata=LTYk9kpUeB9bgfRITQT6wIij3XTOIk37AHXbzQ2UI4Y%3D&reserved=0 > > > > That's the proper direction (maybe as Marek suggested - sharing common > > code like for Analogix DP), not duplicating a driver. > > > > Just to make sure that you are aware of the previous patches and discussions > here are some additional pointers: > > * i.MX8MM glue code from Marek (+ Cc): [1] > * DPHY driver from Marek: [2] > * General discussion about driver implementation: [3] > * Daniel's (+ Cc) suggested direction to move forward: [4] It Looks like Daniel's suggestion is to have a common bridge driver without sharing a code between platforms. It makes sense and clean but the key issues lie on the exynos side, the exynos drm drives require potential changes and tests, which indeed are hard but possible - IMHO. However there is another issue with component_ops the i.MX8M side MXSFB doesn't use any component_ops but the exynos are fully component aware. > > It looks like you already did a fork of the Exynos driver, so your approach > might be generally in line with what Daniel suggested. I did use PMS computation from exynos and reference driver from imx8 tree. Last 2 days I worked on exynos_drm_dsi.c (with some additions) and converted a bridge driver and it worked on my i.MX8MM platform. Right now, I'm checking the possible implementations and will come back to my approach for further comments. Jagan.
Re: [PATCH v5 3/3] drm: protect drm_master pointers in drm_lease.c
On 30/6/21 4:02 pm, Daniel Vetter wrote: On Wed, Jun 30, 2021 at 9:18 AM Desmond Cheong Zhi Xi wrote: On 30/6/21 12:07 am, Daniel Vetter wrote: On Tue, Jun 29, 2021 at 11:37:06AM +0800, Desmond Cheong Zhi Xi wrote: Currently, direct copies of drm_file->master pointers should be protected by drm_device.master_mutex when being dereferenced. This is because drm_file->master is not invariant for the lifetime of drm_file. If drm_file is not the creator of master, then drm_file->is_master is false, and a call to drm_setmaster_ioctl will invoke drm_new_set_master, which then allocates a new master for drm_file and puts the old master. Thus, without holding drm_device.master_mutex, the old value of drm_file->master could be freed while it is being used by another concurrent process. In drm_lease.c, there are multiple instances where drm_file->master is accessed and dereferenced while drm_device.master_mutex is not held. This makes drm_lease.c vulnerable to use-after-free bugs. We address this issue in 3 ways: 1. Clarify in the kerneldoc that drm_file->master is protected by drm_device.master_mutex. 2. Add a new drm_file_get_master() function that calls drm_master_get on drm_file->master while holding on to drm_device.master_mutex. Since drm_master_get increments the reference count of master, this prevents master from being freed until we unreference it with drm_master_put. 3. In each case where drm_file->master is directly accessed and eventually dereferenced in drm_lease.c, we wrap the access in a call to the new drm_file_get_master function, then unreference the master pointer once we are done using it. Reported-by: Daniel Vetter Signed-off-by: Desmond Cheong Zhi Xi Series looks very nice, let's see what intel-gfx-ci says. You should get a mail, but results are also here: https://patchwork.freedesktop.org/series/91969/#rev2 One tiny comment below. --- drivers/gpu/drm/drm_auth.c | 25 drivers/gpu/drm/drm_lease.c | 77 +++-- include/drm/drm_auth.h | 1 + include/drm/drm_file.h | 15 ++-- 4 files changed, 95 insertions(+), 23 deletions(-) diff --git a/drivers/gpu/drm/drm_auth.c b/drivers/gpu/drm/drm_auth.c index ab1863c5a5a0..c36a0b72be26 100644 --- a/drivers/gpu/drm/drm_auth.c +++ b/drivers/gpu/drm/drm_auth.c @@ -384,6 +384,31 @@ struct drm_master *drm_master_get(struct drm_master *master) } EXPORT_SYMBOL(drm_master_get); +/** + * drm_file_get_master - reference &drm_file.master of @file_priv + * @file_priv: DRM file private + * + * Increments the reference count of @file_priv's &drm_file.master and returns + * the &drm_file.master. If @file_priv has no &drm_file.master, returns NULL. + * + * Master pointers returned from this function should be unreferenced using + * drm_master_put(). + */ +struct drm_master *drm_file_get_master(struct drm_file *file_priv) +{ +struct drm_master *master = NULL; + +mutex_lock(&file_priv->minor->dev->master_mutex); +if (!file_priv->master) +goto unlock; +master = drm_master_get(file_priv->master); + +unlock: +mutex_unlock(&file_priv->minor->dev->master_mutex); +return master; +} +EXPORT_SYMBOL(drm_file_get_master); + static void drm_master_destroy(struct kref *kref) { struct drm_master *master = container_of(kref, struct drm_master, refcount); diff --git a/drivers/gpu/drm/drm_lease.c b/drivers/gpu/drm/drm_lease.c index 00fb433bcef1..cdcc87fa9685 100644 --- a/drivers/gpu/drm/drm_lease.c +++ b/drivers/gpu/drm/drm_lease.c @@ -106,10 +106,19 @@ static bool _drm_has_leased(struct drm_master *master, int id) */ bool _drm_lease_held(struct drm_file *file_priv, int id) { -if (!file_priv || !file_priv->master) +bool ret; +struct drm_master *master; + +if (!file_priv) return true; -return _drm_lease_held_master(file_priv->master, id); +master = drm_file_get_master(file_priv); +if (master == NULL) +return true; +ret = _drm_lease_held_master(master, id); +drm_master_put(&master); + +return ret; } /** @@ -128,13 +137,20 @@ bool drm_lease_held(struct drm_file *file_priv, int id) struct drm_master *master; bool ret; -if (!file_priv || !file_priv->master || !file_priv->master->lessor) +if (!file_priv) return true; -master = file_priv->master; +master = drm_file_get_master(file_priv); +if (master == NULL) +return true; +if (!master->lessor) { +drm_master_put(&master); +return true; +} mutex_lock(&master->dev->mode_config.idr_mutex); ret = _drm_lease_held_master(master, id); mutex_unlock(&master->dev->mode_config.idr_mutex); +drm_master_put(&master); return ret; } @@ -154,10 +170,16 @@ uint32_t drm_lease_filter_crtcs(struct drm_file *file_priv, uint32_t crtcs_in) int count_in, count_out; uint32_t crtcs_out = 0; -if (!file_priv
Re: [PATCH v3 1/2] drm/i915: Use the correct IRQ during resume
On Wed, Jun 30, 2021 at 11:52:27AM +0200, Thomas Zimmermann wrote: > The code in xcs_resume() probably didn't work as intended. It uses > struct drm_device.irq, which is allocated to 0, but never initialized > by i915 to the device's interrupt number. > > v3: > * also use intel_synchronize_hardirq() at another callsite > v2: > * wrap irq code in intel_synchronize_hardirq() (Ville) > > Signed-off-by: Thomas Zimmermann > Fixes: 536f77b1caa0 ("drm/i915/gt: Call stop_ring() from ring resume, again") > Cc: Chris Wilson > Cc: Mika Kuoppala > Cc: Daniel Vetter > Cc: Rodrigo Vivi > Cc: Joonas Lahtinen > Cc: Maarten Lankhorst > Cc: Lucas De Marchi > --- > drivers/gpu/drm/i915/gt/intel_engine_cs.c | 2 +- > drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- > drivers/gpu/drm/i915/i915_irq.c | 5 + > drivers/gpu/drm/i915/i915_irq.h | 1 + > 4 files changed, 8 insertions(+), 2 deletions(-) > > diff --git a/drivers/gpu/drm/i915/gt/intel_engine_cs.c > b/drivers/gpu/drm/i915/gt/intel_engine_cs.c > index 88694822716a..5ca3d1664335 100644 > --- a/drivers/gpu/drm/i915/gt/intel_engine_cs.c > +++ b/drivers/gpu/drm/i915/gt/intel_engine_cs.c > @@ -1229,7 +1229,7 @@ bool intel_engine_is_idle(struct intel_engine_cs > *engine) > return true; > > /* Waiting to drain ELSP? */ > - synchronize_hardirq(to_pci_dev(engine->i915->drm.dev)->irq); > + intel_synchronize_hardirq(engine->i915); > intel_engine_flush_submission(engine); > > /* ELSP is empty, but there are ready requests? E.g. after reset */ > diff --git a/drivers/gpu/drm/i915/gt/intel_ring_submission.c > b/drivers/gpu/drm/i915/gt/intel_ring_submission.c > index 5d42a12ef3d6..1b5a22a83db6 100644 > --- a/drivers/gpu/drm/i915/gt/intel_ring_submission.c > +++ b/drivers/gpu/drm/i915/gt/intel_ring_submission.c > @@ -185,7 +185,7 @@ static int xcs_resume(struct intel_engine_cs *engine) >ring->head, ring->tail); > > /* Double check the ring is empty & disabled before we resume */ > - synchronize_hardirq(engine->i915->drm.irq); > + intel_synchronize_hardirq(engine->i915); > if (!stop_ring(engine)) > goto err; > > diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c > index 7d0ce8b9f8ed..2203dca19895 100644 > --- a/drivers/gpu/drm/i915/i915_irq.c > +++ b/drivers/gpu/drm/i915/i915_irq.c > @@ -4575,3 +4575,8 @@ void intel_synchronize_irq(struct drm_i915_private > *i915) > { > synchronize_irq(to_pci_dev(i915->drm.dev)->irq); > } > + > +void intel_synchronize_hardirq(struct drm_i915_private *i915) > +{ > + synchronize_hardirq(to_pci_dev(i915->drm.dev)->irq); I honestly think the hardirq here is about as much cargo-culted as using the wrong irq number. I'd just use intel_synchronize_irq in both places and see whether CI complains, then go with that. -Daniel > +} > diff --git a/drivers/gpu/drm/i915/i915_irq.h b/drivers/gpu/drm/i915/i915_irq.h > index db34d5dbe402..e43b6734f21b 100644 > --- a/drivers/gpu/drm/i915/i915_irq.h > +++ b/drivers/gpu/drm/i915/i915_irq.h > @@ -94,6 +94,7 @@ void intel_runtime_pm_disable_interrupts(struct > drm_i915_private *dev_priv); > void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv); > bool intel_irqs_enabled(struct drm_i915_private *dev_priv); > void intel_synchronize_irq(struct drm_i915_private *i915); > +void intel_synchronize_hardirq(struct drm_i915_private *i915); > > int intel_get_crtc_scanline(struct intel_crtc *crtc); > void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, > -- > 2.32.0 > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
Re: [PATCH V2] treewide: Add missing semicolons to __assign_str uses
On Sat, 2021-06-12 at 08:42 -0700, Joe Perches wrote: > The __assign_str macro has an unusual ending semicolon but the vast > majority of uses of the macro already have semicolon termination. ping?
RE: [PATCH 04/21] drm/i915/xelpd: Define Degamma Lut range struct for HDR planes
> -Original Message- > From: dri-devel On Behalf Of Harry > Wentland > Sent: Monday, June 28, 2021 8:45 PM > To: Shankar, Uma ; intel-...@lists.freedesktop.org; > dri- > de...@lists.freedesktop.org > Cc: Modem, Bhanuprakash > Subject: Re: [PATCH 04/21] drm/i915/xelpd: Define Degamma Lut range struct for > HDR planes > > On 2021-06-01 6:52 a.m., Uma Shankar wrote: > > Define the structure with XE_LPD degamma lut ranges. HDR and SDR > > planes have different capabilities, implemented respective structure > > for the HDR planes. > > > > Signed-off-by: Uma Shankar > > --- > > drivers/gpu/drm/i915/display/intel_color.c | 52 > > ++ > > 1 file changed, 52 insertions(+) > > > > diff --git a/drivers/gpu/drm/i915/display/intel_color.c > > b/drivers/gpu/drm/i915/display/intel_color.c > > index dab892d2251b..c735d06a6b54 100644 > > --- a/drivers/gpu/drm/i915/display/intel_color.c > > +++ b/drivers/gpu/drm/i915/display/intel_color.c > > @@ -2093,6 +2093,58 @@ static void icl_read_luts(struct intel_crtc_state > *crtc_state) > > } > > } > > > > + /* FIXME input bpc? */ > > +__maybe_unused > > +static const struct drm_color_lut_range d13_degamma_hdr[] = { > > + /* segment 1 */ > > + { > > + .flags = (DRM_MODE_LUT_GAMMA | > > Why are these using DRM_MODE_LUT_GAMMA and not > DRM_MODE_LUT_DEGAMMA when the lut_type for this LUT is > LUT_TYPE_DEGAMMA? Thanks Harry for the comments. Yeah this is an oversight, will fix this. > > > > + DRM_MODE_LUT_REFLECT_NEGATIVE | > > + DRM_MODE_LUT_INTERPOLATE | > > + DRM_MODE_LUT_NON_DECREASING), > > + .count = 128, > > + .input_bpc = 24, .output_bpc = 16, > > Why do we need more than 16 bpc for LUT? FP16 is enough to represent HDR in > linear space. Wouldn't 16 bpc be enough? Pipe sometimes works internally on higher precision (just to take care of rounding etc.), later the extra data gets dropped at the end of the pipe. So from source side you are right, 16bpc is enough but the lut precision can go higher. > > > + .start = 0, .end = (1 << 24) - 1, > > + .min = 0, .max = (1 << 24) - 1, > > + }, > > + /* segment 2 */ > > + { > > + .flags = (DRM_MODE_LUT_GAMMA | > > + DRM_MODE_LUT_REFLECT_NEGATIVE | > > + DRM_MODE_LUT_INTERPOLATE | > > + DRM_MODE_LUT_REUSE_LAST | > > + DRM_MODE_LUT_NON_DECREASING), > > + .count = 1, > > + .input_bpc = 24, .output_bpc = 16, > > + .start = (1 << 24) - 1, .end = 1 << 24, > > + .min = 0, .max = (1 << 27) - 1, > > How can max be 1 << 27 if input_bpc is 24? This is to take care of > 1.0 section. 1.0 to 3.0 and 3.0 to 7.0. So we have 3.24 format for Lut to take care of this. Also, I have an action to update the series with UAPI doc and new naming for the property. My apologies for being late on that one. Will update and send that out soon. Thanks & Regards, Uma Shankar > > Harry > > > + }, > > + /* Segment 3 */ > > + { > > + .flags = (DRM_MODE_LUT_GAMMA | > > + DRM_MODE_LUT_REFLECT_NEGATIVE | > > + DRM_MODE_LUT_INTERPOLATE | > > + DRM_MODE_LUT_REUSE_LAST | > > + DRM_MODE_LUT_NON_DECREASING), > > + .count = 1, > > + .input_bpc = 24, .output_bpc = 16, > > + .start = 1 << 24, .end = 3 << 24, > > + .min = 0, .max = (1 << 27) - 1, > > + }, > > + /* Segment 4 */ > > + { > > + .flags = (DRM_MODE_LUT_GAMMA | > > + DRM_MODE_LUT_REFLECT_NEGATIVE | > > + DRM_MODE_LUT_INTERPOLATE | > > + DRM_MODE_LUT_REUSE_LAST | > > + DRM_MODE_LUT_NON_DECREASING), > > + .count = 1, > > + .input_bpc = 24, .output_bpc = 16, > > + .start = 3 << 24, .end = 7 << 24, > > + .min = 0, .max = (1 << 27) - 1, > > + }, > > +}; > > + > > void intel_color_init(struct intel_crtc *crtc) > > { > > struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); > >
Re: [PATCH v15 06/12] swiotlb: Use is_swiotlb_force_bounce for swiotlb data bouncing
On Wed, Jun 30, 2021 at 05:17:27PM +0800, Claire Chang wrote: > On Wed, Jun 30, 2021 at 9:43 AM Nathan Chancellor wrote: > > > > On Thu, Jun 24, 2021 at 11:55:20PM +0800, Claire Chang wrote: > > > Propagate the swiotlb_force into io_tlb_default_mem->force_bounce and > > > use it to determine whether to bounce the data or not. This will be > > > useful later to allow for different pools. > > > > > > Signed-off-by: Claire Chang > > > Reviewed-by: Christoph Hellwig > > > Tested-by: Stefano Stabellini > > > Tested-by: Will Deacon > > > Acked-by: Stefano Stabellini > > > > This patch as commit af452ec1b1a3 ("swiotlb: Use is_swiotlb_force_bounce > > for swiotlb data bouncing") causes my Ryzen 3 4300G system to fail to > > get to an X session consistently (although not every single time), > > presumably due to a crash in the AMDGPU driver that I see in dmesg. > > > > I have attached logs at af452ec1b1a3 and f127c9556a8e and I am happy > > to provide any further information, debug, or test patches as necessary. > > Are you using swiotlb=force? or the swiotlb_map is called because of > !dma_capable? > (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/kernel/dma/direct.h#n93) The command line is in the dmesg: | Kernel command line: initrd=\amd-ucode.img initrd=\initramfs-linux-next-llvm.img root=PARTUUID=8680aa0c-cf09-4a69-8cf3-970478040ee7 rw intel_pstate=no_hwp irqpoll but I worry that this looks _very_ similar to the issue reported by Qian Cai which we thought we had fixed. Nathan -- is the failure deterministic? > `BUG: unable to handle page fault for address: 003a8290` and > the fact it crashed at `_raw_spin_lock_irqsave` look like the memory > (maybe dev->dma_io_tlb_mem) was corrupted? > The dev->dma_io_tlb_mem should be set here > (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/drivers/pci/probe.c#n2528) > through device_initialize. I'm less sure about this. 'dma_io_tlb_mem' should be pointing at 'io_tlb_default_mem', which is a page-aligned allocation from memblock. The spinlock is at offset 0x24 in that structure, and looking at the register dump from the crash: Jun 29 18:28:42 hp-4300G kernel: RSP: 0018:adb4013db9e8 EFLAGS: 00010006 Jun 29 18:28:42 hp-4300G kernel: RAX: 003a8290 RBX: RCX: 8900572ad580 Jun 29 18:28:42 hp-4300G kernel: RDX: 89005653f024 RSI: 000c RDI: 1d17 Jun 29 18:28:42 hp-4300G kernel: RBP: 0a20d000 R08: 000c R09: Jun 29 18:28:42 hp-4300G kernel: R10: 0a20d000 R11: 89005653f000 R12: 0212 Jun 29 18:28:42 hp-4300G kernel: R13: 1000 R14: 0002 R15: 0020 Jun 29 18:28:42 hp-4300G kernel: FS: 7f1f8898ea40() GS:89005728() knlGS: Jun 29 18:28:42 hp-4300G kernel: CS: 0010 DS: ES: CR0: 80050033 Jun 29 18:28:42 hp-4300G kernel: CR2: 003a8290 CR3: 0001020d CR4: 00350ee0 Jun 29 18:28:42 hp-4300G kernel: Call Trace: Jun 29 18:28:42 hp-4300G kernel: _raw_spin_lock_irqsave+0x39/0x50 Jun 29 18:28:42 hp-4300G kernel: swiotlb_tbl_map_single+0x12b/0x4c0 Then that correlates with R11 holding the 'dma_io_tlb_mem' pointer and RDX pointing at the spinlock. Yet RAX is holding junk :/ I agree that enabling KASAN would be a good idea, but I also think we probably need to get some more information out of swiotlb_tbl_map_single() to see see what exactly is going wrong in there. Will
Re: [PATCH v3 2/2] drm/i915: Drop all references to DRM IRQ midlayer
Hi Am 30.06.21 um 12:06 schrieb Greg KH: On Wed, Jun 30, 2021 at 11:52:28AM +0200, Thomas Zimmermann wrote: Remove all references to DRM's IRQ midlayer. i915 uses Linux' interrupt functions directly. v2: * also remove an outdated comment * move IRQ fix into separate patch * update Fixes tag (Daniel) Signed-off-by: Thomas Zimmermann Fixes: b318b82455bd ("drm/i915: Nuke drm_driver irq vfuncs") Cc: Ville Syrjälä Cc: Chris Wilson Cc: Jani Nikula Cc: Joonas Lahtinen Cc: Rodrigo Vivi Cc: intel-...@lists.freedesktop.org Cc: # v5.4+ --- drivers/gpu/drm/i915/i915_drv.c | 1 - drivers/gpu/drm/i915/i915_irq.c | 5 - 2 files changed, 6 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 850b499c71c8..73de45472f60 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -42,7 +42,6 @@ #include #include #include -#include #include #include diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 2203dca19895..1d4c683c9de9 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -33,7 +33,6 @@ #include #include -#include #include "display/intel_de.h" #include "display/intel_display_types.h" @@ -4564,10 +4563,6 @@ void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv) bool intel_irqs_enabled(struct drm_i915_private *dev_priv) { - /* -* We only use drm_irq_uninstall() at unload and VT switch, so -* this is the only thing we need to check. -*/ return dev_priv->runtime_pm.irqs_enabled; } -- 2.32.0 How is this a stable-kernel-related fix? Sorry, it isn't. I forgot to remove the rsp Cc tag. Best regards Thomas thanks, greg k-h -- Thomas Zimmermann Graphics Driver Developer SUSE Software Solutions Germany GmbH Maxfeldstr. 5, 90409 Nürnberg, Germany (HRB 36809, AG Nürnberg) Geschäftsführer: Felix Imendörffer OpenPGP_signature Description: OpenPGP digital signature
[PATCH] drm/vgem: Use 256B aligned pitch
Having different alignment requirement by different drivers, 256B aligned should work for all drm drivers. Signed-off-by: Tejas Upadhyay --- drivers/gpu/drm/vgem/vgem_drv.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/vgem/vgem_drv.c b/drivers/gpu/drm/vgem/vgem_drv.c index bf38a7e319d1..1da6df5e256a 100644 --- a/drivers/gpu/drm/vgem/vgem_drv.c +++ b/drivers/gpu/drm/vgem/vgem_drv.c @@ -215,7 +215,7 @@ static int vgem_gem_dumb_create(struct drm_file *file, struct drm_device *dev, struct drm_gem_object *gem_object; u64 pitch, size; - pitch = args->width * DIV_ROUND_UP(args->bpp, 8); + pitch = ALIGN(args->width * DIV_ROUND_UP(args->bpp, 8), 256); size = args->height * pitch; if (size == 0) return -EINVAL; -- 2.31.1
Re: [Intel-gfx] [PATCH] drm/vgem: Use 256B aligned pitch
On Wed, Jun 30, 2021 at 05:32:15PM +0530, Tejas Upadhyay wrote: > Having different alignment requirement by different drivers, > 256B aligned should work for all drm drivers. What. Like yes vgem abuses dumb_create, but it's not a kms driver. Pitch is meaningless, and that's why we align it minimally to 1 byte (bpp = bits per pixel here). Maybe start with explaining what you're trying to do here. -Daniel > > Signed-off-by: Tejas Upadhyay > --- > drivers/gpu/drm/vgem/vgem_drv.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/vgem/vgem_drv.c b/drivers/gpu/drm/vgem/vgem_drv.c > index bf38a7e319d1..1da6df5e256a 100644 > --- a/drivers/gpu/drm/vgem/vgem_drv.c > +++ b/drivers/gpu/drm/vgem/vgem_drv.c > @@ -215,7 +215,7 @@ static int vgem_gem_dumb_create(struct drm_file *file, > struct drm_device *dev, > struct drm_gem_object *gem_object; > u64 pitch, size; > > - pitch = args->width * DIV_ROUND_UP(args->bpp, 8); > + pitch = ALIGN(args->width * DIV_ROUND_UP(args->bpp, 8), 256); > size = args->height * pitch; > if (size == 0) > return -EINVAL; > -- > 2.31.1 > > ___ > Intel-gfx mailing list > intel-...@lists.freedesktop.org > https://lists.freedesktop.org/mailman/listinfo/intel-gfx -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
Re: [PATCH V2] treewide: Add missing semicolons to __assign_str uses
On Wed, 30 Jun 2021 04:28:39 -0700 Joe Perches wrote: > On Sat, 2021-06-12 at 08:42 -0700, Joe Perches wrote: > > The __assign_str macro has an unusual ending semicolon but the vast > > majority of uses of the macro already have semicolon termination. > > ping? > I wasn't sure I was the one to take this. I can, as I can run tests on it as well. I have some last minute fixes sent to me on something else, and I can apply this along with them. -- Steve
Re: [RFC PATCH 0/9] arm64: imx8mm: Add MIPI DSI support
Hi Peng, On Tue, Jun 29, 2021 at 12:40 PM Peng Fan (OSS) wrote: > > Hi Jagan, > > > Subject: [RFC PATCH 0/9] arm64: imx8mm: Add MIPI DSI support > > > > This series support MIPI DSI on i.MX8MM. > > > > It worked directly with existing mxsfb driver but the SEC DSIM timings has > > to > > be validate and tested through all platforms, ie reason I'm sending it as > > RFC. > > > > Tested on Engicam i.Core MX8M Mini SoM. > > Thanks for the work. > > > > > patch 1: dt-bindings for SEC MIPI DSIM > > > > patch 2: SEC MIPI DSIM bridge driver > > > > patch 3: dt-bindings for SEC DSIM DPHY > > > > patch 4: SEC DSIM DPHY driver > > > > patch 5: MIPI DPHY reset enable in blk-ctl > > > > patch 6: display mix blk ctl node > > > > patch 7: eLCDIF node > > > > patch 8: MIPI DSI pipeline nodes > > > > patch 9: Enable LVDS panel on EDIMM2.2 > > > > Note: > > - all these patches on top of Peng Fan's blk-ctl driver. > > Would you please update to use V8 patchset? > > And the dtb: > https://patchwork.kernel.org/project/linux-arm-kernel/ > patch/20210604111005.6804-1-peng@oss.nxp.com/ Thanks for the details. I will rebase to use this series and test. Will update on blk-ctl patches. Thanks, Jagan.
[PATCH] dma-buf: fix and rework dma_buf_poll v4
Daniel pointed me towards this function and there are multiple obvious problems in the implementation. First of all the retry loop is not working as intended. In general the retry makes only sense if you grab the reference first and then check the sequence values. Then we should always also wait for the exclusive fence. It's also good practice to keep the reference around when installing callbacks to fences you don't own. And last the whole implementation was unnecessary complex and rather hard to understand which could lead to probably unexpected behavior of the IOCTL. Fix all this by reworking the implementation from scratch. Dropping the whole RCU approach and taking the lock instead. Only mildly tested and needs a thoughtful review of the code. v2: fix the reference counting as well v3: keep the excl fence handling as is for stable v4: back to testing all fences, drop RCU Signed-off-by: Christian König CC: sta...@vger.kernel.org --- drivers/dma-buf/dma-buf.c | 132 +- include/linux/dma-buf.h | 2 +- 2 files changed, 46 insertions(+), 88 deletions(-) diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c index eadd1eaa2fb5..192c4d34704b 100644 --- a/drivers/dma-buf/dma-buf.c +++ b/drivers/dma-buf/dma-buf.c @@ -72,7 +72,7 @@ static void dma_buf_release(struct dentry *dentry) * If you hit this BUG() it means someone dropped their ref to the * dma-buf while still having pending operation to the buffer. */ - BUG_ON(dmabuf->cb_shared.active || dmabuf->cb_excl.active); + BUG_ON(dmabuf->cb_in.active || dmabuf->cb_out.active); dmabuf->ops->release(dmabuf); @@ -202,16 +202,19 @@ static void dma_buf_poll_cb(struct dma_fence *fence, struct dma_fence_cb *cb) wake_up_locked_poll(dcb->poll, dcb->active); dcb->active = 0; spin_unlock_irqrestore(&dcb->poll->lock, flags); + dma_fence_put(fence); } static __poll_t dma_buf_poll(struct file *file, poll_table *poll) { + struct dma_buf_poll_cb_t *dcb; struct dma_buf *dmabuf; struct dma_resv *resv; struct dma_resv_list *fobj; - struct dma_fence *fence_excl; + struct dma_fence *fence; + unsigned shared_count; __poll_t events; - unsigned shared_count, seq; + int r, i; dmabuf = file->private_data; if (!dmabuf || !dmabuf->resv) @@ -225,101 +228,56 @@ static __poll_t dma_buf_poll(struct file *file, poll_table *poll) if (!events) return 0; -retry: - seq = read_seqcount_begin(&resv->seq); - rcu_read_lock(); + dcb = events & EPOLLOUT ? &dmabuf->cb_out : &dmabuf->cb_in; + + /* Only queue a new one if we are not still waiting for the old one */ + spin_lock_irq(&dmabuf->poll.lock); + if (dcb->active) + events = 0; + else + dcb->active = events; + spin_unlock_irq(&dmabuf->poll.lock); + if (!events) + return 0; + + dma_resv_lock(resv, NULL); - fobj = rcu_dereference(resv->fence); - if (fobj) + fobj = dma_resv_get_list(resv); + if (fobj && events & EPOLLOUT) shared_count = fobj->shared_count; else shared_count = 0; - fence_excl = rcu_dereference(resv->fence_excl); - if (read_seqcount_retry(&resv->seq, seq)) { - rcu_read_unlock(); - goto retry; - } - if (fence_excl && (!(events & EPOLLOUT) || shared_count == 0)) { - struct dma_buf_poll_cb_t *dcb = &dmabuf->cb_excl; - __poll_t pevents = EPOLLIN; - - if (shared_count == 0) - pevents |= EPOLLOUT; - - spin_lock_irq(&dmabuf->poll.lock); - if (dcb->active) { - dcb->active |= pevents; - events &= ~pevents; - } else - dcb->active = pevents; - spin_unlock_irq(&dmabuf->poll.lock); - - if (events & pevents) { - if (!dma_fence_get_rcu(fence_excl)) { - /* force a recheck */ - events &= ~pevents; - dma_buf_poll_cb(NULL, &dcb->cb); - } else if (!dma_fence_add_callback(fence_excl, &dcb->cb, - dma_buf_poll_cb)) { - events &= ~pevents; - dma_fence_put(fence_excl); - } else { - /* -* No callback queued, wake up any additional -* waiters. -*/ - dma_fence_put(fence_excl); - dma_buf_poll_cb(NULL, &dcb->cb); - } +
RE: [Intel-gfx] [PATCH] drm/vgem: Use 256B aligned pitch
> -Original Message- > From: Daniel Vetter > Sent: 30 June 2021 17:52 > To: Surendrakumar Upadhyay, TejaskumarX > > Cc: dri-devel@lists.freedesktop.org; intel-...@lists.freedesktop.org; > ch...@chris-wilson.co.uk > Subject: Re: [Intel-gfx] [PATCH] drm/vgem: Use 256B aligned pitch > > On Wed, Jun 30, 2021 at 05:32:15PM +0530, Tejas Upadhyay wrote: > > Having different alignment requirement by different drivers, 256B > > aligned should work for all drm drivers. > > What. > > Like yes vgem abuses dumb_create, but it's not a kms driver. Pitch is > meaningless, and that's why we align it minimally to 1 byte (bpp = bits per > pixel here). > > Maybe start with explaining what you're trying to do here. > -Daniel > > Igt tool tests which are trying to exercise tests through VGEM are getting failure (if not 64B aligned) on Intel platforms in creating framebuffer as they need them to be 64B aligned. Then 64B alignment is not A requirement for all drm drivers. Thanks, Tejas > > Signed-off-by: Tejas Upadhyay > > > > --- > > drivers/gpu/drm/vgem/vgem_drv.c | 2 +- > > 1 file changed, 1 insertion(+), 1 deletion(-) > > > > diff --git a/drivers/gpu/drm/vgem/vgem_drv.c > > b/drivers/gpu/drm/vgem/vgem_drv.c index bf38a7e319d1..1da6df5e256a > > 100644 > > --- a/drivers/gpu/drm/vgem/vgem_drv.c > > +++ b/drivers/gpu/drm/vgem/vgem_drv.c > > @@ -215,7 +215,7 @@ static int vgem_gem_dumb_create(struct drm_file > *file, struct drm_device *dev, > > struct drm_gem_object *gem_object; > > u64 pitch, size; > > > > - pitch = args->width * DIV_ROUND_UP(args->bpp, 8); > > + pitch = ALIGN(args->width * DIV_ROUND_UP(args->bpp, 8), 256); > > size = args->height * pitch; > > if (size == 0) > > return -EINVAL; > > -- > > 2.31.1 > > > > ___ > > Intel-gfx mailing list > > intel-...@lists.freedesktop.org > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx > > -- > Daniel Vetter > Software Engineer, Intel Corporation > http://blog.ffwll.ch
[PATCH 0/2] drm/i915/gem: dma-buf fixes for migration
Our dma-buf code is currently completely broken unless the importer is dynamic in which case the sg_list caching saves the day. In particular, the case where another instance of our driver tries to import a dma-buf exported by our driver ends up in a recursive lock. Since the recent TTM migration work spec specifies to fix up the dma-buf code with migration and there's no point in doing so when it's completely broken, take a first step to make at least the exporter obey the dma-buf locking rules the dma-buf core enforces for a dynamic exporter: - Implement and act on pin- and unpin. - Call move_notify if migrating. (we opt not to migrate while dma-buf_mapped). - map_dma_buf() is unconditionally called locked. Add a selftest that ensures that it works with both our own and a fake dynamic importer. Also implement migration in the second patch before pinning in pin() and map_dma_buf(). Note that the importer remains broken for other non-dynamic exporters, but at least not for the same-driver-separate-instances case. Regardless whether we want to fix this now with this series, or in an unspecified future, the selftest may come in handy. Thomas Hellström (2): drm/i915/gem: Make our dma-buf exporter dynamic drm/i915/gem: Migrate to system at dma-buf map time drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 48 ++- .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 118 +- 2 files changed, 162 insertions(+), 4 deletions(-) -- 2.31.1
[PATCH 2/2] drm/i915/gem: Migrate to system at dma-buf map time
Until we support p2p dma or as a complement to that, migrate data to system memory at dma-buf map time if possible. v2: - Rebase on dynamic exporter. Update the igt_dmabuf_import_same_driver selftest to migrate if we are LMEM capable. v3: - Migrate also in the pin() callback. Signed-off-by: Thomas Hellström Reviewed-by: Michael J. Ruhl --- drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 21 +-- .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 4 +++- 2 files changed, 22 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c index 918c19df7b66..13312d89c2ed 100644 --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c @@ -34,7 +34,14 @@ static struct sg_table *i915_gem_map_dma_buf(struct dma_buf_attachment *attachme * Let's pin it here to avoid having to call the move_notify * callback, The call of which is not yet implemented. */ - ret = i915_gem_object_pin_pages(obj); + if (!i915_gem_object_can_migrate(obj, INTEL_REGION_SMEM)) + return ERR_PTR(-EOPNOTSUPP); + + ret = i915_gem_object_migrate(obj, NULL, INTEL_REGION_SMEM); + if (!ret) + ret = i915_gem_object_wait_migration(obj, 0); + if (!ret) + ret = i915_gem_object_pin_pages(obj); if (ret) goto err; @@ -180,9 +187,19 @@ static int i915_gem_end_cpu_access(struct dma_buf *dma_buf, enum dma_data_direct static int i915_gem_dmabuf_pin(struct dma_buf_attachment *attach) { struct drm_i915_gem_object *obj = dma_buf_to_obj(attach->dmabuf); + int ret; assert_object_held(obj); - return i915_gem_object_pin_pages(obj); + + if (!i915_gem_object_can_migrate(obj, INTEL_REGION_SMEM)) + return -EOPNOTSUPP; + ret = i915_gem_object_migrate(obj, NULL, INTEL_REGION_SMEM); + if (!ret) + ret = i915_gem_object_wait_migration(obj, 0); + if (!ret) + ret = i915_gem_object_pin_pages(obj); + + return ret; } static void i915_gem_dmabuf_unpin(struct dma_buf_attachment *attach) diff --git a/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c b/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c index 868b3469ecbd..b1e87ec08741 100644 --- a/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c +++ b/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c @@ -106,7 +106,9 @@ static int igt_dmabuf_import_same_driver(void *arg) int err; force_different_devices = true; - obj = i915_gem_object_create_shmem(i915, PAGE_SIZE); + obj = i915_gem_object_create_lmem(i915, PAGE_SIZE, 0); + if (IS_ERR(obj)) + obj = i915_gem_object_create_shmem(i915, PAGE_SIZE); if (IS_ERR(obj)) goto out_ret; -- 2.31.1
[PATCH 1/2] drm/i915/gem: Make our dma-buf exporter dynamic
If our exported dma-bufs are imported by another instance of our driver, that instance will typically have the imported dma-bufs locked during dma_buf_map_attachment(). But the exporter also locks the same reservation object in the map_dma_buf() callback, which leads to recursive locking. Add a live selftest to exercise both dynamic and non-dynamic exports, and as a workaround until we fully support dynamic import and export, declare the exporter dynamic by providing pin() and unpin() implementations. For dynamic importers, make sure we keep the pinning also in map_dma_buf(), to ensure we never need to call dma_buf_move_notify(). Calling dma_buf_move_notify() is at the discretion of the exporter. v2: - Extend the selftest with a fake dynamic importer. - Provide real pin and unpin callbacks to not abuse the interface. Reported-by: Michael J. Ruhl Signed-off-by: Thomas Hellström --- drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 31 - .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 116 +- 2 files changed, 143 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c index 616c3a2f1baf..918c19df7b66 100644 --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c @@ -12,6 +12,8 @@ #include "i915_gem_object.h" #include "i915_scatterlist.h" +I915_SELFTEST_DECLARE(static bool force_different_devices;) + static struct drm_i915_gem_object *dma_buf_to_obj(struct dma_buf *buf) { return to_intel_bo(buf->priv); @@ -25,7 +27,14 @@ static struct sg_table *i915_gem_map_dma_buf(struct dma_buf_attachment *attachme struct scatterlist *src, *dst; int ret, i; - ret = i915_gem_object_pin_pages_unlocked(obj); + assert_object_held(obj); + + /* +* Note. In the dynamic importer case, the object is not yet pinned. +* Let's pin it here to avoid having to call the move_notify +* callback, The call of which is not yet implemented. +*/ + ret = i915_gem_object_pin_pages(obj); if (ret) goto err; @@ -168,6 +177,21 @@ static int i915_gem_end_cpu_access(struct dma_buf *dma_buf, enum dma_data_direct return err; } +static int i915_gem_dmabuf_pin(struct dma_buf_attachment *attach) +{ + struct drm_i915_gem_object *obj = dma_buf_to_obj(attach->dmabuf); + + assert_object_held(obj); + return i915_gem_object_pin_pages(obj); +} + +static void i915_gem_dmabuf_unpin(struct dma_buf_attachment *attach) +{ + struct drm_i915_gem_object *obj = dma_buf_to_obj(attach->dmabuf); + + i915_gem_object_unpin_pages(obj); +} + static const struct dma_buf_ops i915_dmabuf_ops = { .map_dma_buf = i915_gem_map_dma_buf, .unmap_dma_buf = i915_gem_unmap_dma_buf, @@ -177,6 +201,8 @@ static const struct dma_buf_ops i915_dmabuf_ops = { .vunmap = i915_gem_dmabuf_vunmap, .begin_cpu_access = i915_gem_begin_cpu_access, .end_cpu_access = i915_gem_end_cpu_access, + .pin = i915_gem_dmabuf_pin, + .unpin = i915_gem_dmabuf_unpin, }; struct dma_buf *i915_gem_prime_export(struct drm_gem_object *gem_obj, int flags) @@ -241,7 +267,8 @@ struct drm_gem_object *i915_gem_prime_import(struct drm_device *dev, if (dma_buf->ops == &i915_dmabuf_ops) { obj = dma_buf_to_obj(dma_buf); /* is it from our device? */ - if (obj->base.dev == dev) { + if (obj->base.dev == dev && + !I915_SELFTEST_ONLY(force_different_devices)) { /* * Importing dmabuf exported from out own gem increases * refcount on gem itself instead of f_count of dmabuf. diff --git a/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c b/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c index dd74bc09ec88..868b3469ecbd 100644 --- a/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c +++ b/drivers/gpu/drm/i915/gem/selftests/i915_gem_dmabuf.c @@ -35,7 +35,7 @@ static int igt_dmabuf_export(void *arg) static int igt_dmabuf_import_self(void *arg) { struct drm_i915_private *i915 = arg; - struct drm_i915_gem_object *obj; + struct drm_i915_gem_object *obj, *import_obj; struct drm_gem_object *import; struct dma_buf *dmabuf; int err; @@ -65,14 +65,125 @@ static int igt_dmabuf_import_self(void *arg) err = -EINVAL; goto out_import; } + import_obj = to_intel_bo(import); + + i915_gem_object_lock(import_obj, NULL); + err = i915_gem_object_get_pages(import_obj); + i915_gem_object_unlock(import_obj); + if (err) { + pr_err("Same object dma-buf get_pages failed!\n"); + goto out_import; + } err = 0; out_import: - i915_gem_object_put(to_intel_bo(import)); + i915_gem_objec
Re: [PATCH v6 05/16] drm/panfrost: Drop the pfdev argument passed to panfrost_exception_name()
Reviewed-by: Alyssa Rosenzweig On Wed, Jun 30, 2021 at 08:27:40AM +0200, Boris Brezillon wrote: > Currently unused. We'll add it back if we need per-GPU definitions. > > Signed-off-by: Boris Brezillon > Reviewed-by: Steven Price > --- > drivers/gpu/drm/panfrost/panfrost_device.c | 2 +- > drivers/gpu/drm/panfrost/panfrost_device.h | 2 +- > drivers/gpu/drm/panfrost/panfrost_gpu.c| 2 +- > drivers/gpu/drm/panfrost/panfrost_job.c| 2 +- > drivers/gpu/drm/panfrost/panfrost_mmu.c| 2 +- > 5 files changed, 5 insertions(+), 5 deletions(-) > > diff --git a/drivers/gpu/drm/panfrost/panfrost_device.c > b/drivers/gpu/drm/panfrost/panfrost_device.c > index a2a09c51eed7..f7f5ca94f910 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_device.c > +++ b/drivers/gpu/drm/panfrost/panfrost_device.c > @@ -292,7 +292,7 @@ void panfrost_device_fini(struct panfrost_device *pfdev) > panfrost_clk_fini(pfdev); > } > > -const char *panfrost_exception_name(struct panfrost_device *pfdev, u32 > exception_code) > +const char *panfrost_exception_name(u32 exception_code) > { > switch (exception_code) { > /* Non-Fault Status code */ > diff --git a/drivers/gpu/drm/panfrost/panfrost_device.h > b/drivers/gpu/drm/panfrost/panfrost_device.h > index 8b2cdb8c701d..2fe1550da7f8 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_device.h > +++ b/drivers/gpu/drm/panfrost/panfrost_device.h > @@ -173,6 +173,6 @@ void panfrost_device_reset(struct panfrost_device *pfdev); > int panfrost_device_resume(struct device *dev); > int panfrost_device_suspend(struct device *dev); > > -const char *panfrost_exception_name(struct panfrost_device *pfdev, u32 > exception_code); > +const char *panfrost_exception_name(u32 exception_code); > > #endif > diff --git a/drivers/gpu/drm/panfrost/panfrost_gpu.c > b/drivers/gpu/drm/panfrost/panfrost_gpu.c > index 0e70e27fd8c3..26e4196b6c90 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_gpu.c > +++ b/drivers/gpu/drm/panfrost/panfrost_gpu.c > @@ -33,7 +33,7 @@ static irqreturn_t panfrost_gpu_irq_handler(int irq, void > *data) > address |= gpu_read(pfdev, GPU_FAULT_ADDRESS_LO); > > dev_warn(pfdev->dev, "GPU Fault 0x%08x (%s) at 0x%016llx\n", > - fault_status & 0xFF, panfrost_exception_name(pfdev, > fault_status), > + fault_status & 0xFF, > panfrost_exception_name(fault_status), >address); > > if (state & GPU_IRQ_MULTIPLE_FAULT) > diff --git a/drivers/gpu/drm/panfrost/panfrost_job.c > b/drivers/gpu/drm/panfrost/panfrost_job.c > index 3c1dbae3ebdd..ea3432ffde40 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_job.c > +++ b/drivers/gpu/drm/panfrost/panfrost_job.c > @@ -489,7 +489,7 @@ static irqreturn_t panfrost_job_irq_handler(int irq, void > *data) > > dev_err(pfdev->dev, "js fault, js=%d, status=%s, > head=0x%x, tail=0x%x", > j, > - panfrost_exception_name(pfdev, job_read(pfdev, > JS_STATUS(j))), > + panfrost_exception_name(job_read(pfdev, > JS_STATUS(j))), > job_read(pfdev, JS_HEAD_LO(j)), > job_read(pfdev, JS_TAIL_LO(j))); > > diff --git a/drivers/gpu/drm/panfrost/panfrost_mmu.c > b/drivers/gpu/drm/panfrost/panfrost_mmu.c > index 569509c2ba27..2a9bf30edc9d 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_mmu.c > +++ b/drivers/gpu/drm/panfrost/panfrost_mmu.c > @@ -675,7 +675,7 @@ static irqreturn_t panfrost_mmu_irq_handler_thread(int > irq, void *data) > "TODO", > fault_status, > (fault_status & (1 << 10) ? "DECODER FAULT" : > "SLAVE FAULT"), > - exception_type, panfrost_exception_name(pfdev, > exception_type), > + exception_type, > panfrost_exception_name(exception_type), > access_type, access_type_name(pfdev, > fault_status), > source_id); > > -- > 2.31.1 >
Re: [PATCH 1/2] drm/i915/gem: Make our dma-buf exporter dynamic
On Wed, Jun 30, 2021 at 03:07:00PM +0200, Thomas Hellström wrote: > If our exported dma-bufs are imported by another instance of our driver, > that instance will typically have the imported dma-bufs locked during > dma_buf_map_attachment(). But the exporter also locks the same reservation > object in the map_dma_buf() callback, which leads to recursive locking. > > Add a live selftest to exercise both dynamic and non-dynamic exports, > and as a workaround until we fully support dynamic import and export, > declare the exporter dynamic by providing pin() and unpin() implementations. > For dynamic importers, make sure we keep the pinning also in map_dma_buf(), > to ensure we never need to call dma_buf_move_notify(). > Calling dma_buf_move_notify() is at the discretion of the exporter. > > v2: > - Extend the selftest with a fake dynamic importer. > - Provide real pin and unpin callbacks to not abuse the interface. > > Reported-by: Michael J. Ruhl > Signed-off-by: Thomas Hellström I'm not happy with this, because i915 is currently violating the dma-resv fencing rules for dynamic dma-buf. Yes since this is just the exporter we can probably get away with yolo'ing things, but Christian and me just spend a lot of angry typing figuring out what the rules actually are, so I really don't like bending them even more just because it's less typing. All we need for a quick interim fix is to not take the dma_resv_lock from our map/unamp callbacks. Pinning our backing storage from attach/detach callbacks (which are also called under dma_resv_lock) would also achieve that, without mudding any waters. So essentially just moving the pin/unpin_pages_unlocked and we should be good, which is almost as little typing. Michael, since Thomas is on vacations now, care to type that up? The selftest is imo solid. This is also consistent with what all other ttm based drivers do (aside from amdgpu, which is fully dynamic), see drm_gem_map_attach in drm_prime.c Adding Christian as fyi. -Daniel > --- > drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 31 - > .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 116 +- > 2 files changed, 143 insertions(+), 4 deletions(-) > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > index 616c3a2f1baf..918c19df7b66 100644 > --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > @@ -12,6 +12,8 @@ > #include "i915_gem_object.h" > #include "i915_scatterlist.h" > > +I915_SELFTEST_DECLARE(static bool force_different_devices;) > + > static struct drm_i915_gem_object *dma_buf_to_obj(struct dma_buf *buf) > { > return to_intel_bo(buf->priv); > @@ -25,7 +27,14 @@ static struct sg_table *i915_gem_map_dma_buf(struct > dma_buf_attachment *attachme > struct scatterlist *src, *dst; > int ret, i; > > - ret = i915_gem_object_pin_pages_unlocked(obj); > + assert_object_held(obj); > + > + /* > + * Note. In the dynamic importer case, the object is not yet pinned. > + * Let's pin it here to avoid having to call the move_notify > + * callback, The call of which is not yet implemented. > + */ > + ret = i915_gem_object_pin_pages(obj); > if (ret) > goto err; > > @@ -168,6 +177,21 @@ static int i915_gem_end_cpu_access(struct dma_buf > *dma_buf, enum dma_data_direct > return err; > } > > +static int i915_gem_dmabuf_pin(struct dma_buf_attachment *attach) > +{ > + struct drm_i915_gem_object *obj = dma_buf_to_obj(attach->dmabuf); > + > + assert_object_held(obj); > + return i915_gem_object_pin_pages(obj); > +} > + > +static void i915_gem_dmabuf_unpin(struct dma_buf_attachment *attach) > +{ > + struct drm_i915_gem_object *obj = dma_buf_to_obj(attach->dmabuf); > + > + i915_gem_object_unpin_pages(obj); > +} > + > static const struct dma_buf_ops i915_dmabuf_ops = { > .map_dma_buf = i915_gem_map_dma_buf, > .unmap_dma_buf = i915_gem_unmap_dma_buf, > @@ -177,6 +201,8 @@ static const struct dma_buf_ops i915_dmabuf_ops = { > .vunmap = i915_gem_dmabuf_vunmap, > .begin_cpu_access = i915_gem_begin_cpu_access, > .end_cpu_access = i915_gem_end_cpu_access, > + .pin = i915_gem_dmabuf_pin, > + .unpin = i915_gem_dmabuf_unpin, > }; > > struct dma_buf *i915_gem_prime_export(struct drm_gem_object *gem_obj, int > flags) > @@ -241,7 +267,8 @@ struct drm_gem_object *i915_gem_prime_import(struct > drm_device *dev, > if (dma_buf->ops == &i915_dmabuf_ops) { > obj = dma_buf_to_obj(dma_buf); > /* is it from our device? */ > - if (obj->base.dev == dev) { > + if (obj->base.dev == dev && > + !I915_SELFTEST_ONLY(force_different_devices)) { > /* >* Importing dmabuf exported from out own gem increases >* refcount on gem itself instead
Re: [Intel-gfx] [PATCH] drm/vgem: Use 256B aligned pitch
On Wed, Jun 30, 2021 at 12:46:27PM +, Surendrakumar Upadhyay, TejaskumarX wrote: > > > > -Original Message- > > From: Daniel Vetter > > Sent: 30 June 2021 17:52 > > To: Surendrakumar Upadhyay, TejaskumarX > > > > Cc: dri-devel@lists.freedesktop.org; intel-...@lists.freedesktop.org; > > ch...@chris-wilson.co.uk > > Subject: Re: [Intel-gfx] [PATCH] drm/vgem: Use 256B aligned pitch > > > > On Wed, Jun 30, 2021 at 05:32:15PM +0530, Tejas Upadhyay wrote: > > > Having different alignment requirement by different drivers, 256B > > > aligned should work for all drm drivers. > > > > What. > > > > Like yes vgem abuses dumb_create, but it's not a kms driver. Pitch is > > meaningless, and that's why we align it minimally to 1 byte (bpp = bits per > > pixel here). > > > > Maybe start with explaining what you're trying to do here. > > -Daniel > > > > > Igt tool tests which are trying to exercise tests through VGEM are getting > failure (if not 64B aligned) on Intel platforms in creating framebuffer as > they need them to be 64B aligned. Then 64B alignment is not > A requirement for all drm drivers. Fix the tests. We're not going to encode alignment constraints for all kms drivers in vgem, that's not what vgem is for. Really what we should have done is just give vgem an ioctl to allocate a buffer, with the size specified in bytes. Not this "abuse dumb_create" business we're doing. But that's a past mistake, can't really fix that. -Daniel > > Thanks, > Tejas > > > > Signed-off-by: Tejas Upadhyay > > > > > > --- > > > drivers/gpu/drm/vgem/vgem_drv.c | 2 +- > > > 1 file changed, 1 insertion(+), 1 deletion(-) > > > > > > diff --git a/drivers/gpu/drm/vgem/vgem_drv.c > > > b/drivers/gpu/drm/vgem/vgem_drv.c index bf38a7e319d1..1da6df5e256a > > > 100644 > > > --- a/drivers/gpu/drm/vgem/vgem_drv.c > > > +++ b/drivers/gpu/drm/vgem/vgem_drv.c > > > @@ -215,7 +215,7 @@ static int vgem_gem_dumb_create(struct drm_file > > *file, struct drm_device *dev, > > > struct drm_gem_object *gem_object; > > > u64 pitch, size; > > > > > > - pitch = args->width * DIV_ROUND_UP(args->bpp, 8); > > > + pitch = ALIGN(args->width * DIV_ROUND_UP(args->bpp, 8), 256); > > > size = args->height * pitch; > > > if (size == 0) > > > return -EINVAL; > > > -- > > > 2.31.1 > > > > > > ___ > > > Intel-gfx mailing list > > > intel-...@lists.freedesktop.org > > > https://lists.freedesktop.org/mailman/listinfo/intel-gfx > > > > -- > > Daniel Vetter > > Software Engineer, Intel Corporation > > http://blog.ffwll.ch -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
RE: [PATCH 1/2] drm/i915/gem: Make our dma-buf exporter dynamic
>-Original Message- >From: Daniel Vetter >Sent: Wednesday, June 30, 2021 10:02 AM >To: Thomas Hellström ; Christian König > >Cc: intel-...@lists.freedesktop.org; dri-devel@lists.freedesktop.org; Auld, >Matthew ; maarten.lankho...@linux.intel.com; >dan...@ffwll.ch; Ruhl, Michael J >Subject: Re: [PATCH 1/2] drm/i915/gem: Make our dma-buf exporter dynamic > >On Wed, Jun 30, 2021 at 03:07:00PM +0200, Thomas Hellström wrote: >> If our exported dma-bufs are imported by another instance of our driver, >> that instance will typically have the imported dma-bufs locked during >> dma_buf_map_attachment(). But the exporter also locks the same >reservation >> object in the map_dma_buf() callback, which leads to recursive locking. >> >> Add a live selftest to exercise both dynamic and non-dynamic exports, >> and as a workaround until we fully support dynamic import and export, >> declare the exporter dynamic by providing pin() and unpin() >implementations. >> For dynamic importers, make sure we keep the pinning also in >map_dma_buf(), >> to ensure we never need to call dma_buf_move_notify(). >> Calling dma_buf_move_notify() is at the discretion of the exporter. >> >> v2: >> - Extend the selftest with a fake dynamic importer. >> - Provide real pin and unpin callbacks to not abuse the interface. >> >> Reported-by: Michael J. Ruhl >> Signed-off-by: Thomas Hellström > >I'm not happy with this, because i915 is currently violating the dma-resv >fencing rules for dynamic dma-buf. > >Yes since this is just the exporter we can probably get away with yolo'ing >things, but Christian and me just spend a lot of angry typing figuring out >what the rules actually are, so I really don't like bending them even more >just because it's less typing. > >All we need for a quick interim fix is to not take the dma_resv_lock from >our map/unamp callbacks. Pinning our backing storage from attach/detach >callbacks (which are also called under dma_resv_lock) would also achieve >that, without mudding any waters. So essentially just moving the >pin/unpin_pages_unlocked and we should be good, which is almost as little >typing. > >Michael, since Thomas is on vacations now, care to type that up? The >selftest is imo solid. Yes, I will get that done. Mike >This is also consistent with what all other ttm based drivers do (aside >from amdgpu, which is fully dynamic), see drm_gem_map_attach in >drm_prime.c > >Adding Christian as fyi. >-Daniel > >> --- >> drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 31 - >> .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 116 >+- >> 2 files changed, 143 insertions(+), 4 deletions(-) >> >> diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c >b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c >> index 616c3a2f1baf..918c19df7b66 100644 >> --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c >> +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c >> @@ -12,6 +12,8 @@ >> #include "i915_gem_object.h" >> #include "i915_scatterlist.h" >> >> +I915_SELFTEST_DECLARE(static bool force_different_devices;) >> + >> static struct drm_i915_gem_object *dma_buf_to_obj(struct dma_buf >*buf) >> { >> return to_intel_bo(buf->priv); >> @@ -25,7 +27,14 @@ static struct sg_table >*i915_gem_map_dma_buf(struct dma_buf_attachment *attachme >> struct scatterlist *src, *dst; >> int ret, i; >> >> -ret = i915_gem_object_pin_pages_unlocked(obj); >> +assert_object_held(obj); >> + >> +/* >> + * Note. In the dynamic importer case, the object is not yet pinned. >> + * Let's pin it here to avoid having to call the move_notify >> + * callback, The call of which is not yet implemented. >> + */ >> +ret = i915_gem_object_pin_pages(obj); >> if (ret) >> goto err; >> >> @@ -168,6 +177,21 @@ static int i915_gem_end_cpu_access(struct >dma_buf *dma_buf, enum dma_data_direct >> return err; >> } >> >> +static int i915_gem_dmabuf_pin(struct dma_buf_attachment *attach) >> +{ >> +struct drm_i915_gem_object *obj = dma_buf_to_obj(attach- >>dmabuf); >> + >> +assert_object_held(obj); >> +return i915_gem_object_pin_pages(obj); >> +} >> + >> +static void i915_gem_dmabuf_unpin(struct dma_buf_attachment *attach) >> +{ >> +struct drm_i915_gem_object *obj = dma_buf_to_obj(attach- >>dmabuf); >> + >> +i915_gem_object_unpin_pages(obj); >> +} >> + >> static const struct dma_buf_ops i915_dmabuf_ops = { >> .map_dma_buf = i915_gem_map_dma_buf, >> .unmap_dma_buf = i915_gem_unmap_dma_buf, >> @@ -177,6 +201,8 @@ static const struct dma_buf_ops i915_dmabuf_ops = >{ >> .vunmap = i915_gem_dmabuf_vunmap, >> .begin_cpu_access = i915_gem_begin_cpu_access, >> .end_cpu_access = i915_gem_end_cpu_access, >> +.pin = i915_gem_dmabuf_pin, >> +.unpin = i915_gem_dmabuf_unpin, >> }; >> >> struct dma_buf *i915_gem_prime_export(struct drm_gem_object >*gem_obj, int flags) >> @@ -241,7 +267,8 @@ struct drm_gem_object >*i915_gem_prime_import(struct drm_devi
[PATCH 0/3] drm/bochs: Move to tiny/ and simplify
Move the bochs driver to tiny/ and simplify the clean-up code. Also update GEM VRAM helpers accordingly. Thomas Zimmermann (3): drm/bochs: Move to tiny/ drm/bochs: Use managed initialization for GEM VRAM helpers drm/vram-helper: Unexport drm_vram_helper_{alloc,release}_mm() MAINTAINERS | 2 +- drivers/gpu/drm/Kconfig | 2 - drivers/gpu/drm/Makefile | 1 - drivers/gpu/drm/bochs/Kconfig | 11 - drivers/gpu/drm/bochs/Makefile| 4 - drivers/gpu/drm/bochs/bochs.h | 98 drivers/gpu/drm/bochs/bochs_drv.c | 205 --- drivers/gpu/drm/bochs/bochs_hw.c | 323 --- drivers/gpu/drm/bochs/bochs_kms.c | 178 --- drivers/gpu/drm/bochs/bochs_mm.c | 24 - drivers/gpu/drm/drm_gem_vram_helper.c | 9 +- drivers/gpu/drm/tiny/Kconfig | 13 + drivers/gpu/drm/tiny/Makefile | 1 + drivers/gpu/drm/tiny/bochs.c | 735 ++ include/drm/drm_gem_vram_helper.h | 4 - 15 files changed, 753 insertions(+), 857 deletions(-) delete mode 100644 drivers/gpu/drm/bochs/Kconfig delete mode 100644 drivers/gpu/drm/bochs/Makefile delete mode 100644 drivers/gpu/drm/bochs/bochs.h delete mode 100644 drivers/gpu/drm/bochs/bochs_drv.c delete mode 100644 drivers/gpu/drm/bochs/bochs_hw.c delete mode 100644 drivers/gpu/drm/bochs/bochs_kms.c delete mode 100644 drivers/gpu/drm/bochs/bochs_mm.c create mode 100644 drivers/gpu/drm/tiny/bochs.c -- 2.32.0
[PATCH 1/3] drm/bochs: Move to tiny/
The bochs driver is only ~600 lines of code. Putting it into tiny/ cleans up the DRM directory slightly. Some style problems were fixed and unneeded include statements were removed. No functional changes. Signed-off-by: Thomas Zimmermann --- MAINTAINERS | 2 +- drivers/gpu/drm/Kconfig | 2 - drivers/gpu/drm/Makefile | 1 - drivers/gpu/drm/bochs/Kconfig | 11 - drivers/gpu/drm/bochs/Makefile| 4 - drivers/gpu/drm/bochs/bochs.h | 98 drivers/gpu/drm/bochs/bochs_drv.c | 205 drivers/gpu/drm/bochs/bochs_hw.c | 323 - drivers/gpu/drm/bochs/bochs_kms.c | 178 --- drivers/gpu/drm/bochs/bochs_mm.c | 24 - drivers/gpu/drm/tiny/Kconfig | 13 + drivers/gpu/drm/tiny/Makefile | 1 + drivers/gpu/drm/tiny/bochs.c | 768 ++ 13 files changed, 783 insertions(+), 847 deletions(-) delete mode 100644 drivers/gpu/drm/bochs/Kconfig delete mode 100644 drivers/gpu/drm/bochs/Makefile delete mode 100644 drivers/gpu/drm/bochs/bochs.h delete mode 100644 drivers/gpu/drm/bochs/bochs_drv.c delete mode 100644 drivers/gpu/drm/bochs/bochs_hw.c delete mode 100644 drivers/gpu/drm/bochs/bochs_kms.c delete mode 100644 drivers/gpu/drm/bochs/bochs_mm.c create mode 100644 drivers/gpu/drm/tiny/bochs.c diff --git a/MAINTAINERS b/MAINTAINERS index dcb5f0d32303..95bad8d45200 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -5680,7 +5680,7 @@ M:Gerd Hoffmann L: virtualizat...@lists.linux-foundation.org S: Maintained T: git git://anongit.freedesktop.org/drm/drm-misc -F: drivers/gpu/drm/bochs/ +F: drivers/gpu/drm/tiny/bochs.c DRM DRIVER FOR BOE HIMAX8279D PANELS M: Jerry Han diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig index 1366d8d4610a..0d372354c2d0 100644 --- a/drivers/gpu/drm/Kconfig +++ b/drivers/gpu/drm/Kconfig @@ -322,8 +322,6 @@ source "drivers/gpu/drm/tilcdc/Kconfig" source "drivers/gpu/drm/qxl/Kconfig" -source "drivers/gpu/drm/bochs/Kconfig" - source "drivers/gpu/drm/virtio/Kconfig" source "drivers/gpu/drm/msm/Kconfig" diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile index 12e6f4e485ed..ad1112154898 100644 --- a/drivers/gpu/drm/Makefile +++ b/drivers/gpu/drm/Makefile @@ -98,7 +98,6 @@ obj-y += omapdrm/ obj-$(CONFIG_DRM_SUN4I) += sun4i/ obj-y += tilcdc/ obj-$(CONFIG_DRM_QXL) += qxl/ -obj-$(CONFIG_DRM_BOCHS) += bochs/ obj-$(CONFIG_DRM_VIRTIO_GPU) += virtio/ obj-$(CONFIG_DRM_MSM) += msm/ obj-$(CONFIG_DRM_TEGRA) += tegra/ diff --git a/drivers/gpu/drm/bochs/Kconfig b/drivers/gpu/drm/bochs/Kconfig deleted file mode 100644 index 7bcdf294fed8.. --- a/drivers/gpu/drm/bochs/Kconfig +++ /dev/null @@ -1,11 +0,0 @@ -# SPDX-License-Identifier: GPL-2.0-only -config DRM_BOCHS - tristate "DRM Support for bochs dispi vga interface (qemu stdvga)" - depends on DRM && PCI && MMU - select DRM_KMS_HELPER - select DRM_VRAM_HELPER - select DRM_TTM - select DRM_TTM_HELPER - help - Choose this option for qemu. - If M is selected the module will be called bochs-drm. diff --git a/drivers/gpu/drm/bochs/Makefile b/drivers/gpu/drm/bochs/Makefile deleted file mode 100644 index 55473371300f.. --- a/drivers/gpu/drm/bochs/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -# SPDX-License-Identifier: GPL-2.0-only -bochs-drm-y := bochs_drv.o bochs_mm.o bochs_kms.o bochs_hw.o - -obj-$(CONFIG_DRM_BOCHS)+= bochs-drm.o diff --git a/drivers/gpu/drm/bochs/bochs.h b/drivers/gpu/drm/bochs/bochs.h deleted file mode 100644 index e9645c612aff.. --- a/drivers/gpu/drm/bochs/bochs.h +++ /dev/null @@ -1,98 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ - -#include -#include - -#include -#include -#include -#include -#include -#include -#include - -/* -- */ - -#define VBE_DISPI_IOPORT_INDEX 0x01CE -#define VBE_DISPI_IOPORT_DATA0x01CF - -#define VBE_DISPI_INDEX_ID 0x0 -#define VBE_DISPI_INDEX_XRES 0x1 -#define VBE_DISPI_INDEX_YRES 0x2 -#define VBE_DISPI_INDEX_BPP 0x3 -#define VBE_DISPI_INDEX_ENABLE 0x4 -#define VBE_DISPI_INDEX_BANK 0x5 -#define VBE_DISPI_INDEX_VIRT_WIDTH 0x6 -#define VBE_DISPI_INDEX_VIRT_HEIGHT 0x7 -#define VBE_DISPI_INDEX_X_OFFSET 0x8 -#define VBE_DISPI_INDEX_Y_OFFSET 0x9 -#define VBE_DISPI_INDEX_VIDEO_MEMORY_64K 0xa - -#define VBE_DISPI_ID00xB0C0 -#define VBE_DISPI_ID10xB0C1 -#define VBE_DISPI_ID20xB0C2 -#define VBE_DISPI_ID30xB0C3 -#define VBE_DISPI_ID40xB0C4 -#define VBE_DISPI_ID50xB0C5 - -#define VBE_DISPI_DISABLED 0x00 -#define VBE_DISPI_ENABLED0x01 -#define VBE_DISPI_GETCAPS
[PATCH 2/3] drm/bochs: Use managed initialization for GEM VRAM helpers
Convert to managed GEM VRAM initialization and switch bochs to full autocleanup. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/tiny/bochs.c | 43 +--- 1 file changed, 5 insertions(+), 38 deletions(-) diff --git a/drivers/gpu/drm/tiny/bochs.c b/drivers/gpu/drm/tiny/bochs.c index edcd31db5b9c..254787fbf0ea 100644 --- a/drivers/gpu/drm/tiny/bochs.c +++ b/drivers/gpu/drm/tiny/bochs.c @@ -404,25 +404,6 @@ static void bochs_hw_setbase(struct bochs_device *bochs, int x, int y, int strid /* -- */ -static int bochs_mm_init(struct bochs_device *bochs) -{ - struct drm_vram_mm *vmm; - - vmm = drm_vram_helper_alloc_mm(bochs->dev, bochs->fb_base, - bochs->fb_size); - return PTR_ERR_OR_ZERO(vmm); -} - -static void bochs_mm_fini(struct bochs_device *bochs) -{ - if (!bochs->dev->vram_mm) - return; - - drm_vram_helper_release_mm(bochs->dev); -} - -/* -- */ - static const uint32_t bochs_formats[] = { DRM_FORMAT_XRGB, DRM_FORMAT_BGRX, @@ -582,13 +563,6 @@ static int bochs_kms_init(struct bochs_device *bochs) /* -- */ /* drm interface */ -static void bochs_unload(struct drm_device *dev) -{ - struct bochs_device *bochs = dev->dev_private; - - bochs_mm_fini(bochs); -} - static int bochs_load(struct drm_device *dev) { struct bochs_device *bochs; @@ -602,21 +576,17 @@ static int bochs_load(struct drm_device *dev) ret = bochs_hw_init(dev); if (ret) - goto err; + return ret; - ret = bochs_mm_init(bochs); + ret = drmm_vram_helper_init(dev, bochs->fb_base, bochs->fb_size); if (ret) - goto err; + return ret; ret = bochs_kms_init(bochs); if (ret) - goto err; + return ret; return 0; - -err: - bochs_unload(dev); - return ret; } DEFINE_DRM_GEM_FOPS(bochs_fops); @@ -630,7 +600,6 @@ static const struct drm_driver bochs_driver = { .major = 1, .minor = 0, DRM_GEM_VRAM_DRIVER, - .release= bochs_unload, }; /* -- */ @@ -693,13 +662,11 @@ static int bochs_pci_probe(struct pci_dev *pdev, ret = drm_dev_register(dev, 0); if (ret) - goto err_unload; + goto err_free_dev; drm_fbdev_generic_setup(dev, 32); return ret; -err_unload: - bochs_unload(dev); err_free_dev: drm_dev_put(dev); return ret; -- 2.32.0
[PATCH 3/3] drm/vram-helper: Unexport drm_vram_helper_{alloc, release}_mm()
All GEM-VRAM-based drivers use auto-cleanup via drmm_vram_helper_init(). Unexport the manual APIs and make them internal implementation. Signed-off-by: Thomas Zimmermann --- drivers/gpu/drm/drm_gem_vram_helper.c | 9 +++-- include/drm/drm_gem_vram_helper.h | 4 2 files changed, 3 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/drm_gem_vram_helper.c b/drivers/gpu/drm/drm_gem_vram_helper.c index 2a1229b8364e..1e9b82e51a07 100644 --- a/drivers/gpu/drm/drm_gem_vram_helper.c +++ b/drivers/gpu/drm/drm_gem_vram_helper.c @@ -1012,9 +1012,8 @@ static void drm_vram_mm_cleanup(struct drm_vram_mm *vmm) * Helpers for integration with struct drm_device */ -/* deprecated; use drmm_vram_mm_init() */ -struct drm_vram_mm *drm_vram_helper_alloc_mm( - struct drm_device *dev, uint64_t vram_base, size_t vram_size) +static struct drm_vram_mm *drm_vram_helper_alloc_mm(struct drm_device *dev, uint64_t vram_base, + size_t vram_size) { int ret; @@ -1036,9 +1035,8 @@ struct drm_vram_mm *drm_vram_helper_alloc_mm( dev->vram_mm = NULL; return ERR_PTR(ret); } -EXPORT_SYMBOL(drm_vram_helper_alloc_mm); -void drm_vram_helper_release_mm(struct drm_device *dev) +static void drm_vram_helper_release_mm(struct drm_device *dev) { if (!dev->vram_mm) return; @@ -1047,7 +1045,6 @@ void drm_vram_helper_release_mm(struct drm_device *dev) kfree(dev->vram_mm); dev->vram_mm = NULL; } -EXPORT_SYMBOL(drm_vram_helper_release_mm); static void drm_vram_mm_release(struct drm_device *dev, void *ptr) { diff --git a/include/drm/drm_gem_vram_helper.h b/include/drm/drm_gem_vram_helper.h index f48d181c824b..d3cf06c9af65 100644 --- a/include/drm/drm_gem_vram_helper.h +++ b/include/drm/drm_gem_vram_helper.h @@ -204,10 +204,6 @@ void drm_vram_mm_debugfs_init(struct drm_minor *minor); * Helpers for integration with struct drm_device */ -struct drm_vram_mm *drm_vram_helper_alloc_mm( - struct drm_device *dev, uint64_t vram_base, size_t vram_size); -void drm_vram_helper_release_mm(struct drm_device *dev); - int drmm_vram_helper_init(struct drm_device *dev, uint64_t vram_base, size_t vram_size); -- 2.32.0
Re: [PATCH] dma-buf: fix and rework dma_buf_poll v4
On Wed, Jun 30, 2021 at 2:36 PM Christian König wrote: > > Daniel pointed me towards this function and there are multiple obvious > problems > in the implementation. > > First of all the retry loop is not working as intended. In general the retry > makes only sense if you grab the reference first and then check the sequence > values. > > Then we should always also wait for the exclusive fence. > > It's also good practice to keep the reference around when installing callbacks > to fences you don't own. > > And last the whole implementation was unnecessary complex and rather hard to > understand which could lead to probably unexpected behavior of the IOCTL. > > Fix all this by reworking the implementation from scratch. Dropping the > whole RCU approach and taking the lock instead. > > Only mildly tested and needs a thoughtful review of the code. prime_vgem.c has some basic stuff, but it might actually encoding the broken behaviour. Would be good to extend/fix that I think so we don't entirely rely on review. We can't really build easily on top of the testcase Jason created for import/export, since for implicit sync we need some driver that attaches the fences for us. There's also a vc4 one, but I guess that's less useful for us :-) > v2: fix the reference counting as well > v3: keep the excl fence handling as is for stable > v4: back to testing all fences, drop RCU > > Signed-off-by: Christian König > CC: sta...@vger.kernel.org > --- > drivers/dma-buf/dma-buf.c | 132 +- > include/linux/dma-buf.h | 2 +- > 2 files changed, 46 insertions(+), 88 deletions(-) > > diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c > index eadd1eaa2fb5..192c4d34704b 100644 > --- a/drivers/dma-buf/dma-buf.c > +++ b/drivers/dma-buf/dma-buf.c > @@ -72,7 +72,7 @@ static void dma_buf_release(struct dentry *dentry) > * If you hit this BUG() it means someone dropped their ref to the > * dma-buf while still having pending operation to the buffer. > */ > - BUG_ON(dmabuf->cb_shared.active || dmabuf->cb_excl.active); > + BUG_ON(dmabuf->cb_in.active || dmabuf->cb_out.active); > > dmabuf->ops->release(dmabuf); > > @@ -202,16 +202,19 @@ static void dma_buf_poll_cb(struct dma_fence *fence, > struct dma_fence_cb *cb) > wake_up_locked_poll(dcb->poll, dcb->active); > dcb->active = 0; > spin_unlock_irqrestore(&dcb->poll->lock, flags); > + dma_fence_put(fence); > } > > static __poll_t dma_buf_poll(struct file *file, poll_table *poll) > { > + struct dma_buf_poll_cb_t *dcb; > struct dma_buf *dmabuf; > struct dma_resv *resv; > struct dma_resv_list *fobj; > - struct dma_fence *fence_excl; > + struct dma_fence *fence; > + unsigned shared_count; > __poll_t events; > - unsigned shared_count, seq; > + int r, i; > > dmabuf = file->private_data; > if (!dmabuf || !dmabuf->resv) > @@ -225,101 +228,56 @@ static __poll_t dma_buf_poll(struct file *file, > poll_table *poll) > if (!events) > return 0; > > -retry: > - seq = read_seqcount_begin(&resv->seq); > - rcu_read_lock(); > + dcb = events & EPOLLOUT ? &dmabuf->cb_out : &dmabuf->cb_in; > + > + /* Only queue a new one if we are not still waiting for the old one */ > + spin_lock_irq(&dmabuf->poll.lock); > + if (dcb->active) > + events = 0; > + else > + dcb->active = events; > + spin_unlock_irq(&dmabuf->poll.lock); > + if (!events) > + return 0; > + > + dma_resv_lock(resv, NULL); > > - fobj = rcu_dereference(resv->fence); > - if (fobj) > + fobj = dma_resv_get_list(resv); > + if (fobj && events & EPOLLOUT) > shared_count = fobj->shared_count; > else > shared_count = 0; > - fence_excl = rcu_dereference(resv->fence_excl); > - if (read_seqcount_retry(&resv->seq, seq)) { > - rcu_read_unlock(); > - goto retry; > - } > > - if (fence_excl && (!(events & EPOLLOUT) || shared_count == 0)) { > - struct dma_buf_poll_cb_t *dcb = &dmabuf->cb_excl; > - __poll_t pevents = EPOLLIN; > - > - if (shared_count == 0) > - pevents |= EPOLLOUT; > - > - spin_lock_irq(&dmabuf->poll.lock); > - if (dcb->active) { > - dcb->active |= pevents; > - events &= ~pevents; > - } else > - dcb->active = pevents; > - spin_unlock_irq(&dmabuf->poll.lock); > - > - if (events & pevents) { > - if (!dma_fence_get_rcu(fence_excl)) { > - /* force a recheck */ > - events &= ~pevents; > - dma_buf_po
Re: [PATCH 1/3] drm/bochs: Move to tiny/
On Wed, Jun 30, 2021 at 04:06:57PM +0200, Thomas Zimmermann wrote: > The bochs driver is only ~600 lines of code. Putting it into tiny/ > cleans up the DRM directory slightly. Some style problems were fixed > and unneeded include statements were removed. No functional changes. > > Signed-off-by: Thomas Zimmermann Really nice! On the series: Acked-by: Daniel Vetter I think I've found one missing static below. Cheers, Daniel > --- > MAINTAINERS | 2 +- > drivers/gpu/drm/Kconfig | 2 - > drivers/gpu/drm/Makefile | 1 - > drivers/gpu/drm/bochs/Kconfig | 11 - > drivers/gpu/drm/bochs/Makefile| 4 - > drivers/gpu/drm/bochs/bochs.h | 98 > drivers/gpu/drm/bochs/bochs_drv.c | 205 > drivers/gpu/drm/bochs/bochs_hw.c | 323 - > drivers/gpu/drm/bochs/bochs_kms.c | 178 --- > drivers/gpu/drm/bochs/bochs_mm.c | 24 - > drivers/gpu/drm/tiny/Kconfig | 13 + > drivers/gpu/drm/tiny/Makefile | 1 + > drivers/gpu/drm/tiny/bochs.c | 768 ++ > 13 files changed, 783 insertions(+), 847 deletions(-) > delete mode 100644 drivers/gpu/drm/bochs/Kconfig > delete mode 100644 drivers/gpu/drm/bochs/Makefile > delete mode 100644 drivers/gpu/drm/bochs/bochs.h > delete mode 100644 drivers/gpu/drm/bochs/bochs_drv.c > delete mode 100644 drivers/gpu/drm/bochs/bochs_hw.c > delete mode 100644 drivers/gpu/drm/bochs/bochs_kms.c > delete mode 100644 drivers/gpu/drm/bochs/bochs_mm.c > create mode 100644 drivers/gpu/drm/tiny/bochs.c > > diff --git a/MAINTAINERS b/MAINTAINERS > index dcb5f0d32303..95bad8d45200 100644 > --- a/MAINTAINERS > +++ b/MAINTAINERS > @@ -5680,7 +5680,7 @@ M: Gerd Hoffmann > L: virtualizat...@lists.linux-foundation.org > S: Maintained > T: git git://anongit.freedesktop.org/drm/drm-misc > -F: drivers/gpu/drm/bochs/ > +F: drivers/gpu/drm/tiny/bochs.c > > DRM DRIVER FOR BOE HIMAX8279D PANELS > M: Jerry Han > diff --git a/drivers/gpu/drm/Kconfig b/drivers/gpu/drm/Kconfig > index 1366d8d4610a..0d372354c2d0 100644 > --- a/drivers/gpu/drm/Kconfig > +++ b/drivers/gpu/drm/Kconfig > @@ -322,8 +322,6 @@ source "drivers/gpu/drm/tilcdc/Kconfig" > > source "drivers/gpu/drm/qxl/Kconfig" > > -source "drivers/gpu/drm/bochs/Kconfig" > - > source "drivers/gpu/drm/virtio/Kconfig" > > source "drivers/gpu/drm/msm/Kconfig" > diff --git a/drivers/gpu/drm/Makefile b/drivers/gpu/drm/Makefile > index 12e6f4e485ed..ad1112154898 100644 > --- a/drivers/gpu/drm/Makefile > +++ b/drivers/gpu/drm/Makefile > @@ -98,7 +98,6 @@ obj-y += omapdrm/ > obj-$(CONFIG_DRM_SUN4I) += sun4i/ > obj-y+= tilcdc/ > obj-$(CONFIG_DRM_QXL) += qxl/ > -obj-$(CONFIG_DRM_BOCHS) += bochs/ > obj-$(CONFIG_DRM_VIRTIO_GPU) += virtio/ > obj-$(CONFIG_DRM_MSM) += msm/ > obj-$(CONFIG_DRM_TEGRA) += tegra/ > diff --git a/drivers/gpu/drm/bochs/Kconfig b/drivers/gpu/drm/bochs/Kconfig > deleted file mode 100644 > index 7bcdf294fed8.. > --- a/drivers/gpu/drm/bochs/Kconfig > +++ /dev/null > @@ -1,11 +0,0 @@ > -# SPDX-License-Identifier: GPL-2.0-only > -config DRM_BOCHS > - tristate "DRM Support for bochs dispi vga interface (qemu stdvga)" > - depends on DRM && PCI && MMU > - select DRM_KMS_HELPER > - select DRM_VRAM_HELPER > - select DRM_TTM > - select DRM_TTM_HELPER > - help > - Choose this option for qemu. > - If M is selected the module will be called bochs-drm. > diff --git a/drivers/gpu/drm/bochs/Makefile b/drivers/gpu/drm/bochs/Makefile > deleted file mode 100644 > index 55473371300f.. > --- a/drivers/gpu/drm/bochs/Makefile > +++ /dev/null > @@ -1,4 +0,0 @@ > -# SPDX-License-Identifier: GPL-2.0-only > -bochs-drm-y := bochs_drv.o bochs_mm.o bochs_kms.o bochs_hw.o > - > -obj-$(CONFIG_DRM_BOCHS) += bochs-drm.o > diff --git a/drivers/gpu/drm/bochs/bochs.h b/drivers/gpu/drm/bochs/bochs.h > deleted file mode 100644 > index e9645c612aff.. > --- a/drivers/gpu/drm/bochs/bochs.h > +++ /dev/null > @@ -1,98 +0,0 @@ > -/* SPDX-License-Identifier: GPL-2.0 */ > - > -#include > -#include > - > -#include > -#include > -#include > -#include > -#include > -#include > -#include > - > -/* -- */ > - > -#define VBE_DISPI_IOPORT_INDEX 0x01CE > -#define VBE_DISPI_IOPORT_DATA0x01CF > - > -#define VBE_DISPI_INDEX_ID 0x0 > -#define VBE_DISPI_INDEX_XRES 0x1 > -#define VBE_DISPI_INDEX_YRES 0x2 > -#define VBE_DISPI_INDEX_BPP 0x3 > -#define VBE_DISPI_INDEX_ENABLE 0x4 > -#define VBE_DISPI_INDEX_BANK 0x5 > -#define VBE_DISPI_INDEX_VIRT_WIDTH 0x6 > -#define VBE_DISPI_INDEX_VIRT_HEIGHT 0x7 > -#define VBE_DISPI_INDEX_X_OFFSET 0x8 > -#define VBE_DISPI_INDEX_Y_OFFSET 0x9 > -#define VBE_DISPI_INDEX_VIDEO_MEMORY_64K 0x
Re: [PATCH v6 14/16] drm/panfrost: Kill in-flight jobs on FD close
On 30/06/2021 07:27, Boris Brezillon wrote: > If the process who submitted these jobs decided to close the FD before > the jobs are done it probably means it doesn't care about the result. > > v5: > * Add a panfrost_exception_is_fault() helper and the > DRM_PANFROST_EXCEPTION_MAX_NON_FAULT value > > v4: > * Don't disable/restore irqs when taking the job_lock (not needed since > this lock is never taken from an interrupt context) > > v3: > * Set fence error to ECANCELED when a TERMINATED exception is received > > Signed-off-by: Boris Brezillon > --- > drivers/gpu/drm/panfrost/panfrost_device.h | 7 > drivers/gpu/drm/panfrost/panfrost_job.c| 42 ++ > 2 files changed, 43 insertions(+), 6 deletions(-) The panfrost_exception_is_fault() makes the code much more readable - thanks! Reviewed-by: Steven Price > > diff --git a/drivers/gpu/drm/panfrost/panfrost_device.h > b/drivers/gpu/drm/panfrost/panfrost_device.h > index 68e93b7e5b61..193cd87f643c 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_device.h > +++ b/drivers/gpu/drm/panfrost/panfrost_device.h > @@ -184,6 +184,7 @@ enum drm_panfrost_exception_type { > DRM_PANFROST_EXCEPTION_KABOOM = 0x05, > DRM_PANFROST_EXCEPTION_EUREKA = 0x06, > DRM_PANFROST_EXCEPTION_ACTIVE = 0x08, > + DRM_PANFROST_EXCEPTION_MAX_NON_FAULT = 0x3f, > DRM_PANFROST_EXCEPTION_JOB_CONFIG_FAULT = 0x40, > DRM_PANFROST_EXCEPTION_JOB_POWER_FAULT = 0x41, > DRM_PANFROST_EXCEPTION_JOB_READ_FAULT = 0x42, > @@ -244,6 +245,12 @@ enum drm_panfrost_exception_type { > DRM_PANFROST_EXCEPTION_MEM_ATTR_NONCACHE_3 = 0xef, > }; > > +static inline bool > +panfrost_exception_is_fault(u32 exception_code) > +{ > + return exception_code > DRM_PANFROST_EXCEPTION_MAX_NON_FAULT; > +} > + > const char *panfrost_exception_name(u32 exception_code); > bool panfrost_exception_needs_reset(const struct panfrost_device *pfdev, > u32 exception_code); > diff --git a/drivers/gpu/drm/panfrost/panfrost_job.c > b/drivers/gpu/drm/panfrost/panfrost_job.c > index cf5f9e8b2a27..8a0db9571bfd 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_job.c > +++ b/drivers/gpu/drm/panfrost/panfrost_job.c > @@ -483,14 +483,21 @@ static void panfrost_job_handle_irq(struct > panfrost_device *pfdev, u32 status) > > if (status & JOB_INT_MASK_ERR(j)) { > u32 js_status = job_read(pfdev, JS_STATUS(j)); > + const char *exception_name = > panfrost_exception_name(js_status); > > job_write(pfdev, JS_COMMAND_NEXT(j), JS_COMMAND_NOP); > > - dev_err(pfdev->dev, "js fault, js=%d, status=%s, > head=0x%x, tail=0x%x", > - j, > - panfrost_exception_name(js_status), > - job_read(pfdev, JS_HEAD_LO(j)), > - job_read(pfdev, JS_TAIL_LO(j))); > + if (!panfrost_exception_is_fault(js_status)) { > + dev_dbg(pfdev->dev, "js interrupt, js=%d, > status=%s, head=0x%x, tail=0x%x", > + j, exception_name, > + job_read(pfdev, JS_HEAD_LO(j)), > + job_read(pfdev, JS_TAIL_LO(j))); > + } else { > + dev_err(pfdev->dev, "js fault, js=%d, > status=%s, head=0x%x, tail=0x%x", > + j, exception_name, > + job_read(pfdev, JS_HEAD_LO(j)), > + job_read(pfdev, JS_TAIL_LO(j))); > + } > > /* If we need a reset, signal it to the timeout >* handler, otherwise, update the fence error field and > @@ -499,7 +506,16 @@ static void panfrost_job_handle_irq(struct > panfrost_device *pfdev, u32 status) > if (panfrost_exception_needs_reset(pfdev, js_status)) { > drm_sched_fault(&pfdev->js->queue[j].sched); > } else { > - dma_fence_set_error(pfdev->jobs[j]->done_fence, > -EINVAL); > + int error = 0; > + > + if (js_status == > DRM_PANFROST_EXCEPTION_TERMINATED) > + error = -ECANCELED; > + else if (panfrost_exception_is_fault(js_status)) > + error = -EINVAL; > + > + if (error) > + > dma_fence_set_error(pfdev->jobs[j]->done_fence, error); > + > status |= JOB_INT_MASK_DONE(j); > } > } > @@ -665,10 +681,24 @@ int panfrost_job_open(struct panfrost_file_priv > *panfrost_priv) > > void panfrost_job_close(struc
Re: [PATCH v3 1/2] drm/i915: Use the correct IRQ during resume
Hi Am 30.06.21 um 12:49 schrieb Daniel Vetter: On Wed, Jun 30, 2021 at 11:52:27AM +0200, Thomas Zimmermann wrote: The code in xcs_resume() probably didn't work as intended. It uses struct drm_device.irq, which is allocated to 0, but never initialized by i915 to the device's interrupt number. v3: * also use intel_synchronize_hardirq() at another callsite v2: * wrap irq code in intel_synchronize_hardirq() (Ville) Signed-off-by: Thomas Zimmermann Fixes: 536f77b1caa0 ("drm/i915/gt: Call stop_ring() from ring resume, again") Cc: Chris Wilson Cc: Mika Kuoppala Cc: Daniel Vetter Cc: Rodrigo Vivi Cc: Joonas Lahtinen Cc: Maarten Lankhorst Cc: Lucas De Marchi --- drivers/gpu/drm/i915/gt/intel_engine_cs.c | 2 +- drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- drivers/gpu/drm/i915/i915_irq.c | 5 + drivers/gpu/drm/i915/i915_irq.h | 1 + 4 files changed, 8 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/gt/intel_engine_cs.c b/drivers/gpu/drm/i915/gt/intel_engine_cs.c index 88694822716a..5ca3d1664335 100644 --- a/drivers/gpu/drm/i915/gt/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/gt/intel_engine_cs.c @@ -1229,7 +1229,7 @@ bool intel_engine_is_idle(struct intel_engine_cs *engine) return true; /* Waiting to drain ELSP? */ - synchronize_hardirq(to_pci_dev(engine->i915->drm.dev)->irq); + intel_synchronize_hardirq(engine->i915); intel_engine_flush_submission(engine); /* ELSP is empty, but there are ready requests? E.g. after reset */ diff --git a/drivers/gpu/drm/i915/gt/intel_ring_submission.c b/drivers/gpu/drm/i915/gt/intel_ring_submission.c index 5d42a12ef3d6..1b5a22a83db6 100644 --- a/drivers/gpu/drm/i915/gt/intel_ring_submission.c +++ b/drivers/gpu/drm/i915/gt/intel_ring_submission.c @@ -185,7 +185,7 @@ static int xcs_resume(struct intel_engine_cs *engine) ring->head, ring->tail); /* Double check the ring is empty & disabled before we resume */ - synchronize_hardirq(engine->i915->drm.irq); + intel_synchronize_hardirq(engine->i915); if (!stop_ring(engine)) goto err; diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index 7d0ce8b9f8ed..2203dca19895 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -4575,3 +4575,8 @@ void intel_synchronize_irq(struct drm_i915_private *i915) { synchronize_irq(to_pci_dev(i915->drm.dev)->irq); } + +void intel_synchronize_hardirq(struct drm_i915_private *i915) +{ + synchronize_hardirq(to_pci_dev(i915->drm.dev)->irq); I honestly think the hardirq here is about as much cargo-culted as using the wrong irq number. I'd just use intel_synchronize_irq in both places and see whether CI complains, then go with that. Well, ok. I don't think I have Sandybridge HW available. Would the Intel CI infrastructure catch any problems with such a change? Best regards Thomas -Daniel +} diff --git a/drivers/gpu/drm/i915/i915_irq.h b/drivers/gpu/drm/i915/i915_irq.h index db34d5dbe402..e43b6734f21b 100644 --- a/drivers/gpu/drm/i915/i915_irq.h +++ b/drivers/gpu/drm/i915/i915_irq.h @@ -94,6 +94,7 @@ void intel_runtime_pm_disable_interrupts(struct drm_i915_private *dev_priv); void intel_runtime_pm_enable_interrupts(struct drm_i915_private *dev_priv); bool intel_irqs_enabled(struct drm_i915_private *dev_priv); void intel_synchronize_irq(struct drm_i915_private *i915); +void intel_synchronize_hardirq(struct drm_i915_private *i915); int intel_get_crtc_scanline(struct intel_crtc *crtc); void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, -- 2.32.0 -- Thomas Zimmermann Graphics Driver Developer SUSE Software Solutions Germany GmbH Maxfeldstr. 5, 90409 Nürnberg, Germany (HRB 36809, AG Nürnberg) Geschäftsführer: Felix Imendörffer OpenPGP_signature Description: OpenPGP digital signature
Re: [PATCH 1/2] drm/i915/ttm: Reorganize the ttm move code somewhat
On Thu, 24 Jun 2021 at 20:31, Thomas Hellström wrote: > > In order to make the code a bit more readable and to facilitate > async memcpy moves, reorganize the move code a little. Determine > at an early stage whether to copy or to clear. > > Signed-off-by: Thomas Hellström > --- > drivers/gpu/drm/i915/gem/i915_gem_ttm.c | 70 ++--- > 1 file changed, 40 insertions(+), 30 deletions(-) > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > index c39d982c4fa6..4e529adcdfc7 100644 > --- a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > +++ b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > @@ -431,6 +431,7 @@ i915_ttm_resource_get_st(struct drm_i915_gem_object *obj, > } > > static int i915_ttm_accel_move(struct ttm_buffer_object *bo, > + bool clear, >struct ttm_resource *dst_mem, >struct sg_table *dst_st) > { > @@ -449,13 +450,10 @@ static int i915_ttm_accel_move(struct ttm_buffer_object > *bo, > return -EINVAL; > > dst_level = i915_ttm_cache_level(i915, dst_mem, ttm); > - if (!ttm || !ttm_tt_is_populated(ttm)) { > + if (clear) { > if (bo->type == ttm_bo_type_kernel) > return -EINVAL; Was that meant to be: return 0: ? Also does that mean we are incorrectly falling back to memset, for non-userspace objects, instead of making it a noop? > > - if (ttm && !(ttm->page_flags & TTM_PAGE_FLAG_ZERO_ALLOC)) > - return 0; > - > intel_engine_pm_get(i915->gt.migrate.context->engine); > ret = intel_context_migrate_clear(i915->gt.migrate.context, > NULL, > dst_st->sgl, dst_level, > @@ -489,27 +487,53 @@ static int i915_ttm_accel_move(struct ttm_buffer_object > *bo, > return ret; > } > > -static int i915_ttm_move(struct ttm_buffer_object *bo, bool evict, > -struct ttm_operation_ctx *ctx, > -struct ttm_resource *dst_mem, > -struct ttm_place *hop) > +static void __i915_ttm_move(struct ttm_buffer_object *bo, bool clear, > + struct ttm_resource *dst_mem, > + struct sg_table *dst_st) > { > struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); > - struct ttm_resource_manager *dst_man = > - ttm_manager_type(bo->bdev, dst_mem->mem_type); > struct intel_memory_region *dst_reg, *src_reg; > union { > struct ttm_kmap_iter_tt tt; > struct ttm_kmap_iter_iomap io; > } _dst_iter, _src_iter; > struct ttm_kmap_iter *dst_iter, *src_iter; > - struct sg_table *dst_st; > int ret; > > dst_reg = i915_ttm_region(bo->bdev, dst_mem->mem_type); > src_reg = i915_ttm_region(bo->bdev, bo->resource->mem_type); > GEM_BUG_ON(!dst_reg || !src_reg); > > + ret = i915_ttm_accel_move(bo, clear, dst_mem, dst_st); > + if (ret) { One future consideration is flat CCS where I don't think we can easily fall back to memcpy for userspace objects. Maybe we can make this fallback conditional on DG1 or !ALLOC_USER for now, or just add a TODO? > + dst_iter = !cpu_maps_iomem(dst_mem) ? > + ttm_kmap_iter_tt_init(&_dst_iter.tt, bo->ttm) : > + ttm_kmap_iter_iomap_init(&_dst_iter.io, > &dst_reg->iomap, > +dst_st, > dst_reg->region.start); > + > + src_iter = !cpu_maps_iomem(bo->resource) ? > + ttm_kmap_iter_tt_init(&_src_iter.tt, bo->ttm) : > + ttm_kmap_iter_iomap_init(&_src_iter.io, > &src_reg->iomap, > +obj->ttm.cached_io_st, > +src_reg->region.start); > + > + ttm_move_memcpy(bo, dst_mem->num_pages, dst_iter, src_iter); > + } > +} > + > +static int i915_ttm_move(struct ttm_buffer_object *bo, bool evict, > +struct ttm_operation_ctx *ctx, > +struct ttm_resource *dst_mem, > +struct ttm_place *hop) > +{ > + struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); > + struct ttm_resource_manager *dst_man = > + ttm_manager_type(bo->bdev, dst_mem->mem_type); > + struct ttm_tt *ttm = bo->ttm; > + struct sg_table *dst_st; > + bool clear; > + int ret; > + > /* Sync for now. We could do the actual copy async. */ > ret = ttm_bo_wait_ctx(bo, ctx); > if (ret) > @@ -526,9 +550,8 @@ static int i915_ttm_move(struct ttm_buffer_object *bo, > bool evict, > } > > /* Populate ttm with pages if needed. Typically system memory. */ > - if (b
Re: [PATCH] dma-buf: fix and rework dma_buf_poll v4
Am 30.06.21 um 16:07 schrieb Daniel Vetter: On Wed, Jun 30, 2021 at 2:36 PM Christian König wrote: Daniel pointed me towards this function and there are multiple obvious problems in the implementation. First of all the retry loop is not working as intended. In general the retry makes only sense if you grab the reference first and then check the sequence values. Then we should always also wait for the exclusive fence. It's also good practice to keep the reference around when installing callbacks to fences you don't own. And last the whole implementation was unnecessary complex and rather hard to understand which could lead to probably unexpected behavior of the IOCTL. Fix all this by reworking the implementation from scratch. Dropping the whole RCU approach and taking the lock instead. Only mildly tested and needs a thoughtful review of the code. prime_vgem.c has some basic stuff, but it might actually encoding the broken behaviour. Would be good to extend/fix that I think so we don't entirely rely on review. We can't really build easily on top of the testcase Jason created for import/export, since for implicit sync we need some driver that attaches the fences for us. My question is if I can just send that to intel-...@lists.freedesktop.org and the CI will pick it up? There's also a vc4 one, but I guess that's less useful for us :-) v2: fix the reference counting as well v3: keep the excl fence handling as is for stable v4: back to testing all fences, drop RCU Signed-off-by: Christian König CC: sta...@vger.kernel.org --- drivers/dma-buf/dma-buf.c | 132 +- include/linux/dma-buf.h | 2 +- 2 files changed, 46 insertions(+), 88 deletions(-) diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c index eadd1eaa2fb5..192c4d34704b 100644 --- a/drivers/dma-buf/dma-buf.c +++ b/drivers/dma-buf/dma-buf.c @@ -72,7 +72,7 @@ static void dma_buf_release(struct dentry *dentry) * If you hit this BUG() it means someone dropped their ref to the * dma-buf while still having pending operation to the buffer. */ - BUG_ON(dmabuf->cb_shared.active || dmabuf->cb_excl.active); + BUG_ON(dmabuf->cb_in.active || dmabuf->cb_out.active); dmabuf->ops->release(dmabuf); @@ -202,16 +202,19 @@ static void dma_buf_poll_cb(struct dma_fence *fence, struct dma_fence_cb *cb) wake_up_locked_poll(dcb->poll, dcb->active); dcb->active = 0; spin_unlock_irqrestore(&dcb->poll->lock, flags); + dma_fence_put(fence); } static __poll_t dma_buf_poll(struct file *file, poll_table *poll) { + struct dma_buf_poll_cb_t *dcb; struct dma_buf *dmabuf; struct dma_resv *resv; struct dma_resv_list *fobj; - struct dma_fence *fence_excl; + struct dma_fence *fence; + unsigned shared_count; __poll_t events; - unsigned shared_count, seq; + int r, i; dmabuf = file->private_data; if (!dmabuf || !dmabuf->resv) @@ -225,101 +228,56 @@ static __poll_t dma_buf_poll(struct file *file, poll_table *poll) if (!events) return 0; -retry: - seq = read_seqcount_begin(&resv->seq); - rcu_read_lock(); + dcb = events & EPOLLOUT ? &dmabuf->cb_out : &dmabuf->cb_in; + + /* Only queue a new one if we are not still waiting for the old one */ + spin_lock_irq(&dmabuf->poll.lock); + if (dcb->active) + events = 0; + else + dcb->active = events; + spin_unlock_irq(&dmabuf->poll.lock); + if (!events) + return 0; + + dma_resv_lock(resv, NULL); - fobj = rcu_dereference(resv->fence); - if (fobj) + fobj = dma_resv_get_list(resv); + if (fobj && events & EPOLLOUT) shared_count = fobj->shared_count; else shared_count = 0; - fence_excl = rcu_dereference(resv->fence_excl); - if (read_seqcount_retry(&resv->seq, seq)) { - rcu_read_unlock(); - goto retry; - } - if (fence_excl && (!(events & EPOLLOUT) || shared_count == 0)) { - struct dma_buf_poll_cb_t *dcb = &dmabuf->cb_excl; - __poll_t pevents = EPOLLIN; - - if (shared_count == 0) - pevents |= EPOLLOUT; - - spin_lock_irq(&dmabuf->poll.lock); - if (dcb->active) { - dcb->active |= pevents; - events &= ~pevents; - } else - dcb->active = pevents; - spin_unlock_irq(&dmabuf->poll.lock); - - if (events & pevents) { - if (!dma_fence_get_rcu(fence_excl)) { - /* force a recheck */ - events &= ~pevents; - dma_buf_poll_cb(NULL, &dcb->cb); - } els
Re: [PATCH 2/2] drm/ttm, drm/i915: Update ttm_move_memcpy for async use
On Thu, 24 Jun 2021 at 20:31, Thomas Hellström wrote: > > The buffer object argument to ttm_move_memcpy was only used to > determine whether the destination memory should be cleared only > or whether we should copy data. Replace it with a "clear" bool, and > update the callers. > > The intention here is to be able to use ttm_move_memcpy() async under > a dma-fence as a fallback if an accelerated blit fails in a security- > critical path where data might leak if the blit is not properly > performed. For that purpose the bo is an unsuitable argument since > its relevant members might already have changed at call time. > > Finally, update the ttm_move_memcpy kerneldoc that seems to have > ended up with a stale version. > > Signed-off-by: Thomas Hellström Reviewed-by: Matthew Auld
[PATCH 0/6] Add support to the mmsys driver to be a reset controller
Dear all, The following patchset is a reimplementation of the patch sent by Jitao Shi [1] some time ago. As suggested by Chun-Kuang Hu, this time the reset is done using the reset API, where the mmsys driver is the reset controller and the mtk_dsi driver is the reset consumer. Note that the first patch is kind of unrelated change, it's just a cleanup but is needed if you want to apply all the following patches cleanly. This patchset is important in order to have the DSI panel working on some kukui MT8183 Chromebooks (i.e Lenovo IdeaPad Duet). Without it, you just get a black screen. Best regards, Enric [1] https://lore.kernel.org/linux-arm-kernel/20210420132614.150242-4-jitao@mediatek.com/ Enric Balletbo i Serra (6): arm64: dts: mediatek: Move reset controller constants into common location dt-bindings: mediatek: Add #reset-cells to mmsys system controller arm64: dts: mt8173: Add the mmsys reset bit to reset the dsi0 arm64: dts: mt8183: Add the mmsys reset bit to reset the dsi0 soc: mediatek: mmsys: Add reset controller support drm/mediatek: mtk_dsi: Reset the dsi0 hardware .../bindings/arm/mediatek/mediatek,mmsys.txt | 2 + arch/arm64/boot/dts/mediatek/mt8173.dtsi | 2 + arch/arm64/boot/dts/mediatek/mt8183.dtsi | 5 +- drivers/gpu/drm/mediatek/mtk_dsi.c| 5 +- drivers/soc/mediatek/mtk-mmsys.c | 69 +++ drivers/soc/mediatek/mtk-mmsys.h | 2 + .../mt2712-resets.h | 0 include/dt-bindings/reset/mt8173-resets.h | 2 + .../mt8183-resets.h | 3 + .../mt8192-resets.h | 0 10 files changed, 87 insertions(+), 3 deletions(-) rename include/dt-bindings/{reset-controller => reset}/mt2712-resets.h (100%) rename include/dt-bindings/{reset-controller => reset}/mt8183-resets.h (98%) rename include/dt-bindings/{reset-controller => reset}/mt8192-resets.h (100%) -- 2.30.2
[PATCH 6/6] drm/mediatek: mtk_dsi: Reset the dsi0 hardware
Reset dsi0 HW to default when power on. This prevents to have different settingbetween the bootloader and the kernel. As not all Mediatek boards have the reset consumer configured in their board description, also is not needed on all of them, the reset is optional, so the change is compatible with all boards. Cc: Jitao Shi Suggested-by: Chun-Kuang Hu Signed-off-by: Enric Balletbo i Serra --- drivers/gpu/drm/mediatek/mtk_dsi.c | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/mediatek/mtk_dsi.c b/drivers/gpu/drm/mediatek/mtk_dsi.c index ae403c67cbd9..d8b81e2ab841 100644 --- a/drivers/gpu/drm/mediatek/mtk_dsi.c +++ b/drivers/gpu/drm/mediatek/mtk_dsi.c @@ -11,6 +11,7 @@ #include #include #include +#include #include #include @@ -980,8 +981,10 @@ static int mtk_dsi_bind(struct device *dev, struct device *master, void *data) struct mtk_dsi *dsi = dev_get_drvdata(dev); ret = mtk_dsi_encoder_init(drm, dsi); + if (ret) + return ret; - return ret; + return device_reset_optional(dev); } static void mtk_dsi_unbind(struct device *dev, struct device *master, -- 2.30.2
[PATCH v6 0/4] drm: address potential UAF bugs with drm_master ptrs
This patch series addresses potential use-after-free errors when dereferencing pointers to struct drm_master. These were identified after one such bug was caught by Syzbot in drm_getunique(): https://syzkaller.appspot.com/bug?id=148d2f1dfac64af52ffd27b661981a540724f803 The series is broken up into four patches: 1. Move a call to drm_is_current_master() out from a section locked by &dev->mode_config.mutex in drm_mode_getconnector(). This patch does not apply to stable. 2. Move a call to _drm_lease_held() out from the section locked by &dev->mode_config.idr_mutex in __drm_mode_object_find(). 3. Implement a locked version of drm_is_current_master() function that's used within drm_auth.c. 4. Identify areas in drm_lease.c where pointers to struct drm_master are dereferenced, and ensure that the master pointers are not freed during use. Changes in v5 -> v6: - Patch 2: Add patch 2 to the series. This patch moves the call to _drm_lease_held out from the section locked by &dev->mode_config.idr_mutex in __drm_mode_object_find. - Patch 4: Clarify the kerneldoc for dereferencing drm_file.master, as suggested by Daniel Vetter. Refactor error paths with goto labels so that each function only has a single drm_master_put(), as suggested by Emil Velikov. Modify comparison to NULL into "!master", as suggested by the intel-gfx CI. Changes in v4 -> v5: - Patch 1: Add patch 1 to the series. The changes in patch 1 do not apply to stable because they apply to new changes in the drm-misc-next branch. This patch moves the call to drm_is_current_master in drm_mode_getconnector out from the section locked by &dev->mode_config.mutex. Additionally, added a missing semicolon to the patch, caught by the intel-gfx CI. - Patch 3: Move changes to drm_connector.c into patch 1. Changes in v3 -> v4: - Patch 3: Move the call to drm_is_current_master in drm_mode_getconnector out from the section locked by &dev->mode_config.mutex. As suggested by Daniel Vetter. This avoids a circular lock lock dependency as reported here https://patchwork.freedesktop.org/patch/440406/ Additionally, inside drm_is_current_master, instead of grabbing &fpriv->master->dev->master_mutex, we grab &fpriv->minor->dev->master_mutex to avoid dereferencing a null ptr if fpriv->master is not set. - Patch 4: Modify kerneldoc formatting. Additionally, add a file_priv->master NULL check inside drm_file_get_master, and handle the NULL result accordingly in drm_lease.c. As suggested by Daniel Vetter. Changes in v2 -> v3: - Patch 3: Move the definition of drm_is_current_master and the _locked version higher up in drm_auth.c to avoid needing a forward declaration of drm_is_current_master_locked. As suggested by Daniel Vetter. - Patch 4: Instead of leaking drm_device.master_mutex into drm_lease.c to protect drm_master pointers, add a new drm_file_get_master() function that returns drm_file->master while increasing its reference count, to prevent drm_file->master from being freed. As suggested by Daniel Vetter. Changes in v1 -> v2: - Patch 4: Move the lock and assignment before the DRM_DEBUG_LEASE in drm_mode_get_lease_ioctl, as suggested by Emil Velikov. Desmond Cheong Zhi Xi (4): drm: avoid circular locks in drm_mode_getconnector drm: avoid circular locks in __drm_mode_object_find drm: add a locked version of drm_is_current_master drm: protect drm_master pointers in drm_lease.c drivers/gpu/drm/drm_auth.c| 76 + drivers/gpu/drm/drm_connector.c | 5 +- drivers/gpu/drm/drm_lease.c | 81 +++ drivers/gpu/drm/drm_mode_object.c | 10 ++-- include/drm/drm_auth.h| 1 + include/drm/drm_file.h| 15 -- 6 files changed, 141 insertions(+), 47 deletions(-) -- 2.25.1
[PATCH v6 1/4] drm: avoid circular locks in drm_mode_getconnector
In preparation for a future patch to take a lock on drm_device.master_mutex inside drm_is_current_master(), we first move the call to drm_is_current_master() in drm_mode_getconnector out from the section locked by &dev->mode_config.mutex. This avoids creating a circular lock dependency. Failing to avoid this lock dependency produces the following lockdep splat: == WARNING: possible circular locking dependency detected 5.13.0-rc7-CI-CI_DRM_10254+ #1 Not tainted -- kms_frontbuffer/1087 is trying to acquire lock: 88810dcd01a8 (&dev->master_mutex){+.+.}-{3:3}, at: drm_is_current_master+0x1b/0x40 but task is already holding lock: 88810dcd0488 (&dev->mode_config.mutex){+.+.}-{3:3}, at: drm_mode_getconnector+0x1c6/0x4a0 which lock already depends on the new lock. the existing dependency chain (in reverse order) is: -> #2 (&dev->mode_config.mutex){+.+.}-{3:3}: __mutex_lock+0xab/0x970 drm_client_modeset_probe+0x22e/0xca0 __drm_fb_helper_initial_config_and_unlock+0x42/0x540 intel_fbdev_initial_config+0xf/0x20 [i915] async_run_entry_fn+0x28/0x130 process_one_work+0x26d/0x5c0 worker_thread+0x37/0x380 kthread+0x144/0x170 ret_from_fork+0x1f/0x30 -> #1 (&client->modeset_mutex){+.+.}-{3:3}: __mutex_lock+0xab/0x970 drm_client_modeset_commit_locked+0x1c/0x180 drm_client_modeset_commit+0x1c/0x40 __drm_fb_helper_restore_fbdev_mode_unlocked+0x88/0xb0 drm_fb_helper_set_par+0x34/0x40 intel_fbdev_set_par+0x11/0x40 [i915] fbcon_init+0x270/0x4f0 visual_init+0xc6/0x130 do_bind_con_driver+0x1e5/0x2d0 do_take_over_console+0x10e/0x180 do_fbcon_takeover+0x53/0xb0 register_framebuffer+0x22d/0x310 __drm_fb_helper_initial_config_and_unlock+0x36c/0x540 intel_fbdev_initial_config+0xf/0x20 [i915] async_run_entry_fn+0x28/0x130 process_one_work+0x26d/0x5c0 worker_thread+0x37/0x380 kthread+0x144/0x170 ret_from_fork+0x1f/0x30 -> #0 (&dev->master_mutex){+.+.}-{3:3}: __lock_acquire+0x151e/0x2590 lock_acquire+0xd1/0x3d0 __mutex_lock+0xab/0x970 drm_is_current_master+0x1b/0x40 drm_mode_getconnector+0x37e/0x4a0 drm_ioctl_kernel+0xa8/0xf0 drm_ioctl+0x1e8/0x390 __x64_sys_ioctl+0x6a/0xa0 do_syscall_64+0x39/0xb0 entry_SYSCALL_64_after_hwframe+0x44/0xae other info that might help us debug this: Chain exists of: &dev->master_mutex --> &client->modeset_mutex --> &dev->mode_config.mutex Possible unsafe locking scenario: CPU0CPU1 lock(&dev->mode_config.mutex); lock(&client->modeset_mutex); lock(&dev->mode_config.mutex); lock(&dev->master_mutex); *** DEADLOCK *** 1 lock held by kms_frontbuffer/1087: #0: 88810dcd0488 (&dev->mode_config.mutex){+.+.}-{3:3}, at: drm_mode_getconnector+0x1c6/0x4a0 stack backtrace: CPU: 7 PID: 1087 Comm: kms_frontbuffer Not tainted 5.13.0-rc7-CI-CI_DRM_10254+ #1 Hardware name: Intel Corporation Ice Lake Client Platform/IceLake U DDR4 SODIMM PD RVP TLC, BIOS ICLSFWR1.R00.3234.A01.1906141750 06/14/2019 Call Trace: dump_stack+0x7f/0xad check_noncircular+0x12e/0x150 __lock_acquire+0x151e/0x2590 lock_acquire+0xd1/0x3d0 __mutex_lock+0xab/0x970 drm_is_current_master+0x1b/0x40 drm_mode_getconnector+0x37e/0x4a0 drm_ioctl_kernel+0xa8/0xf0 drm_ioctl+0x1e8/0x390 __x64_sys_ioctl+0x6a/0xa0 do_syscall_64+0x39/0xb0 entry_SYSCALL_64_after_hwframe+0x44/0xae Reported-by: Daniel Vetter Signed-off-by: Desmond Cheong Zhi Xi Reviewed-by: Emil Velikov --- drivers/gpu/drm/drm_connector.c | 5 - 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index da39e7ff6965..2ba257b1ae20 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -2414,6 +2414,7 @@ int drm_mode_getconnector(struct drm_device *dev, void *data, struct drm_mode_modeinfo u_mode; struct drm_mode_modeinfo __user *mode_ptr; uint32_t __user *encoder_ptr; + bool is_current_master; if (!drm_core_check_feature(dev, DRIVER_MODESET)) return -EOPNOTSUPP; @@ -2444,9 +2445,11 @@ int drm_mode_getconnector(struct drm_device *dev, void *data, out_resp->connector_type = connector->connector_type; out_resp->connector_type_id = connector->connector_type_id; + is_current_master = drm_is_current_master(file_priv); + mutex_lock(&dev->mode_config.mutex); if (out_resp->count_modes == 0) { - if (drm_is_current_master(file_priv)) + if (is_current_master) connector->funcs->fill_modes(connector,
[PATCH v6 2/4] drm: avoid circular locks in __drm_mode_object_find
In a future patch, _drm_lease_held will dereference drm_file->master only after making a call to drm_file_get_master which increments the reference count of drm_file->master while holding a lock on drm_device.master_mutex. In preparation for this, the call to _drm_lease_held should be moved out from the section locked by &dev->mode_config.idr_mutex. This avoids inverting the lock hierarchy for &dev->master_mutex --> &dev->mode_config.idr_mutex Signed-off-by: Desmond Cheong Zhi Xi --- drivers/gpu/drm/drm_mode_object.c | 10 ++ 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/drm_mode_object.c b/drivers/gpu/drm/drm_mode_object.c index b26588b52795..63d35f1f98dd 100644 --- a/drivers/gpu/drm/drm_mode_object.c +++ b/drivers/gpu/drm/drm_mode_object.c @@ -146,16 +146,18 @@ struct drm_mode_object *__drm_mode_object_find(struct drm_device *dev, if (obj && obj->id != id) obj = NULL; - if (obj && drm_mode_object_lease_required(obj->type) && - !_drm_lease_held(file_priv, obj->id)) - obj = NULL; - if (obj && obj->free_cb) { if (!kref_get_unless_zero(&obj->refcount)) obj = NULL; } mutex_unlock(&dev->mode_config.idr_mutex); + if (obj && drm_mode_object_lease_required(obj->type) && + !_drm_lease_held(file_priv, obj->id)) { + drm_mode_object_put(obj); + obj = NULL; + } + return obj; } -- 2.25.1
[PATCH v6 3/4] drm: add a locked version of drm_is_current_master
While checking the master status of the DRM file in drm_is_current_master(), the device's master mutex should be held. Without the mutex, the pointer fpriv->master may be freed concurrently by another process calling drm_setmaster_ioctl(). This could lead to use-after-free errors when the pointer is subsequently dereferenced in drm_lease_owner(). The callers of drm_is_current_master() from drm_auth.c hold the device's master mutex, but external callers do not. Hence, we implement drm_is_current_master_locked() to be used within drm_auth.c, and modify drm_is_current_master() to grab the device's master mutex before checking the master status. Reported-by: Daniel Vetter Signed-off-by: Desmond Cheong Zhi Xi Reviewed-by: Emil Velikov --- drivers/gpu/drm/drm_auth.c | 51 -- 1 file changed, 32 insertions(+), 19 deletions(-) diff --git a/drivers/gpu/drm/drm_auth.c b/drivers/gpu/drm/drm_auth.c index f00e5abdbbf4..ab1863c5a5a0 100644 --- a/drivers/gpu/drm/drm_auth.c +++ b/drivers/gpu/drm/drm_auth.c @@ -61,6 +61,35 @@ * trusted clients. */ +static bool drm_is_current_master_locked(struct drm_file *fpriv) +{ + lockdep_assert_held_once(&fpriv->minor->dev->master_mutex); + + return fpriv->is_master && drm_lease_owner(fpriv->master) == fpriv->minor->dev->master; +} + +/** + * drm_is_current_master - checks whether @priv is the current master + * @fpriv: DRM file private + * + * Checks whether @fpriv is current master on its device. This decides whether a + * client is allowed to run DRM_MASTER IOCTLs. + * + * Most of the modern IOCTL which require DRM_MASTER are for kernel modesetting + * - the current master is assumed to own the non-shareable display hardware. + */ +bool drm_is_current_master(struct drm_file *fpriv) +{ + bool ret; + + mutex_lock(&fpriv->minor->dev->master_mutex); + ret = drm_is_current_master_locked(fpriv); + mutex_unlock(&fpriv->minor->dev->master_mutex); + + return ret; +} +EXPORT_SYMBOL(drm_is_current_master); + int drm_getmagic(struct drm_device *dev, void *data, struct drm_file *file_priv) { struct drm_auth *auth = data; @@ -223,7 +252,7 @@ int drm_setmaster_ioctl(struct drm_device *dev, void *data, if (ret) goto out_unlock; - if (drm_is_current_master(file_priv)) + if (drm_is_current_master_locked(file_priv)) goto out_unlock; if (dev->master) { @@ -272,7 +301,7 @@ int drm_dropmaster_ioctl(struct drm_device *dev, void *data, if (ret) goto out_unlock; - if (!drm_is_current_master(file_priv)) { + if (!drm_is_current_master_locked(file_priv)) { ret = -EINVAL; goto out_unlock; } @@ -321,7 +350,7 @@ void drm_master_release(struct drm_file *file_priv) if (file_priv->magic) idr_remove(&file_priv->master->magic_map, file_priv->magic); - if (!drm_is_current_master(file_priv)) + if (!drm_is_current_master_locked(file_priv)) goto out; drm_legacy_lock_master_cleanup(dev, master); @@ -342,22 +371,6 @@ void drm_master_release(struct drm_file *file_priv) mutex_unlock(&dev->master_mutex); } -/** - * drm_is_current_master - checks whether @priv is the current master - * @fpriv: DRM file private - * - * Checks whether @fpriv is current master on its device. This decides whether a - * client is allowed to run DRM_MASTER IOCTLs. - * - * Most of the modern IOCTL which require DRM_MASTER are for kernel modesetting - * - the current master is assumed to own the non-shareable display hardware. - */ -bool drm_is_current_master(struct drm_file *fpriv) -{ - return fpriv->is_master && drm_lease_owner(fpriv->master) == fpriv->minor->dev->master; -} -EXPORT_SYMBOL(drm_is_current_master); - /** * drm_master_get - reference a master pointer * @master: &struct drm_master -- 2.25.1
[PATCH v6 4/4] drm: protect drm_master pointers in drm_lease.c
Currently, direct copies of drm_file->master pointers should be protected by drm_device.master_mutex when being dereferenced. This is because drm_file->master is not invariant for the lifetime of drm_file. If drm_file is not the creator of master, then drm_file->is_master is false, and a call to drm_setmaster_ioctl will invoke drm_new_set_master, which then allocates a new master for drm_file and puts the old master. Thus, without holding drm_device.master_mutex, the old value of drm_file->master could be freed while it is being used by another concurrent process. In drm_lease.c, there are multiple instances where drm_file->master is accessed and dereferenced while drm_device.master_mutex is not held. This makes drm_lease.c vulnerable to use-after-free bugs. We address this issue in 3 ways: 1. Clarify in the kerneldoc that drm_file->master is protected by drm_device.master_mutex. 2. Add a new drm_file_get_master() function that calls drm_master_get on drm_file->master while holding on to drm_device.master_mutex. Since drm_master_get increments the reference count of master, this prevents master from being freed until we unreference it with drm_master_put. 3. In each case where drm_file->master is directly accessed and eventually dereferenced in drm_lease.c, we wrap the access in a call to the new drm_file_get_master function, then unreference the master pointer once we are done using it. Reported-by: Daniel Vetter Signed-off-by: Desmond Cheong Zhi Xi Reviewed-by: Emil Velikov --- drivers/gpu/drm/drm_auth.c | 25 drivers/gpu/drm/drm_lease.c | 81 - include/drm/drm_auth.h | 1 + include/drm/drm_file.h | 15 +-- 4 files changed, 99 insertions(+), 23 deletions(-) diff --git a/drivers/gpu/drm/drm_auth.c b/drivers/gpu/drm/drm_auth.c index ab1863c5a5a0..c36a0b72be26 100644 --- a/drivers/gpu/drm/drm_auth.c +++ b/drivers/gpu/drm/drm_auth.c @@ -384,6 +384,31 @@ struct drm_master *drm_master_get(struct drm_master *master) } EXPORT_SYMBOL(drm_master_get); +/** + * drm_file_get_master - reference &drm_file.master of @file_priv + * @file_priv: DRM file private + * + * Increments the reference count of @file_priv's &drm_file.master and returns + * the &drm_file.master. If @file_priv has no &drm_file.master, returns NULL. + * + * Master pointers returned from this function should be unreferenced using + * drm_master_put(). + */ +struct drm_master *drm_file_get_master(struct drm_file *file_priv) +{ + struct drm_master *master = NULL; + + mutex_lock(&file_priv->minor->dev->master_mutex); + if (!file_priv->master) + goto unlock; + master = drm_master_get(file_priv->master); + +unlock: + mutex_unlock(&file_priv->minor->dev->master_mutex); + return master; +} +EXPORT_SYMBOL(drm_file_get_master); + static void drm_master_destroy(struct kref *kref) { struct drm_master *master = container_of(kref, struct drm_master, refcount); diff --git a/drivers/gpu/drm/drm_lease.c b/drivers/gpu/drm/drm_lease.c index 00fb433bcef1..92eac73d9001 100644 --- a/drivers/gpu/drm/drm_lease.c +++ b/drivers/gpu/drm/drm_lease.c @@ -106,10 +106,19 @@ static bool _drm_has_leased(struct drm_master *master, int id) */ bool _drm_lease_held(struct drm_file *file_priv, int id) { - if (!file_priv || !file_priv->master) + bool ret; + struct drm_master *master; + + if (!file_priv) return true; - return _drm_lease_held_master(file_priv->master, id); + master = drm_file_get_master(file_priv); + if (!master) + return true; + ret = _drm_lease_held_master(master, id); + drm_master_put(&master); + + return ret; } /** @@ -128,13 +137,22 @@ bool drm_lease_held(struct drm_file *file_priv, int id) struct drm_master *master; bool ret; - if (!file_priv || !file_priv->master || !file_priv->master->lessor) + if (!file_priv) return true; - master = file_priv->master; + master = drm_file_get_master(file_priv); + if (!master) + return true; + if (!master->lessor) { + ret = true; + goto out; + } mutex_lock(&master->dev->mode_config.idr_mutex); ret = _drm_lease_held_master(master, id); mutex_unlock(&master->dev->mode_config.idr_mutex); + +out: + drm_master_put(&master); return ret; } @@ -154,10 +172,16 @@ uint32_t drm_lease_filter_crtcs(struct drm_file *file_priv, uint32_t crtcs_in) int count_in, count_out; uint32_t crtcs_out = 0; - if (!file_priv || !file_priv->master || !file_priv->master->lessor) + if (!file_priv) return crtcs_in; - master = file_priv->master; + master = drm_file_get_master(file_priv); + if (!master) + return crtcs_in; + if (!master->lessor) { + crtcs_out = crtcs_in;
Re: [PATCH v6 15/16] drm/panfrost: Queue jobs on the hardware
On 30/06/2021 07:27, Boris Brezillon wrote: > From: Steven Price > > The hardware has a set of '_NEXT' registers that can hold a second job > while the first is executing. Make use of these registers to enqueue a > second job per slot. > > v5: > * Fix a comment in panfrost_job_init() > > v3: > * Fix the done/err job dequeuing logic to get a valid active state > * Only enable the second slot on GPUs supporting jobchain disambiguation > * Split interrupt handling in sub-functions > > Signed-off-by: Steven Price > Signed-off-by: Boris Brezillon FWIW (it has changed a bit since my original version): Reviewed-by: Steven Price > --- > drivers/gpu/drm/panfrost/panfrost_device.h | 2 +- > drivers/gpu/drm/panfrost/panfrost_job.c| 467 +++-- > 2 files changed, 351 insertions(+), 118 deletions(-) > > diff --git a/drivers/gpu/drm/panfrost/panfrost_device.h > b/drivers/gpu/drm/panfrost/panfrost_device.h > index 193cd87f643c..8b25278f34c8 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_device.h > +++ b/drivers/gpu/drm/panfrost/panfrost_device.h > @@ -102,7 +102,7 @@ struct panfrost_device { > > struct panfrost_job_slot *js; > > - struct panfrost_job *jobs[NUM_JOB_SLOTS]; > + struct panfrost_job *jobs[NUM_JOB_SLOTS][2]; > struct list_head scheduled_jobs; > > struct panfrost_perfcnt *perfcnt; > diff --git a/drivers/gpu/drm/panfrost/panfrost_job.c > b/drivers/gpu/drm/panfrost/panfrost_job.c > index 8a0db9571bfd..71a72fb50e6b 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_job.c > +++ b/drivers/gpu/drm/panfrost/panfrost_job.c > @@ -4,6 +4,7 @@ > #include > #include > #include > +#include > #include > #include > #include > @@ -140,9 +141,52 @@ static void panfrost_job_write_affinity(struct > panfrost_device *pfdev, > job_write(pfdev, JS_AFFINITY_NEXT_HI(js), affinity >> 32); > } > > +static u32 > +panfrost_get_job_chain_flag(const struct panfrost_job *job) > +{ > + struct panfrost_fence *f = to_panfrost_fence(job->done_fence); > + > + if (!panfrost_has_hw_feature(job->pfdev, > HW_FEATURE_JOBCHAIN_DISAMBIGUATION)) > + return 0; > + > + return (f->seqno & 1) ? JS_CONFIG_JOB_CHAIN_FLAG : 0; > +} > + > +static struct panfrost_job * > +panfrost_dequeue_job(struct panfrost_device *pfdev, int slot) > +{ > + struct panfrost_job *job = pfdev->jobs[slot][0]; > + > + WARN_ON(!job); > + pfdev->jobs[slot][0] = pfdev->jobs[slot][1]; > + pfdev->jobs[slot][1] = NULL; > + > + return job; > +} > + > +static unsigned int > +panfrost_enqueue_job(struct panfrost_device *pfdev, int slot, > + struct panfrost_job *job) > +{ > + if (WARN_ON(!job)) > + return 0; > + > + if (!pfdev->jobs[slot][0]) { > + pfdev->jobs[slot][0] = job; > + return 0; > + } > + > + WARN_ON(pfdev->jobs[slot][1]); > + pfdev->jobs[slot][1] = job; > + WARN_ON(panfrost_get_job_chain_flag(job) == > + panfrost_get_job_chain_flag(pfdev->jobs[slot][0])); > + return 1; > +} > + > static void panfrost_job_hw_submit(struct panfrost_job *job, int js) > { > struct panfrost_device *pfdev = job->pfdev; > + unsigned int subslot; > u32 cfg; > u64 jc_head = job->jc; > int ret; > @@ -168,7 +212,8 @@ static void panfrost_job_hw_submit(struct panfrost_job > *job, int js) >* start */ > cfg |= JS_CONFIG_THREAD_PRI(8) | > JS_CONFIG_START_FLUSH_CLEAN_INVALIDATE | > - JS_CONFIG_END_FLUSH_CLEAN_INVALIDATE; > + JS_CONFIG_END_FLUSH_CLEAN_INVALIDATE | > + panfrost_get_job_chain_flag(job); > > if (panfrost_has_hw_feature(pfdev, HW_FEATURE_FLUSH_REDUCTION)) > cfg |= JS_CONFIG_ENABLE_FLUSH_REDUCTION; > @@ -182,10 +227,17 @@ static void panfrost_job_hw_submit(struct panfrost_job > *job, int js) > job_write(pfdev, JS_FLUSH_ID_NEXT(js), job->flush_id); > > /* GO ! */ > - dev_dbg(pfdev->dev, "JS: Submitting atom %p to js[%d] with head=0x%llx", > - job, js, jc_head); > > - job_write(pfdev, JS_COMMAND_NEXT(js), JS_COMMAND_START); > + spin_lock(&pfdev->js->job_lock); > + subslot = panfrost_enqueue_job(pfdev, js, job); > + /* Don't queue the job if a reset is in progress */ > + if (!atomic_read(&pfdev->reset.pending)) { > + job_write(pfdev, JS_COMMAND_NEXT(js), JS_COMMAND_START); > + dev_dbg(pfdev->dev, > + "JS: Submitting atom %p to js[%d][%d] with head=0x%llx > AS %d", > + job, js, subslot, jc_head, cfg & 0xf); > + } > + spin_unlock(&pfdev->js->job_lock); > } > > static int panfrost_acquire_object_fences(struct drm_gem_object **bos, > @@ -332,7 +384,11 @@ static struct dma_fence *panfrost_job_run(struct > drm_sched_job *sched_job) > if (unlikely(job->base.s_fence->finished.error)) > return NULL; >
Re: [PATCH v6 16/16] drm/panfrost: Increase the AS_ACTIVE polling timeout
On 30/06/2021 07:27, Boris Brezillon wrote: > Experience has shown that 1ms is sometimes not enough, even when the GPU > is running at its maximum frequency, not to mention that an MMU operation > might take longer if the GPU is running at a lower frequency, which is > likely to be the case if devfreq is active. > > Let's pick a significantly bigger timeout value (1ms -> 100ms) to be on > the safe side. > > v5: > * New patch > > Signed-off-by: Boris Brezillon Reviewed-by: Steven Price > --- > drivers/gpu/drm/panfrost/panfrost_mmu.c | 2 +- > 1 file changed, 1 insertion(+), 1 deletion(-) > > diff --git a/drivers/gpu/drm/panfrost/panfrost_mmu.c > b/drivers/gpu/drm/panfrost/panfrost_mmu.c > index e0356e68e768..0da5b3100ab1 100644 > --- a/drivers/gpu/drm/panfrost/panfrost_mmu.c > +++ b/drivers/gpu/drm/panfrost/panfrost_mmu.c > @@ -34,7 +34,7 @@ static int wait_ready(struct panfrost_device *pfdev, u32 > as_nr) > /* Wait for the MMU status to indicate there is no active command, in >* case one is pending. */ > ret = readl_relaxed_poll_timeout_atomic(pfdev->iomem + AS_STATUS(as_nr), > - val, !(val & AS_STATUS_AS_ACTIVE), 10, 1000); > + val, !(val & AS_STATUS_AS_ACTIVE), 10, 10); > > if (ret) { > /* The GPU hung, let's trigger a reset */ >
[PATCH v5 00/17] New uAPI drm properties for color management
Implementation of https://lkml.org/lkml/2021/5/12/764 now feature complete albeit not fully tested. I have now corrected the DSC behavior, but still no wait to test it. Exact dithering behavior remains a mistery so in case dithering is active it's not 100% clear what "active bpc" means, or where the "max bpc" limit is applied. I have no DP MST splitter at hand. I tried my best to not break anything, but if one who has one could test it would be very helpful. Things on my TODO list: - add "min bpc" property - rewrite "preferred color format" to "force color format" - make "Broadcast RGB" only affect RGB on AMD too - remove unreachable enums of "active/preferred/force color format"
[PATCH v5 04/17] drm/amd/display: Add handling for new "active bpc" property
This commit implements the "active bpc" drm property for the AMD GPU driver. Signed-off-by: Werner Sembach --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 24 ++- .../display/amdgpu_dm/amdgpu_dm_mst_types.c | 4 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index f4abb5f215d1..d984de82ae63 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -7708,8 +7708,10 @@ void amdgpu_dm_connector_init_helper(struct amdgpu_display_manager *dm, adev->mode_info.underscan_vborder_property, 0); - if (!aconnector->mst_port) + if (!aconnector->mst_port) { drm_connector_attach_max_bpc_property(&aconnector->base, 8, 16); + drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + } /* This defaults to the max in the range, but we want 8bpc for non-edp. */ aconnector->base.state->max_bpc = (connector_type == DRM_MODE_CONNECTOR_eDP) ? 16 : 8; @@ -9078,6 +9080,26 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) mutex_unlock(&dm->dc_lock); } + /* Extract information from crtc to communicate it to userspace as connector properties */ + for_each_new_connector_in_state(state, connector, new_con_state, i) { + struct drm_crtc *crtc = new_con_state->crtc; + struct dc_stream_state *stream; + + if (crtc) { + new_crtc_state = drm_atomic_get_new_crtc_state(state, crtc); + dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); + stream = dm_new_crtc_state->stream; + + if (stream) + drm_connector_set_active_bpc_property(connector, + stream->timing.flags.DSC ? + stream->timing.dsc_cfg.bits_per_pixel / 16 / 3 : + convert_dc_color_depth_into_bpc( + stream->timing.display_color_depth)); + } else + drm_connector_set_active_bpc_property(connector, 0); + } + /* Count number of newly disabled CRTCs for dropping PM refs later. */ for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index 5568d4e518e6..0cf38743ec47 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -409,6 +409,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, if (connector->max_bpc_property) drm_connector_attach_max_bpc_property(connector, 8, 16); + connector->active_bpc_property = master->base.active_bpc_property; + if (connector->active_bpc_property) + drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + connector->vrr_capable_property = master->base.vrr_capable_property; if (connector->vrr_capable_property) drm_connector_attach_vrr_capable_property(connector); -- 2.25.1
[PATCH v5 01/17] drm/amd/display: Remove unnecessary SIGNAL_TYPE_HDMI_TYPE_A check
Remove unnecessary SIGNAL_TYPE_HDMI_TYPE_A check that was performed in the drm_mode_is_420_only() case, but not in the drm_mode_is_420_also() && force_yuv420_output case. Without further knowledge if YCbCr 4:2:0 is supported outside of HDMI, there is no reason to use RGB when the display reports drm_mode_is_420_only() even on a non HDMI connection. This patch also moves both checks in the same if-case. This eliminates an extra else-if-case. Signed-off-by: Werner Sembach --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 5 + 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 10f878910e55..e081dd3ffb5f 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -5348,10 +5348,7 @@ static void fill_stream_properties_from_drm_display_mode( timing_out->v_border_bottom = 0; /* TODO: un-hardcode */ if (drm_mode_is_420_only(info, mode_in) - && stream->signal == SIGNAL_TYPE_HDMI_TYPE_A) - timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420; - else if (drm_mode_is_420_also(info, mode_in) - && aconnector->force_yuv420_output) + || (drm_mode_is_420_also(info, mode_in) && aconnector->force_yuv420_output)) timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420; else if ((connector->display_info.color_formats & DRM_COLOR_FORMAT_YCRCB444) && stream->signal == SIGNAL_TYPE_HDMI_TYPE_A) -- 2.25.1
[PATCH v5 02/17] drm/amd/display: Add missing cases convert_dc_color_depth_into_bpc
convert_dc_color_depth_into_bpc() that converts the enum dc_color_depth to an integer had the casses for COLOR_DEPTH_999 and COLOR_DEPTH_11 missing. Signed-off-by: Werner Sembach --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 4 1 file changed, 4 insertions(+) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index e081dd3ffb5f..f4abb5f215d1 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6700,6 +6700,10 @@ static int convert_dc_color_depth_into_bpc (enum dc_color_depth display_color_de return 14; case COLOR_DEPTH_161616: return 16; + case COLOR_DEPTH_999: + return 9; + case COLOR_DEPTH_11: + return 11; default: break; } -- 2.25.1
[PATCH v5 06/17] drm/uAPI: Add "active color format" drm property as feedback for userspace
Add a new general drm property "active color format" which can be used by graphic drivers to report the used color format back to userspace. There was no way to check which color format got actually used on a given monitor. To surely predict this, one must know the exact capabilities of the monitor, the GPU, and the connection used and what the default behaviour of the used driver is (e.g. amdgpu prefers YCbCr 4:4:4 while i915 prefers RGB). This property helps eliminating the guessing on this point. In the future, automatic color calibration for screens might also depend on this information being available. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_connector.c | 63 + include/drm/drm_connector.h | 9 + 2 files changed, 72 insertions(+) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index 6461d00e8e49..075bdc08d5c3 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -889,6 +889,14 @@ static const struct drm_prop_enum_list drm_dp_subconnector_enum_list[] = { { DRM_MODE_SUBCONNECTOR_Native, "Native"}, /* DP */ }; +static const struct drm_prop_enum_list drm_active_color_format_enum_list[] = { + { 0, "not applicable" }, + { DRM_COLOR_FORMAT_RGB444, "rgb" }, + { DRM_COLOR_FORMAT_YCRCB444, "ycbcr444" }, + { DRM_COLOR_FORMAT_YCRCB422, "ycbcr422" }, + { DRM_COLOR_FORMAT_YCRCB420, "ycbcr420" }, +}; + DRM_ENUM_NAME_FN(drm_get_dp_subconnector_name, drm_dp_subconnector_enum_list) @@ -1206,6 +1214,15 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { * Drivers shall use drm_connector_attach_active_bpc_property() to install * this property. A value of 0 means "not applicable". * + * active color format: + * This read-only property tells userspace the color format actually used + * by the hardware display engine "on the cable" on a connector. The chosen + * value depends on hardware capabilities, both display engine and + * connected monitor. Drivers shall use + * drm_connector_attach_active_color_format_property() to install this + * property. Possible values are "not applicable", "rgb", "ycbcr444", + * "ycbcr422", and "ycbcr420". + * * Connectors also have one standardized atomic property: * * CRTC_ID: @@ -2205,6 +,52 @@ void drm_connector_set_active_bpc_property(struct drm_connector *connector, int } EXPORT_SYMBOL(drm_connector_set_active_bpc_property); +/** + * drm_connector_attach_active_color_format_property - attach "active color format" property + * @connector: connector to attach active color format property on. + * + * This is used to check the applied color format on a connector. + * + * Returns: + * Zero on success, negative errno on failure. + */ +int drm_connector_attach_active_color_format_property(struct drm_connector *connector) +{ + struct drm_device *dev = connector->dev; + struct drm_property *prop; + + if (!connector->active_color_format_property) { + prop = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE, "active color format", + drm_active_color_format_enum_list, + ARRAY_SIZE(drm_active_color_format_enum_list)); + if (!prop) + return -ENOMEM; + + connector->active_color_format_property = prop; + } + + drm_object_attach_property(&connector->base, prop, 0); + + return 0; +} +EXPORT_SYMBOL(drm_connector_attach_active_color_format_property); + +/** + * drm_connector_set_active_color_format_property - sets the active color format property for a + * connector + * @connector: drm connector + * @active_color_format: color format for the connector currently active "on the cable" + * + * Should be used by atomic drivers to update the active color format over a connector. + */ +void drm_connector_set_active_color_format_property(struct drm_connector *connector, + u32 active_color_format) +{ + drm_object_property_set_value(&connector->base, connector->active_color_format_property, + active_color_format); +} +EXPORT_SYMBOL(drm_connector_set_active_color_format_property); + /** * drm_connector_attach_hdr_output_metadata_property - attach "HDR_OUTPUT_METADA" property * @connector: connector to attach the property on. diff --git a/include/drm/drm_connector.h b/include/drm/drm_connector.h index eee86de62a5f..8a5197f14e87 100644 --- a/include/drm/drm_connector.h +++ b/include/drm/drm_connector.h @@ -1386,6 +1386,12 @@ struct drm_connector { */ struct drm_property *active_bpc_property; + /** +* @active_color_format_property: Default connector property for the +* active color format to be driven out of the connector.
[PATCH v5 05/17] drm/i915/display: Add handling for new "active bpc" property
This commit implements the "active bpc" drm property for the Intel GPU driver. Signed-off-by: Werner Sembach --- drivers/gpu/drm/i915/display/intel_display.c | 19 +++ drivers/gpu/drm/i915/display/intel_dp.c | 7 +-- drivers/gpu/drm/i915/display/intel_dp_mst.c | 5 + drivers/gpu/drm/i915/display/intel_hdmi.c| 4 +++- 4 files changed, 32 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c index 6be1b31af07b..1b63d1404d06 100644 --- a/drivers/gpu/drm/i915/display/intel_display.c +++ b/drivers/gpu/drm/i915/display/intel_display.c @@ -10839,6 +10839,9 @@ static int intel_atomic_commit(struct drm_device *dev, { struct intel_atomic_state *state = to_intel_atomic_state(_state); struct drm_i915_private *dev_priv = to_i915(dev); + struct drm_connector *connector; + struct drm_connector_state *new_conn_state; + int i; int ret = 0; state->wakeref = intel_runtime_pm_get(&dev_priv->runtime_pm); @@ -10907,6 +10910,22 @@ static int intel_atomic_commit(struct drm_device *dev, intel_shared_dpll_swap_state(state); intel_atomic_track_fbs(state); + /* Extract information from crtc to communicate it to userspace as connector properties */ + for_each_new_connector_in_state(&state->base, connector, new_conn_state, i) { + struct intel_crtc *crtc = to_intel_crtc(new_conn_state->crtc); + + if (crtc) { + struct intel_crtc_state *new_crtc_state = + intel_atomic_get_new_crtc_state(state, crtc); + + drm_connector_set_active_bpc_property(connector, + new_crtc_state->dsc.compression_enable ? + new_crtc_state->dsc.compressed_bpp / 3 : + new_crtc_state->pipe_bpp / 3); + } else + drm_connector_set_active_bpc_property(connector, 0); + } + drm_atomic_state_get(&state->base); INIT_WORK(&state->base.commit_work, intel_atomic_commit_work); diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c index 6cc03b9e4321..815bc313b954 100644 --- a/drivers/gpu/drm/i915/display/intel_dp.c +++ b/drivers/gpu/drm/i915/display/intel_dp.c @@ -4688,10 +4688,13 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connect intel_attach_force_audio_property(connector); intel_attach_broadcast_rgb_property(connector); - if (HAS_GMCH(dev_priv)) + if (HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 6, 10); - else if (DISPLAY_VER(dev_priv) >= 5) + drm_connector_attach_active_bpc_property(connector, 6, 10); + } else if (DISPLAY_VER(dev_priv) >= 5) { drm_connector_attach_max_bpc_property(connector, 6, 12); + drm_connector_attach_active_bpc_property(connector, 6, 12); + } /* Register HDMI colorspace for case of lspcon */ if (intel_bios_is_lspcon_present(dev_priv, port)) { diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.c b/drivers/gpu/drm/i915/display/intel_dp_mst.c index b170e272bdee..16bfc59570a5 100644 --- a/drivers/gpu/drm/i915/display/intel_dp_mst.c +++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c @@ -851,6 +851,11 @@ static struct drm_connector *intel_dp_add_mst_connector(struct drm_dp_mst_topolo if (connector->max_bpc_property) drm_connector_attach_max_bpc_property(connector, 6, 12); + connector->active_bpc_property = + intel_dp->attached_connector->base.active_bpc_property; + if (connector->active_bpc_property) + drm_connector_attach_active_bpc_property(connector, 6, 12); + return connector; err: diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 7e51c98c475e..9160e21ac9d6 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2513,8 +2513,10 @@ intel_hdmi_add_properties(struct intel_hdmi *intel_hdmi, struct drm_connector *c if (DISPLAY_VER(dev_priv) >= 10) drm_connector_attach_hdr_output_metadata_property(connector); - if (!HAS_GMCH(dev_priv)) + if (!HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 8, 12); + drm_connector_attach_active_bpc_property(connector, 8, 12); + } } /* -- 2.25.1
[PATCH v5 03/17] drm/uAPI: Add "active bpc" as feedback channel for "max bpc" drm property
Add a new general drm property "active bpc" which can be used by graphic drivers to report the applied bit depth per pixel color back to userspace. While "max bpc" can be used to change the color depth, there was no way to check which one actually got used. While in theory the driver chooses the best/highest color depth within the max bpc setting a user might not be fully aware what his hardware is or isn't capable off. This is meant as a quick way to double check the setup. In the future, automatic color calibration for screens might also depend on this information being available. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_connector.c | 53 + include/drm/drm_connector.h | 8 + 2 files changed, 61 insertions(+) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index da39e7ff6965..6461d00e8e49 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -1197,6 +1197,15 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { * drm_connector_attach_max_bpc_property() to create and attach the * property to the connector during initialization. * + * active bpc: + * This read-only range property tells userspace the pixel color bit depth + * actually used by the hardware display engine "on the cable" on a + * connector. This means after display stream compression and dithering + * done by the GPU. The chosen value depends on hardware capabilities, both + * display engine and connected monitor, and the "max bpc" property. + * Drivers shall use drm_connector_attach_active_bpc_property() to install + * this property. A value of 0 means "not applicable". + * * Connectors also have one standardized atomic property: * * CRTC_ID: @@ -2152,6 +2161,50 @@ int drm_connector_attach_max_bpc_property(struct drm_connector *connector, } EXPORT_SYMBOL(drm_connector_attach_max_bpc_property); +/** + * drm_connector_attach_active_bpc_property - attach "active bpc" property + * @connector: connector to attach active bpc property on. + * @min: The minimum bit depth supported by the connector. + * @max: The maximum bit depth supported by the connector. + * + * This is used to check the applied bit depth on a connector. + * + * Returns: + * Zero on success, negative errno on failure. + */ +int drm_connector_attach_active_bpc_property(struct drm_connector *connector, int min, int max) +{ + struct drm_device *dev = connector->dev; + struct drm_property *prop; + + if (!connector->active_bpc_property) { + prop = drm_property_create_range(dev, DRM_MODE_PROP_IMMUTABLE, "active bpc", +min, max); + if (!prop) + return -ENOMEM; + + connector->active_bpc_property = prop; + } + + drm_object_attach_property(&connector->base, prop, 0); + + return 0; +} +EXPORT_SYMBOL(drm_connector_attach_active_bpc_property); + +/** + * drm_connector_set_active_bpc_property - sets the active bits per color property for a connector + * @connector: drm connector + * @active_bpc: bits per color for the connector currently active "on the cable" + * + * Should be used by atomic drivers to update the active bits per color over a connector. + */ +void drm_connector_set_active_bpc_property(struct drm_connector *connector, int active_bpc) +{ + drm_object_property_set_value(&connector->base, connector->active_bpc_property, active_bpc); +} +EXPORT_SYMBOL(drm_connector_set_active_bpc_property); + /** * drm_connector_attach_hdr_output_metadata_property - attach "HDR_OUTPUT_METADA" property * @connector: connector to attach the property on. diff --git a/include/drm/drm_connector.h b/include/drm/drm_connector.h index 714d1a01c065..eee86de62a5f 100644 --- a/include/drm/drm_connector.h +++ b/include/drm/drm_connector.h @@ -1380,6 +1380,12 @@ struct drm_connector { */ struct drm_property *max_bpc_property; + /** +* @active_bpc_property: Default connector property for the active bpc +* to be driven out of the connector. +*/ + struct drm_property *active_bpc_property; + #define DRM_CONNECTOR_POLL_HPD (1 << 0) #define DRM_CONNECTOR_POLL_CONNECT (1 << 1) #define DRM_CONNECTOR_POLL_DISCONNECT (1 << 2) @@ -1702,6 +1708,8 @@ int drm_connector_set_panel_orientation_with_quirk( int width, int height); int drm_connector_attach_max_bpc_property(struct drm_connector *connector, int min, int max); +int drm_connector_attach_active_bpc_property(struct drm_connector *connector, int min, int max); +void drm_connector_set_active_bpc_property(struct drm_connector *connector, int active_bpc); /** * struct drm_tile_group - Tile group metadata -- 2.25.1
[PATCH v5 13/17] drm/amd/display: Add handling for new "preferred color format" property
This commit implements the "preferred color format" drm property for the AMD GPU driver. Signed-off-by: Werner Sembach --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 30 +++ .../display/amdgpu_dm/amdgpu_dm_mst_types.c | 4 +++ 2 files changed, 28 insertions(+), 6 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index b4acedac1ac9..02a5809d4993 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -5346,15 +5346,32 @@ static void fill_stream_properties_from_drm_display_mode( timing_out->h_border_right = 0; timing_out->v_border_top = 0; timing_out->v_border_bottom = 0; - /* TODO: un-hardcode */ - if (drm_mode_is_420_only(info, mode_in) - || (drm_mode_is_420_also(info, mode_in) && aconnector->force_yuv420_output)) + + if (connector_state + && (connector_state->preferred_color_format == DRM_COLOR_FORMAT_YCRCB420 + || aconnector->force_yuv420_output) && drm_mode_is_420(info, mode_in)) timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420; - else if ((connector->display_info.color_formats & DRM_COLOR_FORMAT_YCRCB444) - && stream->signal == SIGNAL_TYPE_HDMI_TYPE_A) + else if (connector_state + && connector_state->preferred_color_format == DRM_COLOR_FORMAT_YCRCB444 + && connector->display_info.color_formats & DRM_COLOR_FORMAT_YCRCB444) timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR444; - else + else if (connector_state + && connector_state->preferred_color_format == DRM_COLOR_FORMAT_RGB444 + && !drm_mode_is_420_only(info, mode_in)) timing_out->pixel_encoding = PIXEL_ENCODING_RGB; + else + /* +* connector_state->preferred_color_format not possible +* || connector_state->preferred_color_format == 0 (auto) +* || connector_state->preferred_color_format == DRM_COLOR_FORMAT_YCRCB422 +*/ + if (drm_mode_is_420_only(info, mode_in)) + timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR420; + else if ((connector->display_info.color_formats & DRM_COLOR_FORMAT_YCRCB444) + && stream->signal == SIGNAL_TYPE_HDMI_TYPE_A) + timing_out->pixel_encoding = PIXEL_ENCODING_YCBCR444; + else + timing_out->pixel_encoding = PIXEL_ENCODING_RGB; timing_out->timing_3d_format = TIMING_3D_FORMAT_NONE; timing_out->display_color_depth = convert_color_depth_from_display_info( @@ -7756,6 +7773,7 @@ void amdgpu_dm_connector_init_helper(struct amdgpu_display_manager *dm, if (!aconnector->mst_port) { drm_connector_attach_max_bpc_property(&aconnector->base, 8, 16); drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + drm_connector_attach_preferred_color_format_property(&aconnector->base); drm_connector_attach_active_color_format_property(&aconnector->base); drm_connector_attach_active_color_range_property(&aconnector->base); } diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index b5d57bbbdd20..2563788ba95a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -413,6 +413,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, if (connector->active_bpc_property) drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + connector->preferred_color_format_property = master->base.preferred_color_format_property; + if (connector->preferred_color_format_property) + drm_connector_attach_preferred_color_format_property(&aconnector->base); + connector->active_color_format_property = master->base.active_color_format_property; if (connector->active_color_format_property) drm_connector_attach_active_color_format_property(&aconnector->base); -- 2.25.1
[PATCH v5 07/17] drm/amd/display: Add handling for new "active color format" property
This commit implements the "active color format" drm property for the AMD GPU driver. Signed-off-by: Werner Sembach --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 29 +-- .../display/amdgpu_dm/amdgpu_dm_mst_types.c | 4 +++ 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index d984de82ae63..098f3d53e681 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6710,6 +6710,24 @@ static int convert_dc_color_depth_into_bpc (enum dc_color_depth display_color_de return 0; } +static int convert_dc_pixel_encoding_into_drm_color_format( + enum dc_pixel_encoding display_pixel_encoding) +{ + switch (display_pixel_encoding) { + case PIXEL_ENCODING_RGB: + return DRM_COLOR_FORMAT_RGB444; + case PIXEL_ENCODING_YCBCR422: + return DRM_COLOR_FORMAT_YCRCB422; + case PIXEL_ENCODING_YCBCR444: + return DRM_COLOR_FORMAT_YCRCB444; + case PIXEL_ENCODING_YCBCR420: + return DRM_COLOR_FORMAT_YCRCB420; + default: + break; + } + return 0; +} + static int dm_encoder_helper_atomic_check(struct drm_encoder *encoder, struct drm_crtc_state *crtc_state, struct drm_connector_state *conn_state) @@ -7711,6 +7729,7 @@ void amdgpu_dm_connector_init_helper(struct amdgpu_display_manager *dm, if (!aconnector->mst_port) { drm_connector_attach_max_bpc_property(&aconnector->base, 8, 16); drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + drm_connector_attach_active_color_format_property(&aconnector->base); } /* This defaults to the max in the range, but we want 8bpc for non-edp. */ @@ -9090,14 +9109,20 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); stream = dm_new_crtc_state->stream; - if (stream) + if (stream) { drm_connector_set_active_bpc_property(connector, stream->timing.flags.DSC ? stream->timing.dsc_cfg.bits_per_pixel / 16 / 3 : convert_dc_color_depth_into_bpc( stream->timing.display_color_depth)); - } else + drm_connector_set_active_color_format_property(connector, + convert_dc_pixel_encoding_into_drm_color_format( + dm_new_crtc_state->stream->timing.pixel_encoding)); + } + } else { drm_connector_set_active_bpc_property(connector, 0); + drm_connector_set_active_color_format_property(connector, 0); + } } /* Count number of newly disabled CRTCs for dropping PM refs later. */ diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index 0cf38743ec47..13151d13aa73 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -413,6 +413,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, if (connector->active_bpc_property) drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); + connector->active_color_format_property = master->base.active_color_format_property; + if (connector->active_color_format_property) + drm_connector_attach_active_color_format_property(&aconnector->base); + connector->vrr_capable_property = master->base.vrr_capable_property; if (connector->vrr_capable_property) drm_connector_attach_vrr_capable_property(connector); -- 2.25.1
[PATCH v5 08/17] drm/i915/display: Add handling for new "active color format" property
This commit implements the "active color format" drm property for the Intel GPU driver. Signed-off-by: Werner Sembach --- drivers/gpu/drm/i915/display/intel_display.c | 22 +++- drivers/gpu/drm/i915/display/intel_dp.c | 2 ++ drivers/gpu/drm/i915/display/intel_dp_mst.c | 5 + drivers/gpu/drm/i915/display/intel_hdmi.c| 1 + 4 files changed, 29 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c index 1b63d1404d06..be38f7148285 100644 --- a/drivers/gpu/drm/i915/display/intel_display.c +++ b/drivers/gpu/drm/i915/display/intel_display.c @@ -10609,6 +10609,21 @@ static void intel_atomic_prepare_plane_clear_colors(struct intel_atomic_state *s } } +static int convert_intel_output_format_into_drm_color_format(enum intel_output_format output_format) +{ + switch (output_format) { + case INTEL_OUTPUT_FORMAT_RGB: + return DRM_COLOR_FORMAT_RGB444; + case INTEL_OUTPUT_FORMAT_YCBCR420: + return DRM_COLOR_FORMAT_YCRCB420; + case INTEL_OUTPUT_FORMAT_YCBCR444: + return DRM_COLOR_FORMAT_YCRCB444; + default: + break; + } + return 0; +} + static void intel_atomic_commit_tail(struct intel_atomic_state *state) { struct drm_device *dev = state->base.dev; @@ -10922,8 +10937,13 @@ static int intel_atomic_commit(struct drm_device *dev, new_crtc_state->dsc.compression_enable ? new_crtc_state->dsc.compressed_bpp / 3 : new_crtc_state->pipe_bpp / 3); - } else + drm_connector_set_active_color_format_property(connector, + convert_intel_output_format_into_drm_color_format( + new_crtc_state->output_format)); + } else { drm_connector_set_active_bpc_property(connector, 0); + drm_connector_set_active_color_format_property(connector, 0); + } } drm_atomic_state_get(&state->base); diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c index 815bc313b954..6b85bcdeb238 100644 --- a/drivers/gpu/drm/i915/display/intel_dp.c +++ b/drivers/gpu/drm/i915/display/intel_dp.c @@ -4691,9 +4691,11 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connect if (HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 6, 10); drm_connector_attach_active_bpc_property(connector, 6, 10); + drm_connector_attach_active_color_format_property(connector); } else if (DISPLAY_VER(dev_priv) >= 5) { drm_connector_attach_max_bpc_property(connector, 6, 12); drm_connector_attach_active_bpc_property(connector, 6, 12); + drm_connector_attach_active_color_format_property(connector); } /* Register HDMI colorspace for case of lspcon */ diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.c b/drivers/gpu/drm/i915/display/intel_dp_mst.c index 16bfc59570a5..3e4237df3360 100644 --- a/drivers/gpu/drm/i915/display/intel_dp_mst.c +++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c @@ -856,6 +856,11 @@ static struct drm_connector *intel_dp_add_mst_connector(struct drm_dp_mst_topolo if (connector->active_bpc_property) drm_connector_attach_active_bpc_property(connector, 6, 12); + connector->active_color_format_property = + intel_dp->attached_connector->base.active_color_format_property; + if (connector->active_color_format_property) + drm_connector_attach_active_color_format_property(connector); + return connector; err: diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 9160e21ac9d6..367aba57b55f 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2516,6 +2516,7 @@ intel_hdmi_add_properties(struct intel_hdmi *intel_hdmi, struct drm_connector *c if (!HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 8, 12); drm_connector_attach_active_bpc_property(connector, 8, 12); + drm_connector_attach_active_color_format_property(connector); } } -- 2.25.1
[PATCH v5 11/17] drm/i915/display: Add handling for new "active color range" property
This commit implements the "active color range" drm property for the Intel GPU driver. Signed-off-by: Werner Sembach --- drivers/gpu/drm/i915/display/intel_display.c | 7 +++ drivers/gpu/drm/i915/display/intel_dp.c | 1 + drivers/gpu/drm/i915/display/intel_dp_mst.c | 5 + drivers/gpu/drm/i915/display/intel_hdmi.c| 1 + 4 files changed, 14 insertions(+) diff --git a/drivers/gpu/drm/i915/display/intel_display.c b/drivers/gpu/drm/i915/display/intel_display.c index be38f7148285..b0bcb42a97fc 100644 --- a/drivers/gpu/drm/i915/display/intel_display.c +++ b/drivers/gpu/drm/i915/display/intel_display.c @@ -10940,9 +10940,16 @@ static int intel_atomic_commit(struct drm_device *dev, drm_connector_set_active_color_format_property(connector, convert_intel_output_format_into_drm_color_format( new_crtc_state->output_format)); + drm_connector_set_active_color_range_property(connector, + new_crtc_state->limited_color_range || + new_crtc_state->output_format != INTEL_OUTPUT_FORMAT_RGB ? + DRM_MODE_COLOR_RANGE_LIMITED_16_235 : + DRM_MODE_COLOR_RANGE_FULL); } else { drm_connector_set_active_bpc_property(connector, 0); drm_connector_set_active_color_format_property(connector, 0); + drm_connector_set_active_color_range_property(connector, + DRM_MODE_COLOR_RANGE_UNSET); } } diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c index 6b85bcdeb238..fd33f753244d 100644 --- a/drivers/gpu/drm/i915/display/intel_dp.c +++ b/drivers/gpu/drm/i915/display/intel_dp.c @@ -4688,6 +4688,7 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connect intel_attach_force_audio_property(connector); intel_attach_broadcast_rgb_property(connector); + drm_connector_attach_active_color_range_property(connector); if (HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 6, 10); drm_connector_attach_active_bpc_property(connector, 6, 10); diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.c b/drivers/gpu/drm/i915/display/intel_dp_mst.c index 3e4237df3360..cb876175258f 100644 --- a/drivers/gpu/drm/i915/display/intel_dp_mst.c +++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c @@ -861,6 +861,11 @@ static struct drm_connector *intel_dp_add_mst_connector(struct drm_dp_mst_topolo if (connector->active_color_format_property) drm_connector_attach_active_color_format_property(connector); + connector->active_color_range_property = + intel_dp->attached_connector->base.active_color_range_property; + if (connector->active_color_range_property) + drm_connector_attach_active_color_range_property(connector); + return connector; err: diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 367aba57b55f..3ee25e0cc3b9 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2505,6 +2505,7 @@ intel_hdmi_add_properties(struct intel_hdmi *intel_hdmi, struct drm_connector *c intel_attach_force_audio_property(connector); intel_attach_broadcast_rgb_property(connector); + drm_connector_attach_active_color_range_property(connector); intel_attach_aspect_ratio_property(connector); intel_attach_hdmi_colorspace_property(connector); -- 2.25.1
[PATCH v5 17/17] drm/amd/display: Add handling for new "Broadcast RGB" property
This commit implements the "Broadcast RGB" drm property for the AMD GPU driver. Signed-off-by: Werner Sembach --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 14 +++--- .../amd/display/amdgpu_dm/amdgpu_dm_mst_types.c| 4 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 02a5809d4993..80d5a11fb0c5 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -5247,7 +5247,8 @@ get_aspect_ratio(const struct drm_display_mode *mode_in) } static enum dc_color_space -get_output_color_space(const struct dc_crtc_timing *dc_crtc_timing) +get_output_color_space(const struct dc_crtc_timing *dc_crtc_timing, + enum drm_mode_color_range preferred_color_range) { enum dc_color_space color_space = COLOR_SPACE_SRGB; @@ -5278,7 +5279,10 @@ get_output_color_space(const struct dc_crtc_timing *dc_crtc_timing) } break; case PIXEL_ENCODING_RGB: - color_space = COLOR_SPACE_SRGB; + if (preferred_color_range == DRM_MODE_COLOR_RANGE_LIMITED_16_235) + color_space = COLOR_SPACE_SRGB_LIMITED; + else + color_space = COLOR_SPACE_SRGB; break; default: @@ -5424,7 +5428,10 @@ static void fill_stream_properties_from_drm_display_mode( timing_out->aspect_ratio = get_aspect_ratio(mode_in); - stream->output_color_space = get_output_color_space(timing_out); + stream->output_color_space = get_output_color_space(timing_out, + connector_state ? + connector_state->preferred_color_range : + DRM_MODE_COLOR_RANGE_UNSET); stream->out_transfer_func->type = TF_TYPE_PREDEFINED; stream->out_transfer_func->tf = TRANSFER_FUNCTION_SRGB; @@ -7775,6 +7782,7 @@ void amdgpu_dm_connector_init_helper(struct amdgpu_display_manager *dm, drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); drm_connector_attach_preferred_color_format_property(&aconnector->base); drm_connector_attach_active_color_format_property(&aconnector->base); + drm_connector_attach_preferred_color_range_property(&aconnector->base); drm_connector_attach_active_color_range_property(&aconnector->base); } diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index 2563788ba95a..80e1389fd0ec 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -421,6 +421,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, if (connector->active_color_format_property) drm_connector_attach_active_color_format_property(&aconnector->base); + connector->preferred_color_range_property = master->base.preferred_color_range_property; + if (connector->preferred_color_range_property) + drm_connector_attach_preferred_color_range_property(&aconnector->base); + connector->active_color_range_property = master->base.active_color_range_property; if (connector->active_color_range_property) drm_connector_attach_active_color_range_property(&aconnector->base); -- 2.25.1
[PATCH v5 10/17] drm/amd/display: Add handling for new "active color range" property
This commit implements the "active color range" drm property for the AMD GPU driver. Signed-off-by: Werner Sembach --- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 33 +++ .../display/amdgpu_dm/amdgpu_dm_mst_types.c | 4 +++ 2 files changed, 37 insertions(+) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 098f3d53e681..b4acedac1ac9 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6728,6 +6728,33 @@ static int convert_dc_pixel_encoding_into_drm_color_format( return 0; } +static int convert_dc_color_space_into_drm_mode_color_range(enum dc_color_space color_space) +{ + if (color_space == COLOR_SPACE_SRGB || + color_space == COLOR_SPACE_XR_RGB || + color_space == COLOR_SPACE_MSREF_SCRGB || + color_space == COLOR_SPACE_2020_RGB_FULLRANGE || + color_space == COLOR_SPACE_ADOBERGB || + color_space == COLOR_SPACE_DCIP3 || + color_space == COLOR_SPACE_DOLBYVISION || + color_space == COLOR_SPACE_YCBCR601 || + color_space == COLOR_SPACE_XV_YCC_601 || + color_space == COLOR_SPACE_YCBCR709 || + color_space == COLOR_SPACE_XV_YCC_709 || + color_space == COLOR_SPACE_2020_YCBCR || + color_space == COLOR_SPACE_YCBCR709_BLACK || + color_space == COLOR_SPACE_DISPLAYNATIVE || + color_space == COLOR_SPACE_APPCTRL || + color_space == COLOR_SPACE_CUSTOMPOINTS) + return DRM_MODE_COLOR_RANGE_FULL; + if (color_space == COLOR_SPACE_SRGB_LIMITED || + color_space == COLOR_SPACE_2020_RGB_LIMITEDRANGE || + color_space == COLOR_SPACE_YCBCR601_LIMITED || + color_space == COLOR_SPACE_YCBCR709_LIMITED) + return DRM_MODE_COLOR_RANGE_LIMITED_16_235; + return DRM_MODE_COLOR_RANGE_UNSET; +} + static int dm_encoder_helper_atomic_check(struct drm_encoder *encoder, struct drm_crtc_state *crtc_state, struct drm_connector_state *conn_state) @@ -7730,6 +7757,7 @@ void amdgpu_dm_connector_init_helper(struct amdgpu_display_manager *dm, drm_connector_attach_max_bpc_property(&aconnector->base, 8, 16); drm_connector_attach_active_bpc_property(&aconnector->base, 8, 16); drm_connector_attach_active_color_format_property(&aconnector->base); + drm_connector_attach_active_color_range_property(&aconnector->base); } /* This defaults to the max in the range, but we want 8bpc for non-edp. */ @@ -9118,10 +9146,15 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) drm_connector_set_active_color_format_property(connector, convert_dc_pixel_encoding_into_drm_color_format( dm_new_crtc_state->stream->timing.pixel_encoding)); + drm_connector_set_active_color_range_property(connector, + convert_dc_color_space_into_drm_mode_color_range( + dm_new_crtc_state->stream->output_color_space)); } } else { drm_connector_set_active_bpc_property(connector, 0); drm_connector_set_active_color_format_property(connector, 0); + drm_connector_set_active_color_range_property(connector, + DRM_MODE_COLOR_RANGE_UNSET); } } diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c index 13151d13aa73..b5d57bbbdd20 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c @@ -417,6 +417,10 @@ dm_dp_add_mst_connector(struct drm_dp_mst_topology_mgr *mgr, if (connector->active_color_format_property) drm_connector_attach_active_color_format_property(&aconnector->base); + connector->active_color_range_property = master->base.active_color_range_property; + if (connector->active_color_range_property) + drm_connector_attach_active_color_range_property(&aconnector->base); + connector->vrr_capable_property = master->base.vrr_capable_property; if (connector->vrr_capable_property) drm_connector_attach_vrr_capable_property(connector); -- 2.25.1
[PATCH v5 15/17] drm/uAPI: Move "Broadcast RGB" property from driver specific to general context
Add "Broadcast RGB" to general drm context so that more drivers besides i915 and gma500 can implement it without duplicating code. Userspace can use this property to tell the graphic driver to use full or limited color range for a given connector, overwriting the default behaviour/automatic detection. Possible options are: - Automatic (default/current behaviour) - Full - Limited 16:235 In theory the driver should be able to automatically detect the monitors capabilities, but because of flawed standard implementations in Monitors, this might fail. In this case a manual overwrite is required to not have washed out colors or lose details in very dark or bright scenes. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_atomic_helper.c | 4 +++ drivers/gpu/drm/drm_atomic_uapi.c | 4 +++ drivers/gpu/drm/drm_connector.c | 46 + include/drm/drm_connector.h | 16 ++ 4 files changed, 70 insertions(+) diff --git a/drivers/gpu/drm/drm_atomic_helper.c b/drivers/gpu/drm/drm_atomic_helper.c index 90d62f305257..0c89d32efbd0 100644 --- a/drivers/gpu/drm/drm_atomic_helper.c +++ b/drivers/gpu/drm/drm_atomic_helper.c @@ -691,6 +691,10 @@ drm_atomic_helper_check_modeset(struct drm_device *dev, if (old_connector_state->preferred_color_format != new_connector_state->preferred_color_format) new_crtc_state->connectors_changed = true; + + if (old_connector_state->preferred_color_range != + new_connector_state->preferred_color_range) + new_crtc_state->connectors_changed = true; } if (funcs->atomic_check) diff --git a/drivers/gpu/drm/drm_atomic_uapi.c b/drivers/gpu/drm/drm_atomic_uapi.c index c536f5e22016..c589bb1a8163 100644 --- a/drivers/gpu/drm/drm_atomic_uapi.c +++ b/drivers/gpu/drm/drm_atomic_uapi.c @@ -798,6 +798,8 @@ static int drm_atomic_connector_set_property(struct drm_connector *connector, state->max_requested_bpc = val; } else if (property == connector->preferred_color_format_property) { state->preferred_color_format = val; + } else if (property == connector->preferred_color_range_property) { + state->preferred_color_range = val; } else if (connector->funcs->atomic_set_property) { return connector->funcs->atomic_set_property(connector, state, property, val); @@ -877,6 +879,8 @@ drm_atomic_connector_get_property(struct drm_connector *connector, *val = state->max_requested_bpc; } else if (property == connector->preferred_color_format_property) { *val = state->preferred_color_format; + } else if (property == connector->preferred_color_range_property) { + *val = state->preferred_color_range; } else if (connector->funcs->atomic_get_property) { return connector->funcs->atomic_get_property(connector, state, property, val); diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index 67dd59b12258..20ae2e6d907b 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -905,6 +905,12 @@ static const struct drm_prop_enum_list drm_active_color_format_enum_list[] = { { DRM_COLOR_FORMAT_YCRCB420, "ycbcr420" }, }; +static const struct drm_prop_enum_list drm_preferred_color_range_enum_list[] = { + { DRM_MODE_COLOR_RANGE_UNSET, "Automatic" }, + { DRM_MODE_COLOR_RANGE_FULL, "Full" }, + { DRM_MODE_COLOR_RANGE_LIMITED_16_235, "Limited 16:235" }, +}; + static const struct drm_prop_enum_list drm_active_color_range_enum_list[] = { { DRM_MODE_COLOR_RANGE_UNSET, "Not Applicable" }, { DRM_MODE_COLOR_RANGE_FULL, "Full" }, @@ -1246,6 +1252,15 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { * property. Possible values are "not applicable", "rgb", "ycbcr444", * "ycbcr422", and "ycbcr420". * + * Broadcast RGB: + * This property is used by userspace to change the used color range. This + * property affects the RGB color format as well as the Y'CbCr color + * formats, if the driver supports both full and limited Y'CbCr. Drivers to + * use the function drm_connector_attach_preferred_color_format_property() + * to create and attach the property to the connector during + * initialization. Possible values are "Automatic", "Full", and "Limited + * 16:235". + * * active color range: * This read-only property tells userspace the color range actually used by * the hardware display engine "on the cable" on a connector. The chosen @@ -2331,6 +2346,37 @@ void drm_connector_set_active_color_format_property(struct drm_connector *connec } EXPORT_SYMBOL(drm_connector_set_active_color_format_property);
[PATCH v5 16/17] drm/i915/display: Use the general "Broadcast RGB" implementation
Change from the i915 specific "Broadcast RGB" drm property implementation to the general one. This commit delete all traces of the former "Broadcast RGB" implementation and add a new one using the new driver agnoistic functions an variables. Signed-off-by: Werner Sembach --- drivers/gpu/drm/i915/display/intel_atomic.c | 8 -- .../gpu/drm/i915/display/intel_connector.c| 28 --- .../gpu/drm/i915/display/intel_connector.h| 1 - .../drm/i915/display/intel_display_types.h| 8 -- drivers/gpu/drm/i915/display/intel_dp.c | 9 ++ drivers/gpu/drm/i915/display/intel_dp_mst.c | 6 +++- drivers/gpu/drm/i915/display/intel_hdmi.c | 8 ++ drivers/gpu/drm/i915/display/intel_sdvo.c | 2 +- drivers/gpu/drm/i915/i915_drv.h | 1 - 9 files changed, 12 insertions(+), 59 deletions(-) diff --git a/drivers/gpu/drm/i915/display/intel_atomic.c b/drivers/gpu/drm/i915/display/intel_atomic.c index b4e7ac51aa31..f8d5a0e287b0 100644 --- a/drivers/gpu/drm/i915/display/intel_atomic.c +++ b/drivers/gpu/drm/i915/display/intel_atomic.c @@ -63,8 +63,6 @@ int intel_digital_connector_atomic_get_property(struct drm_connector *connector, if (property == dev_priv->force_audio_property) *val = intel_conn_state->force_audio; - else if (property == dev_priv->broadcast_rgb_property) - *val = intel_conn_state->broadcast_rgb; else { drm_dbg_atomic(&dev_priv->drm, "Unknown property [PROP:%d:%s]\n", @@ -99,11 +97,6 @@ int intel_digital_connector_atomic_set_property(struct drm_connector *connector, return 0; } - if (property == dev_priv->broadcast_rgb_property) { - intel_conn_state->broadcast_rgb = val; - return 0; - } - drm_dbg_atomic(&dev_priv->drm, "Unknown property [PROP:%d:%s]\n", property->base.id, property->name); return -EINVAL; @@ -134,7 +127,6 @@ int intel_digital_connector_atomic_check(struct drm_connector *conn, * up in a modeset. */ if (new_conn_state->force_audio != old_conn_state->force_audio || - new_conn_state->broadcast_rgb != old_conn_state->broadcast_rgb || new_conn_state->base.colorspace != old_conn_state->base.colorspace || new_conn_state->base.picture_aspect_ratio != old_conn_state->base.picture_aspect_ratio || new_conn_state->base.content_type != old_conn_state->base.content_type || diff --git a/drivers/gpu/drm/i915/display/intel_connector.c b/drivers/gpu/drm/i915/display/intel_connector.c index 9bed1ccecea0..89f0edf19182 100644 --- a/drivers/gpu/drm/i915/display/intel_connector.c +++ b/drivers/gpu/drm/i915/display/intel_connector.c @@ -241,34 +241,6 @@ intel_attach_force_audio_property(struct drm_connector *connector) drm_object_attach_property(&connector->base, prop, 0); } -static const struct drm_prop_enum_list broadcast_rgb_names[] = { - { INTEL_BROADCAST_RGB_AUTO, "Automatic" }, - { INTEL_BROADCAST_RGB_FULL, "Full" }, - { INTEL_BROADCAST_RGB_LIMITED, "Limited 16:235" }, -}; - -void -intel_attach_broadcast_rgb_property(struct drm_connector *connector) -{ - struct drm_device *dev = connector->dev; - struct drm_i915_private *dev_priv = to_i915(dev); - struct drm_property *prop; - - prop = dev_priv->broadcast_rgb_property; - if (prop == NULL) { - prop = drm_property_create_enum(dev, DRM_MODE_PROP_ENUM, - "Broadcast RGB", - broadcast_rgb_names, - ARRAY_SIZE(broadcast_rgb_names)); - if (prop == NULL) - return; - - dev_priv->broadcast_rgb_property = prop; - } - - drm_object_attach_property(&connector->base, prop, 0); -} - void intel_attach_aspect_ratio_property(struct drm_connector *connector) { diff --git a/drivers/gpu/drm/i915/display/intel_connector.h b/drivers/gpu/drm/i915/display/intel_connector.h index 661a37a3c6d8..f3058a035476 100644 --- a/drivers/gpu/drm/i915/display/intel_connector.h +++ b/drivers/gpu/drm/i915/display/intel_connector.h @@ -28,7 +28,6 @@ int intel_connector_update_modes(struct drm_connector *connector, struct edid *edid); int intel_ddc_get_modes(struct drm_connector *c, struct i2c_adapter *adapter); void intel_attach_force_audio_property(struct drm_connector *connector); -void intel_attach_broadcast_rgb_property(struct drm_connector *connector); void intel_attach_aspect_ratio_property(struct drm_connector *connector); void intel_attach_hdmi_colorspace_property(struct drm_connector *connector); void intel_attach_dp_colorspace_property(struct drm_connector *connector); diff --git a/drivers/gpu/drm/i915/display/intel_display_types.h b/drivers/gpu/dr
[PATCH v5 12/17] drm/uAPI: Add "preferred color format" drm property as setting for userspace
Add a new general drm property "preferred color format" which can be used by userspace to tell the graphic drivers to which color format to use. Possible options are: - auto (default/current behaviour) - rgb - ycbcr444 - ycbcr422 (not supported by both amdgpu and i915) - ycbcr420 In theory the auto option should choose the best available option for the current setup, but because of bad internal conversion some monitors look better with rgb and some with ycbcr444. Also, because of bad shielded connectors and/or cables, it might be preferable to use the less bandwidth heavy ycbcr422 and ycbcr420 formats for a signal that is less deceptible to interference. In the future, automatic color calibration for screens might also depend on this option being available. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_atomic_helper.c | 4 +++ drivers/gpu/drm/drm_atomic_uapi.c | 4 +++ drivers/gpu/drm/drm_connector.c | 50 - include/drm/drm_connector.h | 17 ++ 4 files changed, 74 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/drm_atomic_helper.c b/drivers/gpu/drm/drm_atomic_helper.c index bc3487964fb5..90d62f305257 100644 --- a/drivers/gpu/drm/drm_atomic_helper.c +++ b/drivers/gpu/drm/drm_atomic_helper.c @@ -687,6 +687,10 @@ drm_atomic_helper_check_modeset(struct drm_device *dev, if (old_connector_state->max_requested_bpc != new_connector_state->max_requested_bpc) new_crtc_state->connectors_changed = true; + + if (old_connector_state->preferred_color_format != + new_connector_state->preferred_color_format) + new_crtc_state->connectors_changed = true; } if (funcs->atomic_check) diff --git a/drivers/gpu/drm/drm_atomic_uapi.c b/drivers/gpu/drm/drm_atomic_uapi.c index 438e9585b225..c536f5e22016 100644 --- a/drivers/gpu/drm/drm_atomic_uapi.c +++ b/drivers/gpu/drm/drm_atomic_uapi.c @@ -796,6 +796,8 @@ static int drm_atomic_connector_set_property(struct drm_connector *connector, fence_ptr); } else if (property == connector->max_bpc_property) { state->max_requested_bpc = val; + } else if (property == connector->preferred_color_format_property) { + state->preferred_color_format = val; } else if (connector->funcs->atomic_set_property) { return connector->funcs->atomic_set_property(connector, state, property, val); @@ -873,6 +875,8 @@ drm_atomic_connector_get_property(struct drm_connector *connector, *val = 0; } else if (property == connector->max_bpc_property) { *val = state->max_requested_bpc; + } else if (property == connector->preferred_color_format_property) { + *val = state->preferred_color_format; } else if (connector->funcs->atomic_get_property) { return connector->funcs->atomic_get_property(connector, state, property, val); diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index ebfdd17a7f59..67dd59b12258 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -889,6 +889,14 @@ static const struct drm_prop_enum_list drm_dp_subconnector_enum_list[] = { { DRM_MODE_SUBCONNECTOR_Native, "Native"}, /* DP */ }; +static const struct drm_prop_enum_list drm_preferred_color_format_enum_list[] = { + { 0, "auto" }, + { DRM_COLOR_FORMAT_RGB444, "rgb" }, + { DRM_COLOR_FORMAT_YCRCB444, "ycbcr444" }, + { DRM_COLOR_FORMAT_YCRCB422, "ycbcr422" }, + { DRM_COLOR_FORMAT_YCRCB420, "ycbcr420" }, +}; + static const struct drm_prop_enum_list drm_active_color_format_enum_list[] = { { 0, "not applicable" }, { DRM_COLOR_FORMAT_RGB444, "rgb" }, @@ -1220,11 +1228,20 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { * Drivers shall use drm_connector_attach_active_bpc_property() to install * this property. A value of 0 means "not applicable". * + * preferred color format: + * This property is used by userspace to change the used color format. When + * used the driver will use the selected format if valid for the hardware, + * sink, and current resolution and refresh rate combination. Drivers to + * use the function drm_connector_attach_preferred_color_format_property() + * to create and attach the property to the connector during + * initialization. Possible values are "auto", "rgb", "ycbcr444", + * "ycbcr422", and "ycbcr420". + * * active color format: * This read-only property tells userspace the color format actually used * by the hardware display engine "on the cable" on a connector. The chosen *
[PATCH v5 09/17] drm/uAPI: Add "active color range" drm property as feedback for userspace
Add a new general drm property "active color range" which can be used by graphic drivers to report the used color range back to userspace. There was no way to check which color range got actually used on a given monitor. To surely predict this, one must know the exact capabilities of the monitor and what the default behaviour of the used driver is. This property helps eliminating the guessing at this point. In the future, automatic color calibration for screens might also depend on this information being available. Signed-off-by: Werner Sembach --- drivers/gpu/drm/drm_connector.c | 61 + include/drm/drm_connector.h | 27 +++ 2 files changed, 88 insertions(+) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index 075bdc08d5c3..ebfdd17a7f59 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -897,6 +897,12 @@ static const struct drm_prop_enum_list drm_active_color_format_enum_list[] = { { DRM_COLOR_FORMAT_YCRCB420, "ycbcr420" }, }; +static const struct drm_prop_enum_list drm_active_color_range_enum_list[] = { + { DRM_MODE_COLOR_RANGE_UNSET, "Not Applicable" }, + { DRM_MODE_COLOR_RANGE_FULL, "Full" }, + { DRM_MODE_COLOR_RANGE_LIMITED_16_235, "Limited 16:235" }, +}; + DRM_ENUM_NAME_FN(drm_get_dp_subconnector_name, drm_dp_subconnector_enum_list) @@ -1223,6 +1229,15 @@ static const struct drm_prop_enum_list dp_colorspaces[] = { * property. Possible values are "not applicable", "rgb", "ycbcr444", * "ycbcr422", and "ycbcr420". * + * active color range: + * This read-only property tells userspace the color range actually used by + * the hardware display engine "on the cable" on a connector. The chosen + * value depends on hardware capabilities of the monitor and the used color + * format. Drivers shall use + * drm_connector_attach_active_color_range_property() to install this + * property. Possible values are "Not Applicable", "Full", and "Limited + * 16:235". + * * Connectors also have one standardized atomic property: * * CRTC_ID: @@ -2268,6 +2283,52 @@ void drm_connector_set_active_color_format_property(struct drm_connector *connec } EXPORT_SYMBOL(drm_connector_set_active_color_format_property); +/** + * drm_connector_attach_active_color_range_property - attach "active color range" property + * @connector: connector to attach active color range property on. + * + * This is used to check the applied color range on a connector. + * + * Returns: + * Zero on success, negative errno on failure. + */ +int drm_connector_attach_active_color_range_property(struct drm_connector *connector) +{ + struct drm_device *dev = connector->dev; + struct drm_property *prop; + + if (!connector->active_color_range_property) { + prop = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE, "active color range", + drm_active_color_range_enum_list, + ARRAY_SIZE(drm_active_color_range_enum_list)); + if (!prop) + return -ENOMEM; + + connector->active_color_range_property = prop; + } + + drm_object_attach_property(&connector->base, prop, DRM_MODE_COLOR_RANGE_UNSET); + + return 0; +} +EXPORT_SYMBOL(drm_connector_attach_active_color_range_property); + +/** + * drm_connector_set_active_color_range_property - sets the active color range property for a + * connector + * @connector: drm connector + * @active_color_range: color range for the connector currently active "on the cable" + * + * Should be used by atomic drivers to update the active color range over a connector. + */ +void drm_connector_set_active_color_range_property(struct drm_connector *connector, + enum drm_mode_color_range active_color_range) +{ + drm_object_property_set_value(&connector->base, connector->active_color_range_property, + active_color_range); +} +EXPORT_SYMBOL(drm_connector_set_active_color_range_property); + /** * drm_connector_attach_hdr_output_metadata_property - attach "HDR_OUTPUT_METADA" property * @connector: connector to attach the property on. diff --git a/include/drm/drm_connector.h b/include/drm/drm_connector.h index 8a5197f14e87..5ef4bb270f71 100644 --- a/include/drm/drm_connector.h +++ b/include/drm/drm_connector.h @@ -648,6 +648,24 @@ struct drm_tv_connector_state { unsigned int hue; }; +/** + * enum drm_mode_color_range - color_range info for &drm_connector + * + * This enum is used to represent full or limited color range on the display + * connector signal. + * + * @DRM_MODE_COLOR_RANGE_UNSET: Color range is unspecified/default. + * @DRM_MODE_COLOR_RANGE_FULL: Color range is full range, 0-255 for + *
[PATCH v5 14/17] drm/i915/display: Add handling for new "preferred color format" property
This commit implements the "preferred color format" drm property for the Intel GPU driver. Signed-off-by: Werner Sembach --- drivers/gpu/drm/i915/display/intel_dp.c | 7 ++- drivers/gpu/drm/i915/display/intel_dp_mst.c | 5 + drivers/gpu/drm/i915/display/intel_hdmi.c | 6 ++ 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/display/intel_dp.c b/drivers/gpu/drm/i915/display/intel_dp.c index fd33f753244d..29bb181ec4be 100644 --- a/drivers/gpu/drm/i915/display/intel_dp.c +++ b/drivers/gpu/drm/i915/display/intel_dp.c @@ -616,9 +616,12 @@ intel_dp_output_format(struct drm_connector *connector, { struct intel_dp *intel_dp = intel_attached_dp(to_intel_connector(connector)); const struct drm_display_info *info = &connector->display_info; + const struct drm_connector_state *connector_state = connector->state; if (!connector->ycbcr_420_allowed || - !drm_mode_is_420_only(info, mode)) + !(drm_mode_is_420_only(info, mode) || + (drm_mode_is_420_also(info, mode) && connector_state && + connector_state->preferred_color_format == DRM_COLOR_FORMAT_YCRCB420))) return INTEL_OUTPUT_FORMAT_RGB; if (intel_dp->dfp.rgb_to_ycbcr && @@ -4692,10 +4695,12 @@ intel_dp_add_properties(struct intel_dp *intel_dp, struct drm_connector *connect if (HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 6, 10); drm_connector_attach_active_bpc_property(connector, 6, 10); + drm_connector_attach_preferred_color_format_property(connector); drm_connector_attach_active_color_format_property(connector); } else if (DISPLAY_VER(dev_priv) >= 5) { drm_connector_attach_max_bpc_property(connector, 6, 12); drm_connector_attach_active_bpc_property(connector, 6, 12); + drm_connector_attach_preferred_color_format_property(connector); drm_connector_attach_active_color_format_property(connector); } diff --git a/drivers/gpu/drm/i915/display/intel_dp_mst.c b/drivers/gpu/drm/i915/display/intel_dp_mst.c index cb876175258f..67f0fb649876 100644 --- a/drivers/gpu/drm/i915/display/intel_dp_mst.c +++ b/drivers/gpu/drm/i915/display/intel_dp_mst.c @@ -856,6 +856,11 @@ static struct drm_connector *intel_dp_add_mst_connector(struct drm_dp_mst_topolo if (connector->active_bpc_property) drm_connector_attach_active_bpc_property(connector, 6, 12); + connector->preferred_color_format_property = + intel_dp->attached_connector->base.preferred_color_format_property; + if (connector->preferred_color_format_property) + drm_connector_attach_preferred_color_format_property(connector); + connector->active_color_format_property = intel_dp->attached_connector->base.active_color_format_property; if (connector->active_color_format_property) diff --git a/drivers/gpu/drm/i915/display/intel_hdmi.c b/drivers/gpu/drm/i915/display/intel_hdmi.c index 3ee25e0cc3b9..a7b85cd13227 100644 --- a/drivers/gpu/drm/i915/display/intel_hdmi.c +++ b/drivers/gpu/drm/i915/display/intel_hdmi.c @@ -2153,6 +2153,11 @@ static int intel_hdmi_compute_output_format(struct intel_encoder *encoder, crtc_state->output_format = INTEL_OUTPUT_FORMAT_RGB; } + if (connector->ycbcr_420_allowed && + conn_state->preferred_color_format == DRM_COLOR_FORMAT_YCRCB420 && + drm_mode_is_420_also(&connector->display_info, adjusted_mode)) + crtc_state->output_format = INTEL_OUTPUT_FORMAT_YCBCR420; + ret = intel_hdmi_compute_clock(encoder, crtc_state); if (ret) { if (crtc_state->output_format != INTEL_OUTPUT_FORMAT_YCBCR420 && @@ -2517,6 +2522,7 @@ intel_hdmi_add_properties(struct intel_hdmi *intel_hdmi, struct drm_connector *c if (!HAS_GMCH(dev_priv)) { drm_connector_attach_max_bpc_property(connector, 8, 12); drm_connector_attach_active_bpc_property(connector, 8, 12); + drm_connector_attach_preferred_color_format_property(connector); drm_connector_attach_active_color_format_property(connector); } } -- 2.25.1
Re: [PATCH 1/2] drm/i915/ttm: Reorganize the ttm move code somewhat
On Wed, 2021-06-30 at 15:19 +0100, Matthew Auld wrote: > On Thu, 24 Jun 2021 at 20:31, Thomas Hellström > wrote: > > > > In order to make the code a bit more readable and to facilitate > > async memcpy moves, reorganize the move code a little. Determine > > at an early stage whether to copy or to clear. > > > > Signed-off-by: Thomas Hellström > > --- > > drivers/gpu/drm/i915/gem/i915_gem_ttm.c | 70 ++--- > > > > 1 file changed, 40 insertions(+), 30 deletions(-) > > > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > index c39d982c4fa6..4e529adcdfc7 100644 > > --- a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > +++ b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > @@ -431,6 +431,7 @@ i915_ttm_resource_get_st(struct > > drm_i915_gem_object *obj, > > } > > > > static int i915_ttm_accel_move(struct ttm_buffer_object *bo, > > + bool clear, > > struct ttm_resource *dst_mem, > > struct sg_table *dst_st) > > { > > @@ -449,13 +450,10 @@ static int i915_ttm_accel_move(struct > > ttm_buffer_object *bo, > > return -EINVAL; > > > > dst_level = i915_ttm_cache_level(i915, dst_mem, ttm); > > - if (!ttm || !ttm_tt_is_populated(ttm)) { > > + if (clear) { > > if (bo->type == ttm_bo_type_kernel) > > return -EINVAL; > > Was that meant to be: > return 0: > > ? > > Also does that mean we are incorrectly falling back to memset, for > non-userspace objects, instead of making it a noop? No, we're deliberately falling back to memset for non-userspace objects, but the logic only memsets in the BO_ALLOC_CPU_CLEAR case if everything is implemented correctly. > > > > > - if (ttm && !(ttm->page_flags & > > TTM_PAGE_FLAG_ZERO_ALLOC)) > > - return 0; > > - > > intel_engine_pm_get(i915->gt.migrate.context- > > >engine); > > ret = intel_context_migrate_clear(i915- > > >gt.migrate.context, NULL, > > dst_st->sgl, > > dst_level, > > @@ -489,27 +487,53 @@ static int i915_ttm_accel_move(struct > > ttm_buffer_object *bo, > > return ret; > > } > > > > -static int i915_ttm_move(struct ttm_buffer_object *bo, bool evict, > > - struct ttm_operation_ctx *ctx, > > - struct ttm_resource *dst_mem, > > - struct ttm_place *hop) > > +static void __i915_ttm_move(struct ttm_buffer_object *bo, bool > > clear, > > + struct ttm_resource *dst_mem, > > + struct sg_table *dst_st) > > { > > struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); > > - struct ttm_resource_manager *dst_man = > > - ttm_manager_type(bo->bdev, dst_mem->mem_type); > > struct intel_memory_region *dst_reg, *src_reg; > > union { > > struct ttm_kmap_iter_tt tt; > > struct ttm_kmap_iter_iomap io; > > } _dst_iter, _src_iter; > > struct ttm_kmap_iter *dst_iter, *src_iter; > > - struct sg_table *dst_st; > > int ret; > > > > dst_reg = i915_ttm_region(bo->bdev, dst_mem->mem_type); > > src_reg = i915_ttm_region(bo->bdev, bo->resource- > > >mem_type); > > GEM_BUG_ON(!dst_reg || !src_reg); > > > > + ret = i915_ttm_accel_move(bo, clear, dst_mem, dst_st); > > + if (ret) { > > One future consideration is flat CCS where I don't think we can > easily > fall back to memcpy for userspace objects. Maybe we can make this > fallback conditional on DG1 or !ALLOC_USER for now, or just add a > TODO? Ugh. Is that true for both clearing and copying, or is it only copying? Problem is if we hit an engine reset and fence error during initial clearing / swapin, the plan moving forward is to intercept that and resort to cpu clearing / copying for security reasons. In the worst case we at least need to be able to clear. /Thomas > > > + dst_iter = !cpu_maps_iomem(dst_mem) ? > > + ttm_kmap_iter_tt_init(&_dst_iter.tt, bo- > > >ttm) : > > + ttm_kmap_iter_iomap_init(&_dst_iter.io, > > &dst_reg->iomap, > > + dst_st, dst_reg- > > >region.start); > > + > > + src_iter = !cpu_maps_iomem(bo->resource) ? > > + ttm_kmap_iter_tt_init(&_src_iter.tt, bo- > > >ttm) : > > + ttm_kmap_iter_iomap_init(&_src_iter.io, > > &src_reg->iomap, > > + obj- > > >ttm.cached_io_st, > > + src_reg- > > >region.start); > > + > > + ttm_move_memcpy(bo, dst_mem->num_pages, dst_iter, > > src_iter); > > + } > > +} > > + > > +static int i915_ttm_move
Re: [PATCH] drm/panel: ws2401: Add driver for WideChips WS2401
Hi Doug, thanks for your review! I fixed most things except this: On Fri, Jun 25, 2021 at 6:42 PM Doug Anderson wrote: > > +static int ws2401_disable(struct drm_panel *panel) > > +{ > > + struct ws2401 *ws = to_ws2401(panel); > > + > > + ws2401_command(ws, MIPI_DCS_SET_DISPLAY_OFF); > > + msleep(25); > > It feels weird / arbitrary the split between "disable" and "unprepare" > on this panel driver compared to the "db7430.c" one. In the other > driver you put the sleep mode here and in this driver you put the > sleep mode un "unpreapre". Is that for a reason, or just arbitrary? > Can it be consistent between the two drivers? > > I guess maybe this is because in "db7430" the power up order was > slightly different? This arbitrary sequence ordering is part of why we can't just have one display driver to rule them all... sadly they also make semantic sense. The vendor driver needs the display to come out of sleep right after the power-on to send the init sequence. The vendor driver does exactly this. The placement of these sleep mode in prepare/unprepare calls is because of this. Yours, Linus Walleij
Re: [PATCH] drm/panel: ws2401: Add driver for WideChips WS2401
On Mon, Jun 28, 2021 at 11:30 AM Noralf Trønnes wrote: > > + dev_info(ws->dev, "MTP ID: %02x %02x %02x\n", id1, id2, id3); > > +} > > Why do you read these id's on every power on, it doesn't look like you > use them? > > If they're just informational, they should be available through debugfs, > see mipi_dbi_debugfs_init(). I moved them to probe. I actually really want to print this into dmesg so we learn to understand these MTP values better, if for nothing else so for the fact that they will turn up in google searches. The actual display controller vendor comes out in the first MTP byte, and by collecting this data we can figure out to some extent what kind of hardware is actually inside some of these displays. In this case 0xDA is 0x40 so that is widechips manufacturer ID. I fixed the rest of the comments! Yours, Linus Walleij
Re: [PATCH v15 06/12] swiotlb: Use is_swiotlb_force_bounce for swiotlb data bouncing
Hi Will and Claire, On Wed, Jun 30, 2021 at 12:43:48PM +0100, Will Deacon wrote: > On Wed, Jun 30, 2021 at 05:17:27PM +0800, Claire Chang wrote: > > On Wed, Jun 30, 2021 at 9:43 AM Nathan Chancellor wrote: > > > > > > On Thu, Jun 24, 2021 at 11:55:20PM +0800, Claire Chang wrote: > > > > Propagate the swiotlb_force into io_tlb_default_mem->force_bounce and > > > > use it to determine whether to bounce the data or not. This will be > > > > useful later to allow for different pools. > > > > > > > > Signed-off-by: Claire Chang > > > > Reviewed-by: Christoph Hellwig > > > > Tested-by: Stefano Stabellini > > > > Tested-by: Will Deacon > > > > Acked-by: Stefano Stabellini > > > > > > This patch as commit af452ec1b1a3 ("swiotlb: Use is_swiotlb_force_bounce > > > for swiotlb data bouncing") causes my Ryzen 3 4300G system to fail to > > > get to an X session consistently (although not every single time), > > > presumably due to a crash in the AMDGPU driver that I see in dmesg. > > > > > > I have attached logs at af452ec1b1a3 and f127c9556a8e and I am happy > > > to provide any further information, debug, or test patches as necessary. > > > > Are you using swiotlb=force? or the swiotlb_map is called because of > > !dma_capable? > > (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/kernel/dma/direct.h#n93) > > The command line is in the dmesg: > > | Kernel command line: initrd=\amd-ucode.img > initrd=\initramfs-linux-next-llvm.img > root=PARTUUID=8680aa0c-cf09-4a69-8cf3-970478040ee7 rw intel_pstate=no_hwp > irqpoll > > but I worry that this looks _very_ similar to the issue reported by Qian > Cai which we thought we had fixed. Nathan -- is the failure deterministic? Yes, for the most part. It does not happen every single boot so when I was bisecting, I did a series of seven boots and only considered the revision good when all seven of them made it to LightDM's greeter. My results that I notated show most bad revisions failed anywhere from four to six times. > > `BUG: unable to handle page fault for address: 003a8290` and > > the fact it crashed at `_raw_spin_lock_irqsave` look like the memory > > (maybe dev->dma_io_tlb_mem) was corrupted? > > The dev->dma_io_tlb_mem should be set here > > (https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git/tree/drivers/pci/probe.c#n2528) > > through device_initialize. > > I'm less sure about this. 'dma_io_tlb_mem' should be pointing at > 'io_tlb_default_mem', which is a page-aligned allocation from memblock. > The spinlock is at offset 0x24 in that structure, and looking at the > register dump from the crash: > > Jun 29 18:28:42 hp-4300G kernel: RSP: 0018:adb4013db9e8 EFLAGS: 00010006 > Jun 29 18:28:42 hp-4300G kernel: RAX: 003a8290 RBX: > RCX: 8900572ad580 > Jun 29 18:28:42 hp-4300G kernel: RDX: 89005653f024 RSI: 000c > RDI: 1d17 > Jun 29 18:28:42 hp-4300G kernel: RBP: 0a20d000 R08: 000c > R09: > Jun 29 18:28:42 hp-4300G kernel: R10: 0a20d000 R11: 89005653f000 > R12: 0212 > Jun 29 18:28:42 hp-4300G kernel: R13: 1000 R14: 0002 > R15: 0020 > Jun 29 18:28:42 hp-4300G kernel: FS: 7f1f8898ea40() > GS:89005728() knlGS: > Jun 29 18:28:42 hp-4300G kernel: CS: 0010 DS: ES: CR0: > 80050033 > Jun 29 18:28:42 hp-4300G kernel: CR2: 003a8290 CR3: 0001020d > CR4: 00350ee0 > Jun 29 18:28:42 hp-4300G kernel: Call Trace: > Jun 29 18:28:42 hp-4300G kernel: _raw_spin_lock_irqsave+0x39/0x50 > Jun 29 18:28:42 hp-4300G kernel: swiotlb_tbl_map_single+0x12b/0x4c0 > > Then that correlates with R11 holding the 'dma_io_tlb_mem' pointer and > RDX pointing at the spinlock. Yet RAX is holding junk :/ > > I agree that enabling KASAN would be a good idea, but I also think we > probably need to get some more information out of swiotlb_tbl_map_single() > to see see what exactly is going wrong in there. I can certainly enable KASAN and if there is any debug print I can add or dump anything, let me know! Cheers, Nathan
Re: [PATCH] dma-buf: fix and rework dma_buf_poll v4
On Wed, Jun 30, 2021 at 4:22 PM Christian König wrote: > > Am 30.06.21 um 16:07 schrieb Daniel Vetter: > > On Wed, Jun 30, 2021 at 2:36 PM Christian König > > wrote: > >> Daniel pointed me towards this function and there are multiple obvious > >> problems > >> in the implementation. > >> > >> First of all the retry loop is not working as intended. In general the > >> retry > >> makes only sense if you grab the reference first and then check the > >> sequence > >> values. > >> > >> Then we should always also wait for the exclusive fence. > >> > >> It's also good practice to keep the reference around when installing > >> callbacks > >> to fences you don't own. > >> > >> And last the whole implementation was unnecessary complex and rather hard > >> to > >> understand which could lead to probably unexpected behavior of the IOCTL. > >> > >> Fix all this by reworking the implementation from scratch. Dropping the > >> whole RCU approach and taking the lock instead. > >> > >> Only mildly tested and needs a thoughtful review of the code. > > prime_vgem.c has some basic stuff, but it might actually encoding the > > broken behaviour. Would be good to extend/fix that I think so we don't > > entirely rely on review. We can't really build easily on top of the > > testcase Jason created for import/export, since for implicit sync we > > need some driver that attaches the fences for us. > > My question is if I can just send that to > intel-...@lists.freedesktop.org and the CI will pick it up? We do run all the prime_vgem tests. Btw if you do an igt patch, you can tell CI to run that igt patch series together with your kernel submission. Pretty useful for hackery like this, documented how it works here: https://intel-gfx-ci.01.org/test-with.html > > > > > There's also a vc4 one, but I guess that's less useful for us :-) > > > >> v2: fix the reference counting as well > >> v3: keep the excl fence handling as is for stable > >> v4: back to testing all fences, drop RCU > >> > >> Signed-off-by: Christian König > >> CC: sta...@vger.kernel.org > >> --- > >> drivers/dma-buf/dma-buf.c | 132 +- > >> include/linux/dma-buf.h | 2 +- > >> 2 files changed, 46 insertions(+), 88 deletions(-) > >> > >> diff --git a/drivers/dma-buf/dma-buf.c b/drivers/dma-buf/dma-buf.c > >> index eadd1eaa2fb5..192c4d34704b 100644 > >> --- a/drivers/dma-buf/dma-buf.c > >> +++ b/drivers/dma-buf/dma-buf.c > >> @@ -72,7 +72,7 @@ static void dma_buf_release(struct dentry *dentry) > >> * If you hit this BUG() it means someone dropped their ref to the > >> * dma-buf while still having pending operation to the buffer. > >> */ > >> - BUG_ON(dmabuf->cb_shared.active || dmabuf->cb_excl.active); > >> + BUG_ON(dmabuf->cb_in.active || dmabuf->cb_out.active); > >> > >> dmabuf->ops->release(dmabuf); > >> > >> @@ -202,16 +202,19 @@ static void dma_buf_poll_cb(struct dma_fence *fence, > >> struct dma_fence_cb *cb) > >> wake_up_locked_poll(dcb->poll, dcb->active); > >> dcb->active = 0; > >> spin_unlock_irqrestore(&dcb->poll->lock, flags); > >> + dma_fence_put(fence); > >> } > >> > >> static __poll_t dma_buf_poll(struct file *file, poll_table *poll) > >> { > >> + struct dma_buf_poll_cb_t *dcb; > >> struct dma_buf *dmabuf; > >> struct dma_resv *resv; > >> struct dma_resv_list *fobj; > >> - struct dma_fence *fence_excl; > >> + struct dma_fence *fence; > >> + unsigned shared_count; > >> __poll_t events; > >> - unsigned shared_count, seq; > >> + int r, i; > >> > >> dmabuf = file->private_data; > >> if (!dmabuf || !dmabuf->resv) > >> @@ -225,101 +228,56 @@ static __poll_t dma_buf_poll(struct file *file, > >> poll_table *poll) > >> if (!events) > >> return 0; > >> > >> -retry: > >> - seq = read_seqcount_begin(&resv->seq); > >> - rcu_read_lock(); > >> + dcb = events & EPOLLOUT ? &dmabuf->cb_out : &dmabuf->cb_in; > >> + > >> + /* Only queue a new one if we are not still waiting for the old > >> one */ > >> + spin_lock_irq(&dmabuf->poll.lock); > >> + if (dcb->active) > >> + events = 0; > >> + else > >> + dcb->active = events; > >> + spin_unlock_irq(&dmabuf->poll.lock); > >> + if (!events) > >> + return 0; > >> + > >> + dma_resv_lock(resv, NULL); > >> > >> - fobj = rcu_dereference(resv->fence); > >> - if (fobj) > >> + fobj = dma_resv_get_list(resv); > >> + if (fobj && events & EPOLLOUT) > >> shared_count = fobj->shared_count; > >> else > >> shared_count = 0; > >> - fence_excl = rcu_dereference(resv->fence_excl); > >> - if (read_seqcount_retry(&resv->seq, seq)) { > >> - rcu_read_unlock(); > >> - goto retry; > >> - }
Re: [PATCH 09/12] media: hantro: Enable H.264 on Rockchip VDPU2
Hi Ezequiel, Am 29.06.21 um 14:28 schrieb Ezequiel Garcia: Hi Alex, On Sat, 2021-06-26 at 10:33 +0200, Alex Bee wrote: Hi Ezequiel, Am 26.06.21 um 02:46 schrieb Ezequiel Garcia: (Adding Nicolas) Hi Alex, On Fri, 2021-06-25 at 01:13 +0200, Alex Bee wrote: Hi Ezequiel, Am 24.06.21 um 20:26 schrieb Ezequiel Garcia: Given H.264 support for VDPU2 was just added, let's enable it. For now, this is only enabled on platform that don't have an RKVDEC core, such as RK3328. Is there any reason, you do not want to enabe H.264 on RK3399? I know H.264 can be done by by rkvdec already, but from what I understand that shouldn't be an issue: The first decoder found that meets the requirements will be taken. Thanks a lot the review. I really doubt userspace stacks are readily supporting that strategy. The first decoder device supporting the codec format will be selected, I doubt features such as profile and levels are checked to decide which decoder to use. I'd rather play safe on the kernel side and avoid offering two competing devices for the same codec. I wasn't aware of that. Current ffmpeg v4l2_request implementation seems to not do VIDIOC_ENUM_FRAMESIZES - so we might end up being able to decode up to 1920x1088 only if hantro decoder is picked/checked first. Speaking of ffmpeg, now that MPEG-2, VP8 and H.264 control interfaces are stable, I think one of the next priorities would be to push Jonas' ffmpeg patches. It would be really cool if someone could take the lead on that front, as it would reduce kodi's out of tree stack, enable mpv, and so on. That's absolutely true. Note that Jonas himself started upstreaming those patches right after H264 uapi got stable [1]. Unfortunately I'm the absolut wrong person for doing/continuing this, since the very first time I ever looked at the implementation details was just for the response I wrote here. So I asked Jernej whos know all the details and contributed to those patches as well - he told me he'll continue whenever he finds time next. Best, Alex [1] https://patchwork.ffmpeg.org/project/ffmpeg/list/?series=2898
understanding virtio-gpu
Hello folks, I'm currently trying to understand how the virtio-gpu driver actually works and got a few noob questions: 1. virtio_gpu_pci_quirk(): * what is the explicit framebuffer removal about ? Do virtio-gpu devices support several framebuffer types (but only one at a time) ? How does it happen that we can have that vga framebuffer standing in our way in the first place ? * why is it necessary to rename the device with "pci:" prefix ? since (IMHO) virtio is an actual bus, that may even exist in HW, but there're also several different virtio transports (got word that somebody's also working on an socket-based one), it smells very strange to me, making it look like a pci device. does it only work w/ pci transport ? what's the background of this ? 2. features[] array: * virgl seems only supported on little endian, and the comment tells that's because virgl is sending the command stream in native endian. * IMHO, this approach isn't entirely correct, since here we're just looking whether the driver/guest side is LE, but looking at the host/device side. otoh, it should still work if both sides are BE. * shouldn't we add some endianess handshake to the protocol ? maybe both should announce what's their native endianess and whether they're capable of doing the conversion, so they can aggree on what to do exactly ? I'm currently trying to find ways for using virgl in containers instead of VMs, so the container workload doesn't need to have any gpu specific (userland) drivers anymore. Not sure whether I'll need special kernel support for this at all. thx, --mtx -- --- Hinweis: unverschlüsselte E-Mails können leicht abgehört und manipuliert werden ! Für eine vertrauliche Kommunikation senden Sie bitte ihren GPG/PGP-Schlüssel zu. --- Enrico Weigelt, metux IT consult Free software and Linux embedded engineering i...@metux.net -- +49-151-27565287
Re: [PATCH 1/2] drm/i915/ttm: Reorganize the ttm move code somewhat
On Wed, 30 Jun 2021 at 16:27, Thomas Hellström wrote: > > On Wed, 2021-06-30 at 15:19 +0100, Matthew Auld wrote: > > On Thu, 24 Jun 2021 at 20:31, Thomas Hellström > > wrote: > > > > > > In order to make the code a bit more readable and to facilitate > > > async memcpy moves, reorganize the move code a little. Determine > > > at an early stage whether to copy or to clear. > > > > > > Signed-off-by: Thomas Hellström > > > --- > > > drivers/gpu/drm/i915/gem/i915_gem_ttm.c | 70 ++--- > > > > > > 1 file changed, 40 insertions(+), 30 deletions(-) > > > > > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > index c39d982c4fa6..4e529adcdfc7 100644 > > > --- a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > +++ b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > @@ -431,6 +431,7 @@ i915_ttm_resource_get_st(struct > > > drm_i915_gem_object *obj, > > > } > > > > > > static int i915_ttm_accel_move(struct ttm_buffer_object *bo, > > > + bool clear, > > >struct ttm_resource *dst_mem, > > >struct sg_table *dst_st) > > > { > > > @@ -449,13 +450,10 @@ static int i915_ttm_accel_move(struct > > > ttm_buffer_object *bo, > > > return -EINVAL; > > > > > > dst_level = i915_ttm_cache_level(i915, dst_mem, ttm); > > > - if (!ttm || !ttm_tt_is_populated(ttm)) { > > > + if (clear) { > > > if (bo->type == ttm_bo_type_kernel) > > > return -EINVAL; > > > > Was that meant to be: > > return 0: > > > > ? > > > > Also does that mean we are incorrectly falling back to memset, for > > non-userspace objects, instead of making it a noop? > > No, we're deliberately falling back to memset for non-userspace > objects, but the logic only memsets in the BO_ALLOC_CPU_CLEAR case if > everything is implemented correctly. > > > > > > > > > - if (ttm && !(ttm->page_flags & > > > TTM_PAGE_FLAG_ZERO_ALLOC)) > > > - return 0; > > > - > > > intel_engine_pm_get(i915->gt.migrate.context- > > > >engine); > > > ret = intel_context_migrate_clear(i915- > > > >gt.migrate.context, NULL, > > > dst_st->sgl, > > > dst_level, > > > @@ -489,27 +487,53 @@ static int i915_ttm_accel_move(struct > > > ttm_buffer_object *bo, > > > return ret; > > > } > > > > > > -static int i915_ttm_move(struct ttm_buffer_object *bo, bool evict, > > > -struct ttm_operation_ctx *ctx, > > > -struct ttm_resource *dst_mem, > > > -struct ttm_place *hop) > > > +static void __i915_ttm_move(struct ttm_buffer_object *bo, bool > > > clear, > > > + struct ttm_resource *dst_mem, > > > + struct sg_table *dst_st) > > > { > > > struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); > > > - struct ttm_resource_manager *dst_man = > > > - ttm_manager_type(bo->bdev, dst_mem->mem_type); > > > struct intel_memory_region *dst_reg, *src_reg; > > > union { > > > struct ttm_kmap_iter_tt tt; > > > struct ttm_kmap_iter_iomap io; > > > } _dst_iter, _src_iter; > > > struct ttm_kmap_iter *dst_iter, *src_iter; > > > - struct sg_table *dst_st; > > > int ret; > > > > > > dst_reg = i915_ttm_region(bo->bdev, dst_mem->mem_type); > > > src_reg = i915_ttm_region(bo->bdev, bo->resource- > > > >mem_type); > > > GEM_BUG_ON(!dst_reg || !src_reg); > > > > > > + ret = i915_ttm_accel_move(bo, clear, dst_mem, dst_st); > > > + if (ret) { > > > > One future consideration is flat CCS where I don't think we can > > easily > > fall back to memcpy for userspace objects. Maybe we can make this > > fallback conditional on DG1 or !ALLOC_USER for now, or just add a > > TODO? > > Ugh. Is that true for both clearing and copying, or is it only copying? With clearing I think we are required to nuke the aux CCS state using some special blitter command. For copying/moving I think it's a similar story, where special care might be needed for the aux state, which likely requires the blitter. Although tbh I don't really remember all the details. > > Problem is if we hit an engine reset and fence error during initial > clearing / swapin, the plan moving forward is to intercept that and > resort to cpu clearing / copying for security reasons. In the worst > case we at least need to be able to clear. > > /Thomas > > > > > > > + dst_iter = !cpu_maps_iomem(dst_mem) ? > > > + ttm_kmap_iter_tt_init(&_dst_iter.tt, bo- > > > >ttm) : > > > + ttm_kmap_iter_iomap_init(&_dst_iter.io, > > > &dst_reg->iomap, > > > +dst_st, dst_reg- >
Re: [Intel-gfx] [PATCH 1/2] drm/i915/ttm: Reorganize the ttm move code somewhat
On Wed, Jun 30, 2021 at 6:54 PM Matthew Auld wrote: > > On Wed, 30 Jun 2021 at 16:27, Thomas Hellström > wrote: > > > > On Wed, 2021-06-30 at 15:19 +0100, Matthew Auld wrote: > > > On Thu, 24 Jun 2021 at 20:31, Thomas Hellström > > > wrote: > > > > > > > > In order to make the code a bit more readable and to facilitate > > > > async memcpy moves, reorganize the move code a little. Determine > > > > at an early stage whether to copy or to clear. > > > > > > > > Signed-off-by: Thomas Hellström > > > > --- > > > > drivers/gpu/drm/i915/gem/i915_gem_ttm.c | 70 ++--- > > > > > > > > 1 file changed, 40 insertions(+), 30 deletions(-) > > > > > > > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > > b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > > index c39d982c4fa6..4e529adcdfc7 100644 > > > > --- a/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > > +++ b/drivers/gpu/drm/i915/gem/i915_gem_ttm.c > > > > @@ -431,6 +431,7 @@ i915_ttm_resource_get_st(struct > > > > drm_i915_gem_object *obj, > > > > } > > > > > > > > static int i915_ttm_accel_move(struct ttm_buffer_object *bo, > > > > + bool clear, > > > >struct ttm_resource *dst_mem, > > > >struct sg_table *dst_st) > > > > { > > > > @@ -449,13 +450,10 @@ static int i915_ttm_accel_move(struct > > > > ttm_buffer_object *bo, > > > > return -EINVAL; > > > > > > > > dst_level = i915_ttm_cache_level(i915, dst_mem, ttm); > > > > - if (!ttm || !ttm_tt_is_populated(ttm)) { > > > > + if (clear) { > > > > if (bo->type == ttm_bo_type_kernel) > > > > return -EINVAL; > > > > > > Was that meant to be: > > > return 0: > > > > > > ? > > > > > > Also does that mean we are incorrectly falling back to memset, for > > > non-userspace objects, instead of making it a noop? > > > > No, we're deliberately falling back to memset for non-userspace > > objects, but the logic only memsets in the BO_ALLOC_CPU_CLEAR case if > > everything is implemented correctly. > > > > > > > > > > > > > - if (ttm && !(ttm->page_flags & > > > > TTM_PAGE_FLAG_ZERO_ALLOC)) > > > > - return 0; > > > > - > > > > intel_engine_pm_get(i915->gt.migrate.context- > > > > >engine); > > > > ret = intel_context_migrate_clear(i915- > > > > >gt.migrate.context, NULL, > > > > dst_st->sgl, > > > > dst_level, > > > > @@ -489,27 +487,53 @@ static int i915_ttm_accel_move(struct > > > > ttm_buffer_object *bo, > > > > return ret; > > > > } > > > > > > > > -static int i915_ttm_move(struct ttm_buffer_object *bo, bool evict, > > > > -struct ttm_operation_ctx *ctx, > > > > -struct ttm_resource *dst_mem, > > > > -struct ttm_place *hop) > > > > +static void __i915_ttm_move(struct ttm_buffer_object *bo, bool > > > > clear, > > > > + struct ttm_resource *dst_mem, > > > > + struct sg_table *dst_st) > > > > { > > > > struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); > > > > - struct ttm_resource_manager *dst_man = > > > > - ttm_manager_type(bo->bdev, dst_mem->mem_type); > > > > struct intel_memory_region *dst_reg, *src_reg; > > > > union { > > > > struct ttm_kmap_iter_tt tt; > > > > struct ttm_kmap_iter_iomap io; > > > > } _dst_iter, _src_iter; > > > > struct ttm_kmap_iter *dst_iter, *src_iter; > > > > - struct sg_table *dst_st; > > > > int ret; > > > > > > > > dst_reg = i915_ttm_region(bo->bdev, dst_mem->mem_type); > > > > src_reg = i915_ttm_region(bo->bdev, bo->resource- > > > > >mem_type); > > > > GEM_BUG_ON(!dst_reg || !src_reg); > > > > > > > > + ret = i915_ttm_accel_move(bo, clear, dst_mem, dst_st); > > > > + if (ret) { > > > > > > One future consideration is flat CCS where I don't think we can > > > easily > > > fall back to memcpy for userspace objects. Maybe we can make this > > > fallback conditional on DG1 or !ALLOC_USER for now, or just add a > > > TODO? > > > > Ugh. Is that true for both clearing and copying, or is it only copying? > > With clearing I think we are required to nuke the aux CCS state using > some special blitter command. > > For copying/moving I think it's a similar story, where special care > might be needed for the aux state, which likely requires the blitter. > Although tbh I don't really remember all the details. There's more than just flat CCS, for dg2 we'll also support resizeable BAR with the goal to make the non-mappable lmem available too. Afaik there's no fallback way to access that memory without a copy engine. I think on those platforms we simply have to go back to wedging the driver if reset of the copy eng
Re: [PATCH v3 1/2] drm/i915: Use the correct IRQ during resume
On Wed, Jun 30, 2021 at 4:18 PM Thomas Zimmermann wrote: > > Hi > > Am 30.06.21 um 12:49 schrieb Daniel Vetter: > > On Wed, Jun 30, 2021 at 11:52:27AM +0200, Thomas Zimmermann wrote: > >> The code in xcs_resume() probably didn't work as intended. It uses > >> struct drm_device.irq, which is allocated to 0, but never initialized > >> by i915 to the device's interrupt number. > >> > >> v3: > >> * also use intel_synchronize_hardirq() at another callsite > >> v2: > >> * wrap irq code in intel_synchronize_hardirq() (Ville) > >> > >> Signed-off-by: Thomas Zimmermann > >> Fixes: 536f77b1caa0 ("drm/i915/gt: Call stop_ring() from ring resume, > >> again") > >> Cc: Chris Wilson > >> Cc: Mika Kuoppala > >> Cc: Daniel Vetter > >> Cc: Rodrigo Vivi > >> Cc: Joonas Lahtinen > >> Cc: Maarten Lankhorst > >> Cc: Lucas De Marchi > >> --- > >> drivers/gpu/drm/i915/gt/intel_engine_cs.c | 2 +- > >> drivers/gpu/drm/i915/gt/intel_ring_submission.c | 2 +- > >> drivers/gpu/drm/i915/i915_irq.c | 5 + > >> drivers/gpu/drm/i915/i915_irq.h | 1 + > >> 4 files changed, 8 insertions(+), 2 deletions(-) > >> > >> diff --git a/drivers/gpu/drm/i915/gt/intel_engine_cs.c > >> b/drivers/gpu/drm/i915/gt/intel_engine_cs.c > >> index 88694822716a..5ca3d1664335 100644 > >> --- a/drivers/gpu/drm/i915/gt/intel_engine_cs.c > >> +++ b/drivers/gpu/drm/i915/gt/intel_engine_cs.c > >> @@ -1229,7 +1229,7 @@ bool intel_engine_is_idle(struct intel_engine_cs > >> *engine) > >> return true; > >> > >> /* Waiting to drain ELSP? */ > >> -synchronize_hardirq(to_pci_dev(engine->i915->drm.dev)->irq); > >> +intel_synchronize_hardirq(engine->i915); > >> intel_engine_flush_submission(engine); > >> > >> /* ELSP is empty, but there are ready requests? E.g. after reset */ > >> diff --git a/drivers/gpu/drm/i915/gt/intel_ring_submission.c > >> b/drivers/gpu/drm/i915/gt/intel_ring_submission.c > >> index 5d42a12ef3d6..1b5a22a83db6 100644 > >> --- a/drivers/gpu/drm/i915/gt/intel_ring_submission.c > >> +++ b/drivers/gpu/drm/i915/gt/intel_ring_submission.c > >> @@ -185,7 +185,7 @@ static int xcs_resume(struct intel_engine_cs *engine) > >> ring->head, ring->tail); > >> > >> /* Double check the ring is empty & disabled before we resume */ > >> -synchronize_hardirq(engine->i915->drm.irq); > >> +intel_synchronize_hardirq(engine->i915); > >> if (!stop_ring(engine)) > >> goto err; > >> > >> diff --git a/drivers/gpu/drm/i915/i915_irq.c > >> b/drivers/gpu/drm/i915/i915_irq.c > >> index 7d0ce8b9f8ed..2203dca19895 100644 > >> --- a/drivers/gpu/drm/i915/i915_irq.c > >> +++ b/drivers/gpu/drm/i915/i915_irq.c > >> @@ -4575,3 +4575,8 @@ void intel_synchronize_irq(struct drm_i915_private > >> *i915) > >> { > >> synchronize_irq(to_pci_dev(i915->drm.dev)->irq); > >> } > >> + > >> +void intel_synchronize_hardirq(struct drm_i915_private *i915) > >> +{ > >> +synchronize_hardirq(to_pci_dev(i915->drm.dev)->irq); > > > > I honestly think the hardirq here is about as much cargo-culted as using > > the wrong irq number. > > > > I'd just use intel_synchronize_irq in both places and see whether CI > > complains, then go with that. > > Well, ok. I don't think I have Sandybridge HW available. Would the Intel > CI infrastructure catch any problems with such a change? If there's anything obvious busted with it it should catch it (like if we end up calling synchronize_irq from softirq context, where only synchronize_hardirq is allowed, but I don't think that's the case). And if I'm wrong we know what kind of comment to put there to explain why things are different. -Daniel > Best regards > Thomas > > > -Daniel > > > >> +} > >> diff --git a/drivers/gpu/drm/i915/i915_irq.h > >> b/drivers/gpu/drm/i915/i915_irq.h > >> index db34d5dbe402..e43b6734f21b 100644 > >> --- a/drivers/gpu/drm/i915/i915_irq.h > >> +++ b/drivers/gpu/drm/i915/i915_irq.h > >> @@ -94,6 +94,7 @@ void intel_runtime_pm_disable_interrupts(struct > >> drm_i915_private *dev_priv); > >> void intel_runtime_pm_enable_interrupts(struct drm_i915_private > >> *dev_priv); > >> bool intel_irqs_enabled(struct drm_i915_private *dev_priv); > >> void intel_synchronize_irq(struct drm_i915_private *i915); > >> +void intel_synchronize_hardirq(struct drm_i915_private *i915); > >> > >> int intel_get_crtc_scanline(struct intel_crtc *crtc); > >> void gen8_irq_power_well_post_enable(struct drm_i915_private *dev_priv, > >> -- > >> 2.32.0 > >> > > > > -- > Thomas Zimmermann > Graphics Driver Developer > SUSE Software Solutions Germany GmbH > Maxfeldstr. 5, 90409 Nürnberg, Germany > (HRB 36809, AG Nürnberg) > Geschäftsführer: Felix Imendörffer > -- Daniel Vetter Software Engineer, Intel Corporation http://blog.ffwll.ch
Re: [PATCH 1/2] drm/i915/gem: Make our dma-buf exporter dynamic
On Wed, Jun 30, 2021 at 4:01 PM Daniel Vetter wrote: > On Wed, Jun 30, 2021 at 03:07:00PM +0200, Thomas Hellström wrote: > > If our exported dma-bufs are imported by another instance of our driver, > > that instance will typically have the imported dma-bufs locked during > > dma_buf_map_attachment(). But the exporter also locks the same reservation > > object in the map_dma_buf() callback, which leads to recursive locking. > > > > Add a live selftest to exercise both dynamic and non-dynamic exports, > > and as a workaround until we fully support dynamic import and export, > > declare the exporter dynamic by providing pin() and unpin() implementations. > > For dynamic importers, make sure we keep the pinning also in map_dma_buf(), > > to ensure we never need to call dma_buf_move_notify(). > > Calling dma_buf_move_notify() is at the discretion of the exporter. > > > > v2: > > - Extend the selftest with a fake dynamic importer. > > - Provide real pin and unpin callbacks to not abuse the interface. > > > > Reported-by: Michael J. Ruhl > > Signed-off-by: Thomas Hellström > > I'm not happy with this, because i915 is currently violating the dma-resv > fencing rules for dynamic dma-buf. > > Yes since this is just the exporter we can probably get away with yolo'ing > things, but Christian and me just spend a lot of angry typing figuring out > what the rules actually are, so I really don't like bending them even more > just because it's less typing. To clarify what I meant here: I think the code is correct in the sense that it's not breaking any other existing code upstream in a functional or security relevant way. What I meant with yolo merging is that if we land some dynamic dma-buf exporter support just to fix a bug which with slightly more lines can be fixed without resorting to quickly enabling dynamic dma-buf exporting while a) we know i915 is breaking dma-resv rules already and b) there was just a few weeks of rather angry discussions on this topic. That's just a recipe to piss people off, at least if I'd be in Christian's shoes and see this land I'd get furious. So yolo on the collaboration and people side of things, not so much technically incorrect. Plus with the sketch I described below we can fix the underlying issue we're seeing in a clean way, by essentially aligning what i915 does to what all other non-dynamic dma-buf ttm driver implementations do in drm_prime.c. Defacto that's the only way that works, and it is the contract for non-dynamic dma-buf for a driver using dma_resv_lock. The only reason we could get away without lockdep splats with our current dma-buf code in i915 of attempting to handle dma-buf more dynamic was because we used our completely independent locking design (and also never shared with another i915 instance). That illusion falls apart with i915 using dma-resv and with now multiple i915 instances being possible. tldr; Using this way we can cleanly untangle solving the locking issue at hand from the fairly bigger topic of how we are going to support dynamic dma-buf and p2p and all that in i915. I hope this explains a bit better why I have my take here like that. -Daniel > All we need for a quick interim fix is to not take the dma_resv_lock from > our map/unamp callbacks. Pinning our backing storage from attach/detach > callbacks (which are also called under dma_resv_lock) would also achieve > that, without mudding any waters. So essentially just moving the > pin/unpin_pages_unlocked and we should be good, which is almost as little > typing. > > Michael, since Thomas is on vacations now, care to type that up? The > selftest is imo solid. > > This is also consistent with what all other ttm based drivers do (aside > from amdgpu, which is fully dynamic), see drm_gem_map_attach in > drm_prime.c > > Adding Christian as fyi. > -Daniel > > > --- > > drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c| 31 - > > .../drm/i915/gem/selftests/i915_gem_dmabuf.c | 116 +- > > 2 files changed, 143 insertions(+), 4 deletions(-) > > > > diff --git a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > > b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > > index 616c3a2f1baf..918c19df7b66 100644 > > --- a/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > > +++ b/drivers/gpu/drm/i915/gem/i915_gem_dmabuf.c > > @@ -12,6 +12,8 @@ > > #include "i915_gem_object.h" > > #include "i915_scatterlist.h" > > > > +I915_SELFTEST_DECLARE(static bool force_different_devices;) > > + > > static struct drm_i915_gem_object *dma_buf_to_obj(struct dma_buf *buf) > > { > > return to_intel_bo(buf->priv); > > @@ -25,7 +27,14 @@ static struct sg_table *i915_gem_map_dma_buf(struct > > dma_buf_attachment *attachme > > struct scatterlist *src, *dst; > > int ret, i; > > > > - ret = i915_gem_object_pin_pages_unlocked(obj); > > + assert_object_held(obj); > > + > > + /* > > + * Note. In the dynamic importer case, the object is not yet pinned. > > + * Let's pin it here to avoid h
Re: [PATCH 47/47] drm/i915/guc: Unblock GuC submission on Gen11+
On Wed, Jun 30, 2021 at 11:22:38AM +0300, Martin Peres wrote: > > > On 24/06/2021 10:05, Matthew Brost wrote: > > From: Daniele Ceraolo Spurio > > > > Unblock GuC submission on Gen11+ platforms. > > > > Signed-off-by: Michal Wajdeczko > > Signed-off-by: Daniele Ceraolo Spurio > > Signed-off-by: Matthew Brost > > --- > > drivers/gpu/drm/i915/gt/uc/intel_guc.h| 1 + > > drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c | 8 > > drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h | 3 +-- > > drivers/gpu/drm/i915/gt/uc/intel_uc.c | 14 +- > > 4 files changed, 19 insertions(+), 7 deletions(-) > > > > diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc.h > > b/drivers/gpu/drm/i915/gt/uc/intel_guc.h > > index fae01dc8e1b9..77981788204f 100644 > > --- a/drivers/gpu/drm/i915/gt/uc/intel_guc.h > > +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc.h > > @@ -54,6 +54,7 @@ struct intel_guc { > > struct ida guc_ids; > > struct list_head guc_id_list; > > + bool submission_supported; > > bool submission_selected; > > struct i915_vma *ads_vma; > > diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c > > b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c > > index a427336ce916..405339202280 100644 > > --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c > > +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c > > @@ -2042,6 +2042,13 @@ void intel_guc_submission_disable(struct intel_guc > > *guc) > > /* Note: By the time we're here, GuC may have already been reset */ > > } > > +static bool __guc_submission_supported(struct intel_guc *guc) > > +{ > > + /* GuC submission is unavailable for pre-Gen11 */ > > + return intel_guc_is_supported(guc) && > > + INTEL_GEN(guc_to_gt(guc)->i915) >= 11; > > +} > > + > > static bool __guc_submission_selected(struct intel_guc *guc) > > { > > struct drm_i915_private *i915 = guc_to_gt(guc)->i915; > > @@ -2054,6 +2061,7 @@ static bool __guc_submission_selected(struct > > intel_guc *guc) > > void intel_guc_submission_init_early(struct intel_guc *guc) > > { > > + guc->submission_supported = __guc_submission_supported(guc); > > guc->submission_selected = __guc_submission_selected(guc); > > } > > diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h > > b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h > > index a2a3fad72be1..be767eb6ff71 100644 > > --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h > > +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h > > @@ -37,8 +37,7 @@ int intel_guc_wait_for_pending_msg(struct intel_guc *guc, > > static inline bool intel_guc_submission_is_supported(struct intel_guc > > *guc) > > { > > - /* XXX: GuC submission is unavailable for now */ > > - return false; > > + return guc->submission_supported; > > } > > static inline bool intel_guc_submission_is_wanted(struct intel_guc *guc) > > diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc.c > > b/drivers/gpu/drm/i915/gt/uc/intel_uc.c > > index 7a69c3c027e9..61be0aa81492 100644 > > --- a/drivers/gpu/drm/i915/gt/uc/intel_uc.c > > +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc.c > > @@ -34,8 +34,15 @@ static void uc_expand_default_options(struct intel_uc > > *uc) > > return; > > } > > - /* Default: enable HuC authentication only */ > > - i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; > > + /* Intermediate platforms are HuC authentication only */ > > + if (IS_DG1(i915) || IS_ALDERLAKE_S(i915)) { > > + drm_dbg(&i915->drm, "Disabling GuC only due to old platform\n"); > > This comment does not seem accurate, given that DG1 is barely out, and ADL > is not out yet. How about: > > "Disabling GuC on untested platforms"? This isn't my comment but it seems right to me. AFAIK this describes the current PR but it is subject to change (i.e. we may enable GuC on DG1 by default at some point). > > > + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; > > + return; > > + } > > + > > + /* Default: enable HuC authentication and GuC submission */ > > + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC | ENABLE_GUC_SUBMISSION; > > This seems to be in contradiction with the GuC submission plan which states: > > "Not enabled by default on any current platforms but can be enabled via > modparam enable_guc". > I don't believe any current platform gets this point where GuC submission would be enabled by default. The first would be ADL-P which isn't out yet. > When you rework the patch, could you please add a warning when the user > force-enables the GuC Command Submission? Something like: > > "WARNING: The user force-enabled the experimental GuC command submission > backend using i915.enable_guc. Please disable it if experiencing stability > issues. No bug reports will be accepted on this backend". > > This should allow you to work on the backend, while communicating clearly to > users that it is not ready just yet. Once i
[PATCH 1/2 v2] drm/panel: Add DT bindings for Samsung LMS380KF01
This adds device tree bindings for the Samsung Mobile Displays LMS380KF01 RGB DPI display panel. Cc: devicet...@vger.kernel.org Cc: phone-de...@vger.kernel.org Cc: Douglas Anderson Cc: Noralf Trønnes Signed-off-by: Linus Walleij --- ChangeLog v1->v2: - Expect SPI bindings to be pulled in for the client and state spi-cpha: true etc. - Make port a required node. - Update the example to use a proper SPI controller (spi-gpio) so we get full validation of the example. --- .../display/panel/samsung,lms380kf01.yaml | 97 +++ 1 file changed, 97 insertions(+) create mode 100644 Documentation/devicetree/bindings/display/panel/samsung,lms380kf01.yaml diff --git a/Documentation/devicetree/bindings/display/panel/samsung,lms380kf01.yaml b/Documentation/devicetree/bindings/display/panel/samsung,lms380kf01.yaml new file mode 100644 index ..ebc33c36c124 --- /dev/null +++ b/Documentation/devicetree/bindings/display/panel/samsung,lms380kf01.yaml @@ -0,0 +1,97 @@ +# SPDX-License-Identifier: (GPL-2.0-only OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/display/panel/samsung,lms380kf01.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Samsung LMS380KF01 display panel + +description: The LMS380KF01 is a 480x800 DPI display panel from Samsung Mobile + Displays (SMD) utilizing the WideChips WS2401 display controller. It can be + used with internal or external backlight control. + +maintainers: + - Linus Walleij + +allOf: + - $ref: panel-common.yaml# + +properties: + compatible: +const: samsung,lms380kf01 + + reg: true + + interrupts: +description: provides an optional ESD (electrostatic discharge) + interrupt that signals abnormalities in the display hardware. + This can also be raised for other reasons like erroneous + configuration. +maxItems: 1 + + reset-gpios: true + + vci-supply: +description: regulator that supplies the VCI analog voltage + usually around 3.0 V + + vccio-supply: +description: regulator that supplies the VCCIO voltage usually + around 1.8 V + + backlight: true + + spi-cpha: true + + spi-cpol: true + + spi-max-frequency: +maximum: 120 + + port: true + +required: + - compatible + - reg + - spi-cpha + - spi-cpol + - port + +additionalProperties: false + +examples: + - | +#include +#include + +spi { + compatible = "spi-gpio"; + sck-gpios = <&gpio 0 GPIO_ACTIVE_HIGH>; + miso-gpios = <&gpio 1 GPIO_ACTIVE_HIGH>; + mosi-gpios = <&gpio 2 GPIO_ACTIVE_HIGH>; + cs-gpios = <&gpio 3 GPIO_ACTIVE_HIGH>; + num-chipselects = <1>; + #address-cells = <1>; + #size-cells = <0>; + + panel@0 { +compatible = "samsung,lms380kf01"; +spi-max-frequency = <120>; +spi-cpha; +spi-cpol; +reg = <0>; +vci-supply = <&lcd_3v0_reg>; +vccio-supply = <&lcd_1v8_reg>; +reset-gpios = <&gpio 4 GPIO_ACTIVE_LOW>; +interrupt-parent = <&gpio>; +interrupts = <5 IRQ_TYPE_EDGE_RISING>; + +port { + panel_in: endpoint { +remote-endpoint = <&display_out>; + }; +}; + }; +}; + +... -- 2.31.1
[PATCH 2/2 v2] drm/panel: ws2401: Add driver for WideChips WS2401
This adds a driver for panels based on the WideChips WS2401 display controller. This display controller is used in the Samsung LMS380KF01 display found in the Samsung GT-I8160 (Codina) mobile phone and possibly others. As is common with Samsung displays manufacturer commands are necessary to configure the display to a working state. The display optionally supports internal backlight control, but can also use an external backlight. This driver re-uses the DBI infrastructure to communicate with the display. Cc: phone-de...@vger.kernel.org Cc: Douglas Anderson Cc: Noralf Trønnes Signed-off-by: Linus Walleij --- ChangeLog v1->v2: - Disable the backlight in ->unprepare() before entering sleep mode. - If we are not using internal backlight, close the L2 access after initializing. - Depromote some talkative dev_info()s to dev_dbg(). - Power up and read the MTP values before we register the display. This works fine and is probably how MTP is supposed to work. - Fix the set-up of gamma values, this was found in the GT-I8160 HD kernel tree. - Bail out properly if drm_panel_of_backlight() returns -EDEFER_PROBE. - Drop OF from dependencies since drm_panel_of_backlight() has static inline stubs in the header file. - Sort MAINTAINERS properly. - Alphabetize includes - Use format specifier %#02x so we get 0x... output in debug - Drop unnecessary braces around if () in debug macro - Drop unused include. --- MAINTAINERS | 7 + drivers/gpu/drm/panel/Kconfig | 9 + drivers/gpu/drm/panel/Makefile| 1 + .../gpu/drm/panel/panel-widechips-ws2401.c| 440 ++ 4 files changed, 457 insertions(+) create mode 100644 drivers/gpu/drm/panel/panel-widechips-ws2401.c diff --git a/MAINTAINERS b/MAINTAINERS index bd7aff0c120f..10bba4be1678 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -5956,6 +5956,13 @@ T: git git://people.freedesktop.org/~sroland/linux F: drivers/gpu/drm/vmwgfx/ F: include/uapi/drm/vmwgfx_drm.h +DRM DRIVER FOR WIDECHIPS WS2401 PANELS +M: Linus Walleij +S: Maintained +T: git git://anongit.freedesktop.org/drm/drm-misc +F: Documentation/devicetree/bindings/display/panel/samsung,lms380kf01.yaml +F: drivers/gpu/drm/panel/panel-widechips-ws2401.c + DRM DRIVERS M: David Airlie M: Daniel Vetter diff --git a/drivers/gpu/drm/panel/Kconfig b/drivers/gpu/drm/panel/Kconfig index 4894913936e9..319fa44c4bc9 100644 --- a/drivers/gpu/drm/panel/Kconfig +++ b/drivers/gpu/drm/panel/Kconfig @@ -552,6 +552,15 @@ config DRM_PANEL_VISIONOX_RM69299 Say Y here if you want to enable support for Visionox RM69299 DSI Video Mode panel. +config DRM_PANEL_WIDECHIPS_WS2401 + tristate "Widechips WS2401 DPI panel driver" + depends on SPI && GPIOLIB + depends on BACKLIGHT_CLASS_DEVICE + select DRM_MIPI_DBI + help + Say Y here if you want to enable support for the Widechips WS2401 DPI + 480x800 display controller used in panels such as Samsung LMS380KF01. + config DRM_PANEL_XINPENG_XPP055C272 tristate "Xinpeng XPP055C272 panel driver" depends on OF diff --git a/drivers/gpu/drm/panel/Makefile b/drivers/gpu/drm/panel/Makefile index cae4d976c069..d94c27df17aa 100644 --- a/drivers/gpu/drm/panel/Makefile +++ b/drivers/gpu/drm/panel/Makefile @@ -58,4 +58,5 @@ obj-$(CONFIG_DRM_PANEL_TPO_TD043MTEA1) += panel-tpo-td043mtea1.o obj-$(CONFIG_DRM_PANEL_TPO_TPG110) += panel-tpo-tpg110.o obj-$(CONFIG_DRM_PANEL_TRULY_NT35597_WQXGA) += panel-truly-nt35597.o obj-$(CONFIG_DRM_PANEL_VISIONOX_RM69299) += panel-visionox-rm69299.o +obj-$(CONFIG_DRM_PANEL_WIDECHIPS_WS2401) += panel-widechips-ws2401.o obj-$(CONFIG_DRM_PANEL_XINPENG_XPP055C272) += panel-xinpeng-xpp055c272.o diff --git a/drivers/gpu/drm/panel/panel-widechips-ws2401.c b/drivers/gpu/drm/panel/panel-widechips-ws2401.c new file mode 100644 index ..e5731c08fc94 --- /dev/null +++ b/drivers/gpu/drm/panel/panel-widechips-ws2401.c @@ -0,0 +1,440 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Panel driver for the WideChips WS2401 480x800 DPI RGB panel, used in + * the Samsung Mobile Display (SMD) LMS380KF01. + * Found in the Samsung Galaxy Ace 2 GT-I8160 mobile phone. + * Linus Walleij + * Inspired by code and know-how in the vendor driver by Gareth Phillips. + */ +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#define WS2401_RESCTL 0xb8 /* Resolution select control */ +#define WS2401_PSMPS 0xbd /* SMPS positive control */ +#define WS2401_NSMPS 0xbe /* SMPS negative control */ +#define WS2401_SMPS0xbf +#define WS2401_BCMODE 0xc1 /* Backlight control mode */ +#define WS2401_WRBLCTL 0xc3 /* Backlight control */ +#define WS2401_WRDISBV 0xc4 /* W
Re: [PATCH 47/47] drm/i915/guc: Unblock GuC submission on Gen11+
On 6/30/2021 01:22, Martin Peres wrote: On 24/06/2021 10:05, Matthew Brost wrote: From: Daniele Ceraolo Spurio Unblock GuC submission on Gen11+ platforms. Signed-off-by: Michal Wajdeczko Signed-off-by: Daniele Ceraolo Spurio Signed-off-by: Matthew Brost --- drivers/gpu/drm/i915/gt/uc/intel_guc.h | 1 + drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c | 8 drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h | 3 +-- drivers/gpu/drm/i915/gt/uc/intel_uc.c | 14 +- 4 files changed, 19 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc.h b/drivers/gpu/drm/i915/gt/uc/intel_guc.h index fae01dc8e1b9..77981788204f 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc.h @@ -54,6 +54,7 @@ struct intel_guc { struct ida guc_ids; struct list_head guc_id_list; + bool submission_supported; bool submission_selected; struct i915_vma *ads_vma; diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c index a427336ce916..405339202280 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.c @@ -2042,6 +2042,13 @@ void intel_guc_submission_disable(struct intel_guc *guc) /* Note: By the time we're here, GuC may have already been reset */ } +static bool __guc_submission_supported(struct intel_guc *guc) +{ + /* GuC submission is unavailable for pre-Gen11 */ + return intel_guc_is_supported(guc) && + INTEL_GEN(guc_to_gt(guc)->i915) >= 11; +} + static bool __guc_submission_selected(struct intel_guc *guc) { struct drm_i915_private *i915 = guc_to_gt(guc)->i915; @@ -2054,6 +2061,7 @@ static bool __guc_submission_selected(struct intel_guc *guc) void intel_guc_submission_init_early(struct intel_guc *guc) { + guc->submission_supported = __guc_submission_supported(guc); guc->submission_selected = __guc_submission_selected(guc); } diff --git a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h index a2a3fad72be1..be767eb6ff71 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h +++ b/drivers/gpu/drm/i915/gt/uc/intel_guc_submission.h @@ -37,8 +37,7 @@ int intel_guc_wait_for_pending_msg(struct intel_guc *guc, static inline bool intel_guc_submission_is_supported(struct intel_guc *guc) { - /* XXX: GuC submission is unavailable for now */ - return false; + return guc->submission_supported; } static inline bool intel_guc_submission_is_wanted(struct intel_guc *guc) diff --git a/drivers/gpu/drm/i915/gt/uc/intel_uc.c b/drivers/gpu/drm/i915/gt/uc/intel_uc.c index 7a69c3c027e9..61be0aa81492 100644 --- a/drivers/gpu/drm/i915/gt/uc/intel_uc.c +++ b/drivers/gpu/drm/i915/gt/uc/intel_uc.c @@ -34,8 +34,15 @@ static void uc_expand_default_options(struct intel_uc *uc) return; } - /* Default: enable HuC authentication only */ - i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; + /* Intermediate platforms are HuC authentication only */ + if (IS_DG1(i915) || IS_ALDERLAKE_S(i915)) { + drm_dbg(&i915->drm, "Disabling GuC only due to old platform\n"); This comment does not seem accurate, given that DG1 is barely out, and ADL is not out yet. How about: "Disabling GuC on untested platforms"? Just because something is not in the shops yet does not mean it is new. Technology is always obsolete by the time it goes on sale. And the issue is not a lack of testing, it is a question of whether we are allowed to change the default on something that has already started being used by customers or not (including pre-release beta customers). I.e. it is basically a political decision not an engineering decision. + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC; + return; + } + + /* Default: enable HuC authentication and GuC submission */ + i915->params.enable_guc = ENABLE_GUC_LOAD_HUC | ENABLE_GUC_SUBMISSION; This seems to be in contradiction with the GuC submission plan which states: "Not enabled by default on any current platforms but can be enabled via modparam enable_guc". All current platforms have already been explicitly tested for above. This is setting the default on newer platforms - ADL-P and later. For which the official expectation is to have GuC enabled. When you rework the patch, could you please add a warning when the user force-enables the GuC Command Submission? There already is one. If you set the module parameter then the kernel is tainted. That means 'here be dragons' - you have done something officially not supported to your kernel so all bets are off, if it blows up it is your own problem. Something like: "WARNING: The user force-enabled the experimental GuC command submission backend using i915.enable_guc. Please disable it if experie
[Bug 213391] AMDGPU retries page fault with some specific processes amdgpu and sometimes followed [gfxhub0] retry page fault until *ERROR* ring gfx timeout, but soft recovered
https://bugzilla.kernel.org/show_bug.cgi?id=213391 --- Comment #28 from Leandro Jacques (ls...@yahoo.com) --- (In reply to Leandro Jacques from comment #25) Until now, no problems. So the problem is with newer firmware versions, working without any issues since 2021-06-21 19:26:28 UTC with version 20210315 -- You may reply to this email to add a comment. You are receiving this mail because: You are watching the assignee of the bug.
[Bug 209457] AMDGPU resume fail with RX 580 GPU
https://bugzilla.kernel.org/show_bug.cgi?id=209457 --- Comment #30 from Leandro Jacques (ls...@yahoo.com) --- (In reply to Leandro Jacques from comment #29) Until now, no problems. So the problem is with newer firmware versions, working without any issues since 2021-06-22 17:16:25 UTC with version 20210315 -- You may reply to this email to add a comment. You are receiving this mail because: You are watching the assignee of the bug.