[Intel-gfx] [PATCH 1/6] drm/i915: Allow removal of whitelist register and refactor
Umesh Nerlige Ramappa
umesh.nerlige.ramappa at intel.com
Thu Jul 30 00:48:21 UTC 2020
- Add a helper to remove whitelisted register from the list.
- Refactor _wa_add to use _wa_index to find an existing whitelisted
register.
- Free the old list when growing the whitelist.
Signed-off-by: Umesh Nerlige Ramappa <umesh.nerlige.ramappa at intel.com>
---
drivers/gpu/drm/i915/gt/intel_workarounds.c | 82 +++++++++++++++------
1 file changed, 58 insertions(+), 24 deletions(-)
diff --git a/drivers/gpu/drm/i915/gt/intel_workarounds.c b/drivers/gpu/drm/i915/gt/intel_workarounds.c
index cef1c122696f..98927f5d63ab 100644
--- a/drivers/gpu/drm/i915/gt/intel_workarounds.c
+++ b/drivers/gpu/drm/i915/gt/intel_workarounds.c
@@ -81,10 +81,49 @@ static void wa_init_finish(struct i915_wa_list *wal)
wal->wa_count, wal->name, wal->engine_name);
}
+static int _wa_index(struct i915_wa_list *wal, i915_reg_t reg)
+{
+ unsigned int addr = i915_mmio_reg_offset(reg);
+ int start = 0, end = wal->count;
+
+ while (start < end) {
+ int mid = start + (end - start) / 2;
+ unsigned int wal_reg = i915_mmio_reg_offset(wal->list[mid].reg);
+
+ wal_reg &= RING_FORCE_TO_NONPRIV_ADDRESS_MASK;
+
+ if (wal_reg < addr)
+ start = mid + 1;
+ else if (wal_reg > addr)
+ end = mid;
+ else
+ return mid;
+ }
+
+ return -1;
+}
+
+static void _wa_remove(struct i915_wa_list *wal, i915_reg_t reg)
+{
+ int index = _wa_index(wal, reg);
+ struct i915_wa *wa = wal->list;
+
+ if (index < 0)
+ return;
+
+ memset(wa + index, 0, sizeof(*wa));
+
+ while (index < wal->count - 1) {
+ swap(wa[index], wa[index + 1]);
+ index++;
+ }
+
+ wal->count--;
+}
+
static void _wa_add(struct i915_wa_list *wal, const struct i915_wa *wa)
{
- unsigned int addr = i915_mmio_reg_offset(wa->reg);
- unsigned int start = 0, end = wal->count;
+ int index;
const unsigned int grow = WA_LIST_CHUNK;
struct i915_wa *wa_;
@@ -100,36 +139,31 @@ static void _wa_add(struct i915_wa_list *wal, const struct i915_wa *wa)
return;
}
- if (wal->list)
+ if (wal->list) {
memcpy(list, wal->list, sizeof(*wa) * wal->count);
+ kfree(wal->list);
+ }
wal->list = list;
}
- while (start < end) {
- unsigned int mid = start + (end - start) / 2;
+ index = _wa_index(wal, wa->reg);
+ if (index >= 0) {
+ wa_ = &wal->list[index];
- if (i915_mmio_reg_offset(wal->list[mid].reg) < addr) {
- start = mid + 1;
- } else if (i915_mmio_reg_offset(wal->list[mid].reg) > addr) {
- end = mid;
- } else {
- wa_ = &wal->list[mid];
-
- if ((wa->clr | wa_->clr) && !(wa->clr & ~wa_->clr)) {
- DRM_ERROR("Discarding overwritten w/a for reg %04x (clear: %08x, set: %08x)\n",
- i915_mmio_reg_offset(wa_->reg),
- wa_->clr, wa_->set);
-
- wa_->set &= ~wa->clr;
- }
+ if ((wa->clr | wa_->clr) && !(wa->clr & ~wa_->clr)) {
+ DRM_ERROR("Discarding overwritten w/a for reg %04x (clear: %08x, set: %08x)\n",
+ i915_mmio_reg_offset(wa_->reg),
+ wa_->clr, wa_->set);
- wal->wa_count++;
- wa_->set |= wa->set;
- wa_->clr |= wa->clr;
- wa_->read |= wa->read;
- return;
+ wa_->set &= ~wa->clr;
}
+
+ wal->wa_count++;
+ wa_->set |= wa->set;
+ wa_->clr |= wa->clr;
+ wa_->read |= wa->read;
+ return;
}
wal->wa_count++;
--
2.20.1
More information about the Intel-gfx
mailing list