Skip to content

Commit b7a5738

Browse files
committed
Merge tag 'drm-misc-fixes-2023-07-13' of ssh://git.freedesktop.org/git/drm/drm-misc into drm-fixes
A couple of nouveau patches addressing improving HDMI support and firmware handling, a fix for TTM to skip pinned BO when evicting, and a fix for the fbdev documentation. Signed-off-by: Dave Airlie <[email protected]> From: Maxime Ripard <[email protected]> Link: https://patchwork.freedesktop.org/patch/msgid/nq3ke75juephbex5acfyi5t6bxv22nhmfcpfhru55haj2nv3us@gehrlmjbqgjk
2 parents 06c2afb + 835a65f commit b7a5738

32 files changed

+206
-119
lines changed

drivers/accel/ivpu/ivpu_drv.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ struct ivpu_wa_table {
7575
bool punit_disabled;
7676
bool clear_runtime_mem;
7777
bool d3hot_after_power_off;
78+
bool interrupt_clear_with_0;
7879
};
7980

8081
struct ivpu_hw_info;

drivers/accel/ivpu/ivpu_hw_mtl.c

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,9 @@ static void ivpu_hw_wa_init(struct ivpu_device *vdev)
101101
vdev->wa.punit_disabled = ivpu_is_fpga(vdev);
102102
vdev->wa.clear_runtime_mem = false;
103103
vdev->wa.d3hot_after_power_off = true;
104+
105+
if (ivpu_device_id(vdev) == PCI_DEVICE_ID_MTL && ivpu_revision(vdev) < 4)
106+
vdev->wa.interrupt_clear_with_0 = true;
104107
}
105108

106109
static void ivpu_hw_timeouts_init(struct ivpu_device *vdev)
@@ -885,7 +888,7 @@ static void ivpu_hw_mtl_irq_disable(struct ivpu_device *vdev)
885888
REGB_WR32(MTL_BUTTRESS_GLOBAL_INT_MASK, 0x1);
886889
REGB_WR32(MTL_BUTTRESS_LOCAL_INT_MASK, BUTTRESS_IRQ_DISABLE_MASK);
887890
REGV_WR64(MTL_VPU_HOST_SS_ICB_ENABLE_0, 0x0ull);
888-
REGB_WR32(MTL_VPU_HOST_SS_FW_SOC_IRQ_EN, 0x0);
891+
REGV_WR32(MTL_VPU_HOST_SS_FW_SOC_IRQ_EN, 0x0);
889892
}
890893

891894
static void ivpu_hw_mtl_irq_wdt_nce_handler(struct ivpu_device *vdev)
@@ -973,12 +976,15 @@ static u32 ivpu_hw_mtl_irqb_handler(struct ivpu_device *vdev, int irq)
973976
schedule_recovery = true;
974977
}
975978

976-
/*
977-
* Clear local interrupt status by writing 0 to all bits.
978-
* This must be done after interrupts are cleared at the source.
979-
* Writing 1 triggers an interrupt, so we can't perform read update write.
980-
*/
981-
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, 0x0);
979+
/* This must be done after interrupts are cleared at the source. */
980+
if (IVPU_WA(interrupt_clear_with_0))
981+
/*
982+
* Writing 1 triggers an interrupt, so we can't perform read update write.
983+
* Clear local interrupt status by writing 0 to all bits.
984+
*/
985+
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, 0x0);
986+
else
987+
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, status);
982988

983989
/* Re-enable global interrupt */
984990
REGB_WR32(MTL_BUTTRESS_GLOBAL_INT_MASK, 0x0);

drivers/dma-buf/dma-fence-unwrap.c

Lines changed: 22 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -66,18 +66,36 @@ struct dma_fence *__dma_fence_unwrap_merge(unsigned int num_fences,
6666
{
6767
struct dma_fence_array *result;
6868
struct dma_fence *tmp, **array;
69+
ktime_t timestamp;
6970
unsigned int i;
7071
size_t count;
7172

7273
count = 0;
74+
timestamp = ns_to_ktime(0);
7375
for (i = 0; i < num_fences; ++i) {
74-
dma_fence_unwrap_for_each(tmp, &iter[i], fences[i])
75-
if (!dma_fence_is_signaled(tmp))
76+
dma_fence_unwrap_for_each(tmp, &iter[i], fences[i]) {
77+
if (!dma_fence_is_signaled(tmp)) {
7678
++count;
79+
} else if (test_bit(DMA_FENCE_FLAG_TIMESTAMP_BIT,
80+
&tmp->flags)) {
81+
if (ktime_after(tmp->timestamp, timestamp))
82+
timestamp = tmp->timestamp;
83+
} else {
84+
/*
85+
* Use the current time if the fence is
86+
* currently signaling.
87+
*/
88+
timestamp = ktime_get();
89+
}
90+
}
7791
}
7892

93+
/*
94+
* If we couldn't find a pending fence just return a private signaled
95+
* fence with the timestamp of the last signaled one.
96+
*/
7997
if (count == 0)
80-
return dma_fence_get_stub();
98+
return dma_fence_allocate_private_stub(timestamp);
8199

82100
array = kmalloc_array(count, sizeof(*array), GFP_KERNEL);
83101
if (!array)
@@ -138,7 +156,7 @@ struct dma_fence *__dma_fence_unwrap_merge(unsigned int num_fences,
138156
} while (tmp);
139157

140158
if (count == 0) {
141-
tmp = dma_fence_get_stub();
159+
tmp = dma_fence_allocate_private_stub(ktime_get());
142160
goto return_tmp;
143161
}
144162

drivers/dma-buf/dma-fence.c

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -150,16 +150,17 @@ EXPORT_SYMBOL(dma_fence_get_stub);
150150

151151
/**
152152
* dma_fence_allocate_private_stub - return a private, signaled fence
153+
* @timestamp: timestamp when the fence was signaled
153154
*
154155
* Return a newly allocated and signaled stub fence.
155156
*/
156-
struct dma_fence *dma_fence_allocate_private_stub(void)
157+
struct dma_fence *dma_fence_allocate_private_stub(ktime_t timestamp)
157158
{
158159
struct dma_fence *fence;
159160

160161
fence = kzalloc(sizeof(*fence), GFP_KERNEL);
161162
if (fence == NULL)
162-
return ERR_PTR(-ENOMEM);
163+
return NULL;
163164

164165
dma_fence_init(fence,
165166
&dma_fence_stub_ops,
@@ -169,7 +170,7 @@ struct dma_fence *dma_fence_allocate_private_stub(void)
169170
set_bit(DMA_FENCE_FLAG_ENABLE_SIGNAL_BIT,
170171
&fence->flags);
171172

172-
dma_fence_signal(fence);
173+
dma_fence_signal_timestamp(fence, timestamp);
173174

174175
return fence;
175176
}

drivers/gpu/drm/armada/armada_fbdev.c

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -209,10 +209,6 @@ void armada_fbdev_setup(struct drm_device *dev)
209209
goto err_drm_client_init;
210210
}
211211

212-
ret = armada_fbdev_client_hotplug(&fbh->client);
213-
if (ret)
214-
drm_dbg_kms(dev, "client hotplug ret=%d\n", ret);
215-
216212
drm_client_register(&fbh->client);
217213

218214
return;

drivers/gpu/drm/bridge/synopsys/dw-hdmi.c

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1426,9 +1426,9 @@ void dw_hdmi_set_high_tmds_clock_ratio(struct dw_hdmi *hdmi,
14261426
/* Control for TMDS Bit Period/TMDS Clock-Period Ratio */
14271427
if (dw_hdmi_support_scdc(hdmi, display)) {
14281428
if (mtmdsclock > HDMI14_MAX_TMDSCLK)
1429-
drm_scdc_set_high_tmds_clock_ratio(&hdmi->connector, 1);
1429+
drm_scdc_set_high_tmds_clock_ratio(hdmi->curr_conn, 1);
14301430
else
1431-
drm_scdc_set_high_tmds_clock_ratio(&hdmi->connector, 0);
1431+
drm_scdc_set_high_tmds_clock_ratio(hdmi->curr_conn, 0);
14321432
}
14331433
}
14341434
EXPORT_SYMBOL_GPL(dw_hdmi_set_high_tmds_clock_ratio);
@@ -2116,7 +2116,7 @@ static void hdmi_av_composer(struct dw_hdmi *hdmi,
21162116
min_t(u8, bytes, SCDC_MIN_SOURCE_VERSION));
21172117

21182118
/* Enabled Scrambling in the Sink */
2119-
drm_scdc_set_scrambling(&hdmi->connector, 1);
2119+
drm_scdc_set_scrambling(hdmi->curr_conn, 1);
21202120

21212121
/*
21222122
* To activate the scrambler feature, you must ensure
@@ -2132,7 +2132,7 @@ static void hdmi_av_composer(struct dw_hdmi *hdmi,
21322132
hdmi_writeb(hdmi, 0, HDMI_FC_SCRAMBLER_CTRL);
21332133
hdmi_writeb(hdmi, (u8)~HDMI_MC_SWRSTZ_TMDSSWRST_REQ,
21342134
HDMI_MC_SWRSTZ);
2135-
drm_scdc_set_scrambling(&hdmi->connector, 0);
2135+
drm_scdc_set_scrambling(hdmi->curr_conn, 0);
21362136
}
21372137
}
21382138

@@ -3553,6 +3553,7 @@ struct dw_hdmi *dw_hdmi_probe(struct platform_device *pdev,
35533553
hdmi->bridge.ops = DRM_BRIDGE_OP_DETECT | DRM_BRIDGE_OP_EDID
35543554
| DRM_BRIDGE_OP_HPD;
35553555
hdmi->bridge.interlace_allowed = true;
3556+
hdmi->bridge.ddc = hdmi->ddc;
35563557
#ifdef CONFIG_OF
35573558
hdmi->bridge.of_node = pdev->dev.of_node;
35583559
#endif

drivers/gpu/drm/bridge/ti-sn65dsi86.c

Lines changed: 22 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -170,10 +170,10 @@
170170
* @pwm_refclk_freq: Cache for the reference clock input to the PWM.
171171
*/
172172
struct ti_sn65dsi86 {
173-
struct auxiliary_device bridge_aux;
174-
struct auxiliary_device gpio_aux;
175-
struct auxiliary_device aux_aux;
176-
struct auxiliary_device pwm_aux;
173+
struct auxiliary_device *bridge_aux;
174+
struct auxiliary_device *gpio_aux;
175+
struct auxiliary_device *aux_aux;
176+
struct auxiliary_device *pwm_aux;
177177

178178
struct device *dev;
179179
struct regmap *regmap;
@@ -468,27 +468,34 @@ static void ti_sn65dsi86_delete_aux(void *data)
468468
auxiliary_device_delete(data);
469469
}
470470

471-
/*
472-
* AUX bus docs say that a non-NULL release is mandatory, but it makes no
473-
* sense for the model used here where all of the aux devices are allocated
474-
* in the single shared structure. We'll use this noop as a workaround.
475-
*/
476-
static void ti_sn65dsi86_noop(struct device *dev) {}
471+
static void ti_sn65dsi86_aux_device_release(struct device *dev)
472+
{
473+
struct auxiliary_device *aux = container_of(dev, struct auxiliary_device, dev);
474+
475+
kfree(aux);
476+
}
477477

478478
static int ti_sn65dsi86_add_aux_device(struct ti_sn65dsi86 *pdata,
479-
struct auxiliary_device *aux,
479+
struct auxiliary_device **aux_out,
480480
const char *name)
481481
{
482482
struct device *dev = pdata->dev;
483+
struct auxiliary_device *aux;
483484
int ret;
484485

486+
aux = kzalloc(sizeof(*aux), GFP_KERNEL);
487+
if (!aux)
488+
return -ENOMEM;
489+
485490
aux->name = name;
486491
aux->dev.parent = dev;
487-
aux->dev.release = ti_sn65dsi86_noop;
492+
aux->dev.release = ti_sn65dsi86_aux_device_release;
488493
device_set_of_node_from_dev(&aux->dev, dev);
489494
ret = auxiliary_device_init(aux);
490-
if (ret)
495+
if (ret) {
496+
kfree(aux);
491497
return ret;
498+
}
492499
ret = devm_add_action_or_reset(dev, ti_sn65dsi86_uninit_aux, aux);
493500
if (ret)
494501
return ret;
@@ -497,6 +504,8 @@ static int ti_sn65dsi86_add_aux_device(struct ti_sn65dsi86 *pdata,
497504
if (ret)
498505
return ret;
499506
ret = devm_add_action_or_reset(dev, ti_sn65dsi86_delete_aux, aux);
507+
if (!ret)
508+
*aux_out = aux;
500509

501510
return ret;
502511
}

drivers/gpu/drm/drm_client.c

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -122,13 +122,34 @@ EXPORT_SYMBOL(drm_client_init);
122122
* drm_client_register() it is no longer permissible to call drm_client_release()
123123
* directly (outside the unregister callback), instead cleanup will happen
124124
* automatically on driver unload.
125+
*
126+
* Registering a client generates a hotplug event that allows the client
127+
* to set up its display from pre-existing outputs. The client must have
128+
* initialized its state to able to handle the hotplug event successfully.
125129
*/
126130
void drm_client_register(struct drm_client_dev *client)
127131
{
128132
struct drm_device *dev = client->dev;
133+
int ret;
129134

130135
mutex_lock(&dev->clientlist_mutex);
131136
list_add(&client->list, &dev->clientlist);
137+
138+
if (client->funcs && client->funcs->hotplug) {
139+
/*
140+
* Perform an initial hotplug event to pick up the
141+
* display configuration for the client. This step
142+
* has to be performed *after* registering the client
143+
* in the list of clients, or a concurrent hotplug
144+
* event might be lost; leaving the display off.
145+
*
146+
* Hold the clientlist_mutex as for a regular hotplug
147+
* event.
148+
*/
149+
ret = client->funcs->hotplug(client);
150+
if (ret)
151+
drm_dbg_kms(dev, "client hotplug ret=%d\n", ret);
152+
}
132153
mutex_unlock(&dev->clientlist_mutex);
133154
}
134155
EXPORT_SYMBOL(drm_client_register);

drivers/gpu/drm/drm_fbdev_dma.c

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -217,7 +217,7 @@ static const struct drm_client_funcs drm_fbdev_dma_client_funcs = {
217217
* drm_fbdev_dma_setup() - Setup fbdev emulation for GEM DMA helpers
218218
* @dev: DRM device
219219
* @preferred_bpp: Preferred bits per pixel for the device.
220-
* @dev->mode_config.preferred_depth is used if this is zero.
220+
* 32 is used if this is zero.
221221
*
222222
* This function sets up fbdev emulation for GEM DMA drivers that support
223223
* dumb buffers with a virtual address and that can be mmap'ed.
@@ -252,10 +252,6 @@ void drm_fbdev_dma_setup(struct drm_device *dev, unsigned int preferred_bpp)
252252
goto err_drm_client_init;
253253
}
254254

255-
ret = drm_fbdev_dma_client_hotplug(&fb_helper->client);
256-
if (ret)
257-
drm_dbg_kms(dev, "client hotplug ret=%d\n", ret);
258-
259255
drm_client_register(&fb_helper->client);
260256

261257
return;

drivers/gpu/drm/drm_fbdev_generic.c

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -339,10 +339,6 @@ void drm_fbdev_generic_setup(struct drm_device *dev, unsigned int preferred_bpp)
339339
goto err_drm_client_init;
340340
}
341341

342-
ret = drm_fbdev_generic_client_hotplug(&fb_helper->client);
343-
if (ret)
344-
drm_dbg_kms(dev, "client hotplug ret=%d\n", ret);
345-
346342
drm_client_register(&fb_helper->client);
347343

348344
return;

0 commit comments

Comments
 (0)