@@ -270,6 +270,24 @@ void bxt_port_to_phy_channel(struct drm_i915_private *dev_priv, enum port port,
270
270
* ch = DPIO_CH0 ;
271
271
}
272
272
273
+ /*
274
+ * Like intel_de_rmw() but reads from a single per-lane register and
275
+ * writes to the group register to write the same value to all the lanes.
276
+ */
277
+ static u32 bxt_ddi_phy_rmw_grp (struct drm_i915_private * i915 ,
278
+ i915_reg_t reg_single ,
279
+ i915_reg_t reg_group ,
280
+ u32 clear , u32 set )
281
+ {
282
+ u32 old , val ;
283
+
284
+ old = intel_de_read (i915 , reg_single );
285
+ val = (old & ~clear ) | set ;
286
+ intel_de_write (i915 , reg_group , val );
287
+
288
+ return old ;
289
+ }
290
+
273
291
void bxt_ddi_phy_set_signal_levels (struct intel_encoder * encoder ,
274
292
const struct intel_crtc_state * crtc_state )
275
293
{
@@ -291,35 +309,34 @@ void bxt_ddi_phy_set_signal_levels(struct intel_encoder *encoder,
291
309
* While we write to the group register to program all lanes at once we
292
310
* can read only lane registers and we pick lanes 0/1 for that.
293
311
*/
294
- val = intel_de_read (dev_priv , BXT_PORT_PCS_DW10_LN01 (phy , ch ));
295
- val &= ~(TX2_SWING_CALC_INIT | TX1_SWING_CALC_INIT );
296
- intel_de_write (dev_priv , BXT_PORT_PCS_DW10_GRP (phy , ch ), val );
297
-
298
- val = intel_de_read (dev_priv , BXT_PORT_TX_DW2_LN (phy , ch , 0 ));
299
- val &= ~(MARGIN_000_MASK | UNIQ_TRANS_SCALE_MASK );
300
- val |= MARGIN_000 (trans -> entries [level ].bxt .margin ) |
301
- UNIQ_TRANS_SCALE (trans -> entries [level ].bxt .scale );
302
- intel_de_write (dev_priv , BXT_PORT_TX_DW2_GRP (phy , ch ), val );
312
+ bxt_ddi_phy_rmw_grp (dev_priv , BXT_PORT_PCS_DW10_LN01 (phy , ch ),
313
+ BXT_PORT_PCS_DW10_GRP (phy , ch ),
314
+ TX2_SWING_CALC_INIT | TX1_SWING_CALC_INIT , 0 );
315
+
316
+ bxt_ddi_phy_rmw_grp (dev_priv , BXT_PORT_TX_DW2_LN (phy , ch , 0 ),
317
+ BXT_PORT_TX_DW2_GRP (phy , ch ),
318
+ MARGIN_000_MASK | UNIQ_TRANS_SCALE_MASK ,
319
+ MARGIN_000 (trans -> entries [level ].bxt .margin ) |
320
+ UNIQ_TRANS_SCALE (trans -> entries [level ].bxt .scale ));
321
+
322
+ bxt_ddi_phy_rmw_grp (dev_priv , BXT_PORT_TX_DW3_LN (phy , ch , 0 ),
323
+ BXT_PORT_TX_DW3_GRP (phy , ch ),
324
+ SCALE_DCOMP_METHOD ,
325
+ trans -> entries [level ].bxt .enable ?
326
+ SCALE_DCOMP_METHOD : 0 );
303
327
304
328
val = intel_de_read (dev_priv , BXT_PORT_TX_DW3_LN (phy , ch , 0 ));
305
- val &= ~SCALE_DCOMP_METHOD ;
306
- if (trans -> entries [level ].bxt .enable )
307
- val |= SCALE_DCOMP_METHOD ;
308
-
309
329
if ((val & UNIQUE_TRANGE_EN_METHOD ) && !(val & SCALE_DCOMP_METHOD ))
310
330
drm_err (& dev_priv -> drm ,
311
331
"Disabled scaling while ouniqetrangenmethod was set" );
312
332
313
- intel_de_write (dev_priv , BXT_PORT_TX_DW3_GRP (phy , ch ), val );
314
-
315
- val = intel_de_read (dev_priv , BXT_PORT_TX_DW4_LN (phy , ch , 0 ));
316
- val &= ~DE_EMPHASIS_MASK ;
317
- val |= DE_EMPHASIS (trans -> entries [level ].bxt .deemphasis );
318
- intel_de_write (dev_priv , BXT_PORT_TX_DW4_GRP (phy , ch ), val );
333
+ bxt_ddi_phy_rmw_grp (dev_priv , BXT_PORT_TX_DW4_LN (phy , ch , 0 ),
334
+ BXT_PORT_TX_DW4_GRP (phy , ch ), DE_EMPHASIS_MASK ,
335
+ DE_EMPHASIS (trans -> entries [level ].bxt .deemphasis ));
319
336
320
- val = intel_de_read (dev_priv , BXT_PORT_PCS_DW10_LN01 (phy , ch ));
321
- val |= TX2_SWING_CALC_INIT | TX1_SWING_CALC_INIT ;
322
- intel_de_write ( dev_priv , BXT_PORT_PCS_DW10_GRP ( phy , ch ), val );
337
+ bxt_ddi_phy_rmw_grp (dev_priv , BXT_PORT_PCS_DW10_LN01 (phy , ch ),
338
+ BXT_PORT_PCS_DW10_GRP ( phy , ch ),
339
+ 0 , TX2_SWING_CALC_INIT | TX1_SWING_CALC_INIT );
323
340
}
324
341
325
342
bool bxt_ddi_phy_is_enabled (struct drm_i915_private * dev_priv ,
0 commit comments