@@ -263,13 +263,99 @@ static const struct net_device_ops mlxbf_gige_netdev_ops = {
263
263
.ndo_get_stats64 = mlxbf_gige_get_stats64 ,
264
264
};
265
265
266
- static void mlxbf_gige_adjust_link (struct net_device * netdev )
266
+ static void mlxbf_gige_bf2_adjust_link (struct net_device * netdev )
267
267
{
268
268
struct phy_device * phydev = netdev -> phydev ;
269
269
270
270
phy_print_status (phydev );
271
271
}
272
272
273
+ static void mlxbf_gige_bf3_adjust_link (struct net_device * netdev )
274
+ {
275
+ struct mlxbf_gige * priv = netdev_priv (netdev );
276
+ struct phy_device * phydev = netdev -> phydev ;
277
+ u8 sgmii_mode ;
278
+ u16 ipg_size ;
279
+ u32 val ;
280
+
281
+ if (phydev -> link && phydev -> speed != priv -> prev_speed ) {
282
+ switch (phydev -> speed ) {
283
+ case 1000 :
284
+ ipg_size = MLXBF_GIGE_1G_IPG_SIZE ;
285
+ sgmii_mode = MLXBF_GIGE_1G_SGMII_MODE ;
286
+ break ;
287
+ case 100 :
288
+ ipg_size = MLXBF_GIGE_100M_IPG_SIZE ;
289
+ sgmii_mode = MLXBF_GIGE_100M_SGMII_MODE ;
290
+ break ;
291
+ case 10 :
292
+ ipg_size = MLXBF_GIGE_10M_IPG_SIZE ;
293
+ sgmii_mode = MLXBF_GIGE_10M_SGMII_MODE ;
294
+ break ;
295
+ default :
296
+ return ;
297
+ }
298
+
299
+ val = readl (priv -> plu_base + MLXBF_GIGE_PLU_TX_REG0 );
300
+ val &= ~(MLXBF_GIGE_PLU_TX_IPG_SIZE_MASK | MLXBF_GIGE_PLU_TX_SGMII_MODE_MASK );
301
+ val |= FIELD_PREP (MLXBF_GIGE_PLU_TX_IPG_SIZE_MASK , ipg_size );
302
+ val |= FIELD_PREP (MLXBF_GIGE_PLU_TX_SGMII_MODE_MASK , sgmii_mode );
303
+ writel (val , priv -> plu_base + MLXBF_GIGE_PLU_TX_REG0 );
304
+
305
+ val = readl (priv -> plu_base + MLXBF_GIGE_PLU_RX_REG0 );
306
+ val &= ~MLXBF_GIGE_PLU_RX_SGMII_MODE_MASK ;
307
+ val |= FIELD_PREP (MLXBF_GIGE_PLU_RX_SGMII_MODE_MASK , sgmii_mode );
308
+ writel (val , priv -> plu_base + MLXBF_GIGE_PLU_RX_REG0 );
309
+
310
+ priv -> prev_speed = phydev -> speed ;
311
+ }
312
+
313
+ phy_print_status (phydev );
314
+ }
315
+
316
+ static void mlxbf_gige_bf2_set_phy_link_mode (struct phy_device * phydev )
317
+ {
318
+ /* MAC only supports 1000T full duplex mode */
319
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_1000baseT_Half_BIT );
320
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_100baseT_Full_BIT );
321
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_100baseT_Half_BIT );
322
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_10baseT_Full_BIT );
323
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_10baseT_Half_BIT );
324
+
325
+ /* Only symmetric pause with flow control enabled is supported so no
326
+ * need to negotiate pause.
327
+ */
328
+ linkmode_clear_bit (ETHTOOL_LINK_MODE_Pause_BIT , phydev -> advertising );
329
+ linkmode_clear_bit (ETHTOOL_LINK_MODE_Asym_Pause_BIT , phydev -> advertising );
330
+ }
331
+
332
+ static void mlxbf_gige_bf3_set_phy_link_mode (struct phy_device * phydev )
333
+ {
334
+ /* MAC only supports full duplex mode */
335
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_1000baseT_Half_BIT );
336
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_100baseT_Half_BIT );
337
+ phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_10baseT_Half_BIT );
338
+
339
+ /* Only symmetric pause with flow control enabled is supported so no
340
+ * need to negotiate pause.
341
+ */
342
+ linkmode_clear_bit (ETHTOOL_LINK_MODE_Pause_BIT , phydev -> advertising );
343
+ linkmode_clear_bit (ETHTOOL_LINK_MODE_Asym_Pause_BIT , phydev -> advertising );
344
+ }
345
+
346
+ static struct mlxbf_gige_link_cfg mlxbf_gige_link_cfgs [] = {
347
+ [MLXBF_GIGE_VERSION_BF2 ] = {
348
+ .set_phy_link_mode = mlxbf_gige_bf2_set_phy_link_mode ,
349
+ .adjust_link = mlxbf_gige_bf2_adjust_link ,
350
+ .phy_mode = PHY_INTERFACE_MODE_GMII
351
+ },
352
+ [MLXBF_GIGE_VERSION_BF3 ] = {
353
+ .set_phy_link_mode = mlxbf_gige_bf3_set_phy_link_mode ,
354
+ .adjust_link = mlxbf_gige_bf3_adjust_link ,
355
+ .phy_mode = PHY_INTERFACE_MODE_SGMII
356
+ }
357
+ };
358
+
273
359
static int mlxbf_gige_probe (struct platform_device * pdev )
274
360
{
275
361
struct phy_device * phydev ;
@@ -359,25 +445,14 @@ static int mlxbf_gige_probe(struct platform_device *pdev)
359
445
phydev -> irq = phy_irq ;
360
446
361
447
err = phy_connect_direct (netdev , phydev ,
362
- mlxbf_gige_adjust_link ,
363
- PHY_INTERFACE_MODE_GMII );
448
+ mlxbf_gige_link_cfgs [ priv -> hw_version ]. adjust_link ,
449
+ mlxbf_gige_link_cfgs [ priv -> hw_version ]. phy_mode );
364
450
if (err ) {
365
451
dev_err (& pdev -> dev , "Could not attach to PHY\n" );
366
452
goto out ;
367
453
}
368
454
369
- /* MAC only supports 1000T full duplex mode */
370
- phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_1000baseT_Half_BIT );
371
- phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_100baseT_Full_BIT );
372
- phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_100baseT_Half_BIT );
373
- phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_10baseT_Full_BIT );
374
- phy_remove_link_mode (phydev , ETHTOOL_LINK_MODE_10baseT_Half_BIT );
375
-
376
- /* Only symmetric pause with flow control enabled is supported so no
377
- * need to negotiate pause.
378
- */
379
- linkmode_clear_bit (ETHTOOL_LINK_MODE_Pause_BIT , phydev -> advertising );
380
- linkmode_clear_bit (ETHTOOL_LINK_MODE_Asym_Pause_BIT , phydev -> advertising );
455
+ mlxbf_gige_link_cfgs [priv -> hw_version ].set_phy_link_mode (phydev );
381
456
382
457
/* Display information about attached PHY device */
383
458
phy_attached_info (phydev );
0 commit comments